399 lines
13 KiB
C++
399 lines
13 KiB
C++
|
/*
|
||
|
*
|
||
|
* (C) Copyright IBM Corp. and others 1998-2013 - All Rights Reserved
|
||
|
*
|
||
|
*/
|
||
|
|
||
|
#include "LETypes.h"
|
||
|
#include "MorphTables.h"
|
||
|
#include "StateTables.h"
|
||
|
#include "MorphStateTables.h"
|
||
|
#include "SubtableProcessor2.h"
|
||
|
#include "StateTableProcessor2.h"
|
||
|
#include "IndicRearrangementProcessor2.h"
|
||
|
#include "LEGlyphStorage.h"
|
||
|
#include "LESwaps.h"
|
||
|
|
||
|
U_NAMESPACE_BEGIN
|
||
|
|
||
|
UOBJECT_DEFINE_RTTI_IMPLEMENTATION(IndicRearrangementProcessor2)
|
||
|
|
||
|
IndicRearrangementProcessor2::IndicRearrangementProcessor2(const MorphSubtableHeader2 *morphSubtableHeader)
|
||
|
: StateTableProcessor2(morphSubtableHeader)
|
||
|
{
|
||
|
indicRearrangementSubtableHeader = (const IndicRearrangementSubtableHeader2 *) morphSubtableHeader;
|
||
|
entryTable = (const IndicRearrangementStateEntry2 *) ((char *) &stateTableHeader->stHeader + entryTableOffset);
|
||
|
}
|
||
|
|
||
|
IndicRearrangementProcessor2::~IndicRearrangementProcessor2()
|
||
|
{
|
||
|
}
|
||
|
|
||
|
void IndicRearrangementProcessor2::beginStateTable()
|
||
|
{
|
||
|
firstGlyph = 0;
|
||
|
lastGlyph = 0;
|
||
|
}
|
||
|
|
||
|
le_uint16 IndicRearrangementProcessor2::processStateEntry(LEGlyphStorage &glyphStorage, le_int32 &currGlyph, EntryTableIndex2 index)
|
||
|
{
|
||
|
const IndicRearrangementStateEntry2 *entry = &entryTable[index];
|
||
|
le_uint16 newState = SWAPW(entry->newStateIndex); // index to the new state
|
||
|
IndicRearrangementFlags flags = (IndicRearrangementFlags) SWAPW(entry->flags);
|
||
|
|
||
|
if (flags & irfMarkFirst) {
|
||
|
firstGlyph = currGlyph;
|
||
|
}
|
||
|
|
||
|
if (flags & irfMarkLast) {
|
||
|
lastGlyph = currGlyph;
|
||
|
}
|
||
|
|
||
|
doRearrangementAction(glyphStorage, (IndicRearrangementVerb) (flags & irfVerbMask));
|
||
|
|
||
|
if (!(flags & irfDontAdvance)) {
|
||
|
currGlyph += dir;
|
||
|
}
|
||
|
|
||
|
return newState; // index to new state
|
||
|
}
|
||
|
|
||
|
void IndicRearrangementProcessor2::endStateTable()
|
||
|
{
|
||
|
}
|
||
|
|
||
|
void IndicRearrangementProcessor2::doRearrangementAction(LEGlyphStorage &glyphStorage, IndicRearrangementVerb verb) const
|
||
|
{
|
||
|
LEGlyphID a, b, c, d;
|
||
|
le_int32 ia, ib, ic, id, ix, x;
|
||
|
LEErrorCode success = LE_NO_ERROR;
|
||
|
|
||
|
switch(verb)
|
||
|
{
|
||
|
case irvNoAction:
|
||
|
break;
|
||
|
|
||
|
case irvxA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
x = firstGlyph + 1;
|
||
|
|
||
|
while (x <= lastGlyph) {
|
||
|
glyphStorage[x - 1] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x - 1, ix, success);
|
||
|
x += 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvDx:
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = lastGlyph - 1;
|
||
|
|
||
|
while (x >= firstGlyph) {
|
||
|
glyphStorage[x + 1] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x + 1, ix, success);
|
||
|
x -= 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = d;
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
break;
|
||
|
|
||
|
case irvDxA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
|
||
|
glyphStorage[firstGlyph] = glyphStorage[lastGlyph];
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvxAB:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
x = firstGlyph + 2;
|
||
|
|
||
|
while (x <= lastGlyph) {
|
||
|
glyphStorage[x - 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x - 2, ix, success);
|
||
|
x += 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = a;
|
||
|
glyphStorage[lastGlyph] = b;
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ia, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ib, success);
|
||
|
break;
|
||
|
|
||
|
case irvxBA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
x = firstGlyph + 2;
|
||
|
|
||
|
while (x <= lastGlyph) {
|
||
|
glyphStorage[x - 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x - 2, ix, success);
|
||
|
x += 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = b;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ib, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvCDx:
|
||
|
c = glyphStorage[lastGlyph - 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = lastGlyph - 2;
|
||
|
|
||
|
while (x >= firstGlyph) {
|
||
|
glyphStorage[x + 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x + 2, ix, success);
|
||
|
x -= 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = c;
|
||
|
glyphStorage[firstGlyph + 1] = d;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, ic, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, id, success);
|
||
|
break;
|
||
|
|
||
|
case irvDCx:
|
||
|
c = glyphStorage[lastGlyph - 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = lastGlyph - 2;
|
||
|
|
||
|
while (x >= firstGlyph) {
|
||
|
glyphStorage[x + 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x + 2, ix, success);
|
||
|
x -= 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = d;
|
||
|
glyphStorage[firstGlyph + 1] = c;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, ic, success);
|
||
|
break;
|
||
|
|
||
|
case irvCDxA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
c = glyphStorage[lastGlyph - 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = lastGlyph - 2;
|
||
|
|
||
|
while (x > firstGlyph) {
|
||
|
glyphStorage[x + 1] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x + 1, ix, success);
|
||
|
x -= 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = c;
|
||
|
glyphStorage[firstGlyph + 1] = d;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, ic, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, id, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvDCxA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
c = glyphStorage[lastGlyph - 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = lastGlyph - 2;
|
||
|
|
||
|
while (x > firstGlyph) {
|
||
|
glyphStorage[x + 1] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x + 1, ix, success);
|
||
|
x -= 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = d;
|
||
|
glyphStorage[firstGlyph + 1] = c;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, ic, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvDxAB:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = firstGlyph + 2;
|
||
|
|
||
|
while (x < lastGlyph) {
|
||
|
glyphStorage[x - 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x - 2, ix, success);
|
||
|
x += 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = d;
|
||
|
glyphStorage[lastGlyph - 1] = a;
|
||
|
glyphStorage[lastGlyph] = b;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ia, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ib, success);
|
||
|
break;
|
||
|
|
||
|
case irvDxBA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
d = glyphStorage[lastGlyph];
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
x = firstGlyph + 2;
|
||
|
|
||
|
while (x < lastGlyph) {
|
||
|
glyphStorage[x - 2] = glyphStorage[x];
|
||
|
ix = glyphStorage.getCharIndex(x, success);
|
||
|
glyphStorage.setCharIndex(x - 2, ix, success);
|
||
|
x += 1;
|
||
|
}
|
||
|
|
||
|
glyphStorage[firstGlyph] = d;
|
||
|
glyphStorage[lastGlyph - 1] = b;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ib, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvCDxAB:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
|
||
|
glyphStorage[firstGlyph] = glyphStorage[lastGlyph - 1];
|
||
|
glyphStorage[firstGlyph + 1] = glyphStorage[lastGlyph];
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = a;
|
||
|
glyphStorage[lastGlyph] = b;
|
||
|
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, ic, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, id, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ia, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ib, success);
|
||
|
break;
|
||
|
|
||
|
case irvCDxBA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
|
||
|
glyphStorage[firstGlyph] = glyphStorage[lastGlyph - 1];
|
||
|
glyphStorage[firstGlyph + 1] = glyphStorage[lastGlyph];
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = b;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, ic, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, id, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ib, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
case irvDCxAB:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
|
||
|
glyphStorage[firstGlyph] = glyphStorage[lastGlyph];
|
||
|
glyphStorage[firstGlyph + 1] = glyphStorage[lastGlyph - 1];
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = a;
|
||
|
glyphStorage[lastGlyph] = b;
|
||
|
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, ic, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ia, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ib, success);
|
||
|
break;
|
||
|
|
||
|
case irvDCxBA:
|
||
|
a = glyphStorage[firstGlyph];
|
||
|
b = glyphStorage[firstGlyph + 1];
|
||
|
|
||
|
glyphStorage[firstGlyph] = glyphStorage[lastGlyph];
|
||
|
glyphStorage[firstGlyph + 1] = glyphStorage[lastGlyph - 1];
|
||
|
|
||
|
glyphStorage[lastGlyph - 1] = b;
|
||
|
glyphStorage[lastGlyph] = a;
|
||
|
|
||
|
ia = glyphStorage.getCharIndex(firstGlyph, success);
|
||
|
ib = glyphStorage.getCharIndex(firstGlyph + 1, success);
|
||
|
ic = glyphStorage.getCharIndex(lastGlyph - 1, success);
|
||
|
id = glyphStorage.getCharIndex(lastGlyph, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(firstGlyph, id, success);
|
||
|
glyphStorage.setCharIndex(firstGlyph + 1, ic, success);
|
||
|
|
||
|
glyphStorage.setCharIndex(lastGlyph - 1, ib, success);
|
||
|
glyphStorage.setCharIndex(lastGlyph, ia, success);
|
||
|
break;
|
||
|
|
||
|
default:
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
U_NAMESPACE_END
|