Skip to content

Commit

Permalink
Support multiline url declarations
Browse files Browse the repository at this point in the history
This is a continuation of the previous work done to bring our
`url()` parsing up to scratch with Ruby Sass. With this update
we can remove the trasnitional legacy `url()` parsing logic.

Fixes sass#1096
  • Loading branch information
xzyfer committed Dec 28, 2015
1 parent 2ecaa66 commit 431d477
Show file tree
Hide file tree
Showing 4 changed files with 36 additions and 28 deletions.
45 changes: 35 additions & 10 deletions src/parser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -298,12 +298,13 @@ namespace Sass {
else if (lex< uri_prefix >()) {
Arguments* args = SASS_MEMORY_NEW(ctx.mem, Arguments, pstate);
Function_Call* result = SASS_MEMORY_NEW(ctx.mem, Function_Call, pstate, "url", args);

if (lex< quoted_string >()) {
Expression* the_url = parse_string();
*args << SASS_MEMORY_NEW(ctx.mem, Argument, the_url->pstate(), the_url);
}
else if (lex < uri_value >(false)) { // don't skip comments
String* the_url = parse_interpolated_chunk(lexed);
else if (String* the_url = parse_url_function_argument()) {

*args << SASS_MEMORY_NEW(ctx.mem, Argument, the_url->pstate(), the_url);
}
else if (peek < skip_over_scopes < exactly < '(' >, exactly < ')' > > >(position)) {
Expand Down Expand Up @@ -1687,29 +1688,53 @@ namespace Sass {
}

String* Parser::parse_url_function_string()
{
std::string prefix("");
if (lex< uri_prefix >()) {
prefix = std::string(lexed);
}

String* url_string = parse_url_function_argument();

std::string suffix("");
if (lex< real_uri_suffix >()) {
suffix = std::string(lexed);
}

if (String_Schema* schema = dynamic_cast<String_Schema*>(url_string)) {
String_Schema* res = SASS_MEMORY_NEW(ctx.mem, String_Schema, pstate);
(*res) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, prefix);
(*res) += schema;
(*res) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, suffix);
return res;
} else {
std::string res = prefix + url_string->to_string() + suffix;
return SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, res);
}
}

String* Parser::parse_url_function_argument()
{
const char* p = position;

lex< uri_prefix >();
std::string prefix = lexed;
std::string uri("");
if (lex< real_uri_value >(false)) {
uri = lexed.to_string();
}

lex< real_uri_value >(false);
std::string uri = lexed;

if (peek< exactly< hash_lbrace > >()) {
const char* pp = position;
// TODO: error checking for unclosed interpolants
while (peek< exactly< hash_lbrace > >(pp)) {
pp = sequence< interpolant, real_uri_value >(pp);
}
position = peek< real_uri_suffix >(pp);
position = pp;
return parse_interpolated_chunk(Token(p, position));
} else {
lex< real_uri_suffix >();
std::string res = prefix + Util::rtrim(uri) + lexed.to_string();
std::string res = Util::rtrim(uri);
return SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, res);
}

}

Function_Call* Parser::parse_function_call()
Expand Down
1 change: 1 addition & 0 deletions src/parser.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -253,6 +253,7 @@ namespace Sass {
Function_Call* parse_function_call();
Function_Call_Schema* parse_function_call_schema();
String* parse_url_function_string();
String* parse_url_function_argument();
String* parse_interpolated_chunk(Token, bool constant = false);
String* parse_string();
String_Constant* parse_static_expression();
Expand Down
17 changes: 0 additions & 17 deletions src/prelexer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -605,23 +605,6 @@ namespace Sass {
const char* uri_prefix(const char* src) {
return exactly<url_kwd>(src);
}
const char* uri_value(const char* src)
{
return
sequence <
negate <
exactly < '$' >
>,
zero_plus <
alternatives <
alnum,
interpolant,
exactly <'/'>,
class_char < uri_chars >
>
>
>(src);
}

// TODO: rename the following two functions
/* no longer used - remove?
Expand Down
1 change: 0 additions & 1 deletion src/prelexer.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -296,7 +296,6 @@ namespace Sass {
// const char* rgb_prefix(const char* src);
// Match CSS uri specifiers.
const char* uri_prefix(const char* src);
const char* uri_value(const char* src);
// Match CSS "!important" keyword.
const char* kwd_important(const char* src);
// Match CSS "!optional" keyword.
Expand Down

0 comments on commit 431d477

Please # to comment.