diff --git a/src/renderer/dx/CustomTextLayout.cpp b/src/renderer/dx/CustomTextLayout.cpp index d3715d999be..7cf0fcb32e4 100644 --- a/src/renderer/dx/CustomTextLayout.cpp +++ b/src/renderer/dx/CustomTextLayout.cpp @@ -498,6 +498,20 @@ CustomTextLayout::CustomTextLayout(IDWriteFactory2* const factory, glyphRunDescription.stringLength = run.textLength; glyphRunDescription.textPosition = run.textStart; + // Calculate the origin for the next run based on the amount of space + // that would be consumed. We are doing this calculation now, not after, + // because if the text is RTL then we need to advance immediately, before the + // write call since DirectX expects the origin to the RIGHT of the text for RTL. + const auto postOriginX = std::accumulate(_glyphAdvances.begin() + run.glyphStart, + _glyphAdvances.begin() + run.glyphStart + run.glyphCount, + mutableOrigin.x); + + // Check for RTL, if it is, apply space adjustment. + if (WI_IsFlagSet(glyphRun.bidiLevel, 1)) + { + mutableOrigin.x = postOriginX; + } + // Try to draw it RETURN_IF_FAILED(renderer->DrawGlyphRun(clientDrawingContext, mutableOrigin.x, @@ -507,10 +521,9 @@ CustomTextLayout::CustomTextLayout(IDWriteFactory2* const factory, &glyphRunDescription, nullptr)); - // Shift origin to the right for the next run based on the amount of space consumed. - mutableOrigin.x = std::accumulate(_glyphAdvances.begin() + run.glyphStart, - _glyphAdvances.begin() + run.glyphStart + run.glyphCount, - mutableOrigin.x); + // Either way, we should be at this point by the end of writing this sequence, + // whether it was LTR or RTL. + mutableOrigin.x = postOriginX; } } CATCH_RETURN();