Example #1
0
// DirectionString reports the direction of the given label as defined by RFC
// 5893. The Bidi Rule does not have to be applied to labels of the category
// LeftToRight.
func DirectionString(s string) bidi.Direction {
	for i := 0; i < len(s); {
		e, sz := bidi.LookupString(s[i:])
		if sz == 0 {
			i++
		}
		c := e.Class()
		if c == bidi.R || c == bidi.AL || c == bidi.AN {
			return bidi.RightToLeft
		}
		i += sz
	}
	return bidi.LeftToRight
}
Example #2
0
func (t *Transformer) advanceString(s string) (n int, ok bool) {
	var e bidi.Properties
	var sz int
	for n < len(s) {
		if s[n] < utf8.RuneSelf {
			e, sz = asciiTable[s[n]], 1
		} else {
			e, sz = bidi.LookupString(s[n:])
			if sz <= 1 {
				if sz == 1 {
					return n, false // invalid UTF-8
				}
				return n, true // incomplete UTF-8 encoding
			}
		}
		// TODO: using CompactClass results in noticeable speedup.
		// See unicode/bidi/prop.go:Properties.CompactClass.
		c := uint16(1 << e.Class())
		t.seen |= c
		if t.seen&exclusiveRTL == exclusiveRTL {
			t.state = ruleInvalid
			return n, false
		}
		switch tr := transitions[t.state]; {
		case tr[0].mask&c != 0:
			t.state = tr[0].next
		case tr[1].mask&c != 0:
			t.state = tr[1].next
		default:
			t.state = ruleInvalid
			if t.isRTL() {
				return n, false
			}
		}
		n += sz
	}
	return n, true
}