CSSTokenizer::Scope::Scope(const String& string, CSSParserObserverWrapper& wrapper)
: m_string(string)
{
    if (string.isEmpty())
        return;

    CSSTokenizerInputStream input(string);
    CSSTokenizer tokenizer(input, *this);

    unsigned offset = 0;
    while (true) {
        CSSParserToken token = tokenizer.nextToken();
        if (token.type() == EOFToken)
            break;
        if (token.type() == CommentToken) {
            wrapper.addComment(offset, input.offset(), m_tokens.size());
        } else {
            m_tokens.append(token);
            wrapper.addToken(offset);
        }
        offset = input.offset();
    }

    wrapper.addToken(offset);
    wrapper.finalizeConstruction(m_tokens.begin());
}
Beispiel #2
0
void compareTokens(const CSSParserToken& expected, const CSSParserToken& actual)
{
    ASSERT_EQ(expected.type(), actual.type());
    switch (expected.type()) {
    case DelimiterToken:
        ASSERT_EQ(expected.delimiter(), actual.delimiter());
        break;
    case IdentToken:
    case FunctionToken:
    case StringToken:
    case UrlToken:
        ASSERT_EQ(expected.value(), actual.value());
        break;
    case DimensionToken:
        ASSERT_EQ(expected.value(), actual.value());
        // fallthrough
    case NumberToken:
    case PercentageToken:
        ASSERT_EQ(expected.numericValueType(), actual.numericValueType());
        ASSERT_DOUBLE_EQ(expected.numericValue(), actual.numericValue());
        break;
    case UnicodeRangeToken:
        ASSERT_EQ(expected.unicodeRangeStart(), actual.unicodeRangeStart());
        ASSERT_EQ(expected.unicodeRangeEnd(), actual.unicodeRangeEnd());
        break;
    case HashToken:
        ASSERT_EQ(expected.value(), actual.value());
        ASSERT_EQ(expected.hashTokenType(), actual.hashTokenType());
        break;
    default:
        break;
    }
}
CSSTokenizer::Scope::Scope(const String& string)
: m_string(string)
{
    // According to the spec, we should perform preprocessing here.
    // See: http://dev.w3.org/csswg/css-syntax/#input-preprocessing
    //
    // However, we can skip this step since:
    // * We're using HTML spaces (which accept \r and \f as a valid white space)
    // * Do not count white spaces
    // * CSSTokenizerInputStream::peek replaces NULLs for replacement characters

    if (string.isEmpty())
        return;

    // To avoid resizing we err on the side of reserving too much space.
    // Most strings we tokenize have about 3.5 to 5 characters per token.
    m_tokens.reserveInitialCapacity(string.length() / 3);

    CSSTokenizerInputStream input(string);
    CSSTokenizer tokenizer(input, *this);
    while (true) {
        CSSParserToken token = tokenizer.nextToken();
        if (token.type() == CommentToken)
            continue;
        if (token.type() == EOFToken)
            return;
        m_tokens.append(token);
    }
}
    bool parseValue(CSSParserTokenRange& tokens, Value* result)
    {
        CSSParserToken token = tokens.consumeIncludingWhitespace();
        if (!(token.type() == NumberToken || token.type() == PercentageToken || token.type() == DimensionToken))
            return false;

        CSSPrimitiveValue::UnitType type = token.unitType();
        if (unitCategory(type) == CalcOther)
            return false;

        result->value = CSSCalcPrimitiveValue::create(
            CSSPrimitiveValue::create(token.numericValue(), type), token.numericValueType() == IntegerValueType);

        return true;
    }
Beispiel #5
0
bool consumeSlashIncludingWhitespace(CSSParserTokenRange& range)
{
    CSSParserToken value = range.peek();
    if (value.type() != DelimiterToken || value.delimiter() != '/')
        return false;
    range.consumeIncludingWhitespace();
    return true;
}
Beispiel #6
0
bool consumeCommaIncludingWhitespace(CSSParserTokenRange& range)
{
    CSSParserToken value = range.peek();
    if (value.type() != CommaToken)
        return false;
    range.consumeIncludingWhitespace();
    return true;
}
Beispiel #7
0
void testTokens(const String& string, const CSSParserToken& token1, const CSSParserToken& token2 = CSSParserToken(EOFToken), const CSSParserToken& token3 = CSSParserToken(EOFToken))
{
    Vector<CSSParserToken> expectedTokens;
    expectedTokens.append(token1);
    if (token2.type() != EOFToken) {
        expectedTokens.append(token2);
        if (token3.type() != EOFToken)
            expectedTokens.append(token3);
    }

    Vector<CSSParserToken> actualTokens;
    CSSTokenizer::tokenize(string, actualTokens);

    ASSERT_EQ(expectedTokens.size(), actualTokens.size());
    for (size_t i = 0; i < expectedTokens.size(); ++i)
        compareTokens(expectedTokens[i], actualTokens[i]);
}
bool CSSVariableParser::isValidVariableName(const CSSParserToken& token)
{
    if (token.type() != IdentToken)
        return false;

    CSSParserString value = token.value();
    return value.length() >= 2 && value[0] == '-' && value[1] == '-';
}
void MediaQueryParser::processToken(const CSSParserToken& token)
{
    CSSParserTokenType type = token.type();

    handleBlocks(token);
    m_blockWatcher.handleToken(token);

    // Call the function that handles current state
    if (type != WhitespaceToken)
        ((this)->*(m_state))(type, token);
}
void testTokens(const String& string, const CSSParserToken& token1, const CSSParserToken& token2 = CSSParserToken(EOFToken), const CSSParserToken& token3 = CSSParserToken(EOFToken))
{
    Vector<CSSParserToken> expectedTokens;
    expectedTokens.append(token1);
    if (token2.type() != EOFToken) {
        expectedTokens.append(token2);
        if (token3.type() != EOFToken)
            expectedTokens.append(token3);
    }

    CSSParserTokenRange expected(expectedTokens);

    CSSTokenizer::Scope actualScope(string);
    CSSParserTokenRange actual = actualScope.tokenRange();

    // Just check that serialization doesn't hit any asserts
    actual.serialize();

    while (!expected.atEnd() || !actual.atEnd())
        compareTokens(expected.consume(), actual.consume());
}
Beispiel #11
0
void CSSTokenizer::tokenize(String string, Vector<CSSParserToken>& outTokens)
{
    // According to the spec, we should perform preprocessing here.
    // See: http://dev.w3.org/csswg/css-syntax/#input-preprocessing
    //
    // However, we can skip this step since:
    // * We're using HTML spaces (which accept \r and \f as a valid white space)
    // * Do not count white spaces
    // * consumeEscape replaces NULLs for replacement characters

    if (string.isEmpty())
        return;

    CSSTokenizerInputStream input(string);
    CSSTokenizer tokenizer(input);
    while (true) {
        CSSParserToken token = tokenizer.nextToken();
        outTokens.append(token);
        if (token.type() == EOFToken)
            return;
    }
}
void MediaQueryParser::handleBlocks(const CSSParserToken& token)
{
    if (token.blockType() == CSSParserToken::BlockStart
        && (token.type() != LeftParenthesisToken || m_blockWatcher.blockLevel()))
            m_state = SkipUntilBlockEnd;
}
 char operatorValue(const CSSParserToken& token)
 {
     if (token.type() == DelimiterToken)
         return token.delimiter();
     return 0;
 }