Commit 90ed96a7 authored by Nikolay Sivov's avatar Nikolay Sivov Committed by Alexandre Julliard

dwrite: Fix splitting by bidi levels.

parent 1f55764d
......@@ -2750,15 +2750,17 @@ static HRESULT WINAPI dwritetextlayout_sink_SetBidiLevel(IDWriteTextAnalysisSink
struct dwrite_textlayout *layout = impl_from_IDWriteTextAnalysisSink(iface);
struct layout_run *cur_run;
TRACE("%u %u %u %u\n", position, length, explicitLevel, resolvedLevel);
LIST_FOR_EACH_ENTRY(cur_run, &layout->runs, struct layout_run, entry) {
struct regular_layout_run *cur = &cur_run->u.regular;
struct layout_run *run, *run2;
struct layout_run *run;
if (cur_run->kind == LAYOUT_RUN_INLINE)
continue;
/* FIXME: levels are reported in a natural forward direction, so start loop from a run we ended on */
if (position < cur->descr.textPosition || position > cur->descr.textPosition + cur->descr.stringLength)
if (position < cur->descr.textPosition || position >= cur->descr.textPosition + cur->descr.stringLength)
continue;
/* full hit - just set run level */
......@@ -2775,35 +2777,23 @@ static HRESULT WINAPI dwritetextlayout_sink_SetBidiLevel(IDWriteTextAnalysisSink
continue;
}
/* now starting point is in a run, so it splits it */
/* all fully covered runs are processed at this point, reuse existing run for remaining
reported bidi range and add another run for the rest of original one */
run = alloc_layout_run(LAYOUT_RUN_REGULAR);
if (!run)
return E_OUTOFMEMORY;
*run = *cur_run;
run->u.regular.descr.textPosition = position;
run->u.regular.descr.stringLength = cur->descr.stringLength - position + cur->descr.textPosition;
run->u.regular.descr.string = &layout->str[position];
run->u.regular.run.bidiLevel = resolvedLevel;
cur->descr.stringLength -= position - cur->descr.textPosition;
run->u.regular.descr.textPosition = position + length;
run->u.regular.descr.stringLength = cur->descr.stringLength - length;
run->u.regular.descr.string = &layout->str[position + length];
list_add_after(&cur_run->entry, &run->entry);
if (position + length == run->u.regular.descr.textPosition + run->u.regular.descr.stringLength)
break;
/* reduce existing run */
cur->run.bidiLevel = resolvedLevel;
cur->descr.stringLength -= length;
/* split second time */
run2 = alloc_layout_run(LAYOUT_RUN_REGULAR);
if (!run2)
return E_OUTOFMEMORY;
*run2 = *cur_run;
run2->u.regular.descr.textPosition = run->u.regular.descr.textPosition + run->u.regular.descr.stringLength;
run2->u.regular.descr.stringLength = cur->descr.textPosition + cur->descr.stringLength - position - length;
run2->u.regular.descr.string = &layout->str[run2->u.regular.descr.textPosition];
run->u.regular.descr.stringLength -= run2->u.regular.descr.stringLength;
list_add_after(&run->entry, &run2->entry);
list_add_after(&cur_run->entry, &run->entry);
break;
}
......
......@@ -878,6 +878,13 @@ static struct sa_test sa_tests[] = {
{0x2d30,0x2d4a,0}, 1,
{ { 0, 2, DWRITE_SCRIPT_SHAPES_DEFAULT }}
},
{
/* LRE/PDF */
{0x202a,0x202c,'a','b','c','\r',0}, 3,
{ { 0, 2, DWRITE_SCRIPT_SHAPES_NO_VISUAL },
{ 2, 3, DWRITE_SCRIPT_SHAPES_DEFAULT },
{ 5, 1, DWRITE_SCRIPT_SHAPES_NO_VISUAL } }
},
/* keep this as end marker */
{ {0} }
};
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment