@Override
    public DatatypeStreamingValidator createStreamingValidator(
            ValidationContext context) {
        return new DatatypeStreamingValidator() {

            int codepoint = -2;

            private void addCharacter(char c) {
                if (codepoint == -1) {
                    return;
                } else if ((codepoint & 0xFC00) == 0xD800) {
                    if ((c & 0xFC00) == 0xDC00) {
                        codepoint = (codepoint << 10) + c + SURROGATE_OFFSET;
                    } else {
                        codepoint = -1;
                    }
                } else if (codepoint == -2) {
                    codepoint = c;
                } else {
                    codepoint = -1;
                }
            }

            @Override
            public void addCharacters(char[] buf, int start, int len) {
                if (codepoint == -1) {
                    return;
                } else {
                    for (int i = start; i < start + len; i++) {
                        addCharacter(buf[i]);
                    }
                }
            }

            @Override
            public void checkValid() throws DatatypeException {
                if (codepoint == -2) {
                    throw newDatatypeException(
                            "The empty string is not a " + getName() + ".");
                } else if (codepoint == -1) {
                    throw newDatatypeException(
                            "A " + getName() + " must be a single character.");
                } else if (!getUnicodeSet().contains(codepoint)) {
                    throw newDatatypeException(0, "The character ",
                            UCharacter.toString(codepoint),
                            " is not a " + getName() + ".");
                }
            }

            @Override
            public boolean isValid() {
                try {
                    checkValid();
                    return true;
                } catch (DatatypeException e) {
                    return false;
                }
            }

        };
    }
@see nu.validator.datatype.AbstractDatatype#createStreamingValidator(org.relaxng.datatype.ValidationContext)
src/nu/validator/datatype/AbstractUnicodeClassCharacter.java