Class | Kwartz::CssStyleParser |
In: |
kwartz/parser.rb
|
Parent: | PresentationLogicParser |
css style presentation logic parser
example of presentation logic in css style:
/* comment */ #idname, .classname, tagname { value: @var; attrs: "class" @classname, "bgcolro" color; append: @value==item['list'] ? ' checked' : ''; logic: { @list.each { |item| _stag _cont _etag } } }
CSSSTYLE_KEYWORDS | = | { 'begin'=>:begin, 'end'=>:end } |
mode | [RW] |
# File kwartz/parser.rb, line 605 def initialize(*args) super @mode = :selector # :selector or :declaration end
# File kwartz/parser.rb, line 613 def parse(input, filename='') reset(input, filename) scan() rulesets = [] while @token == :command # '@import' command = @value case command when '@import' imported_rulesets = parse_import_command() rulesets += imported_rulesets when '@from' # TODO when '@import_pdata' # TODO else raise parse_error("#{command}: unsupported command.") end end while @token == :selector selectors = parse_selectors() unless @token == '{''{' raise parse_error("'#{@value}': '{' is expected.") #' end @mode = :declaration _linenum, _column = @linenum, @column ruleset = Ruleset.new(selectors) parse_declaration(ruleset) unless @token raise parse_error("'#{selectors.first}': is not closed by '}'.", _linenum, _column) end @mode = :selector rulesets << ruleset scan() end unless @token == nil raise parse_error("'#{@value}': selector is expected.") end return rulesets end
# File kwartz/parser.rb, line 741 def has_colon? unless @ch == ?: raise parse_error("'#{@value}': ':' is required.") end getch() end
# File kwartz/parser.rb, line 766 def parse_declaration(ruleset) assert unless @token == '{''{' while true scan() flag_escape = escape?(@value) case @token when nil ; break when '}''}' ; break when :stag ; has_colon?(); ruleset.set_stag _parse_expr() , flag_escape when :cont ; has_colon?(); ruleset.set_cont _parse_expr() , flag_escape when :etag ; has_colon?(); ruleset.set_etag _parse_expr() , flag_escape when :elem ; has_colon?(); ruleset.set_elem _parse_expr() , flag_escape when :value ; has_colon?(); ruleset.set_value _parse_expr() , flag_escape when :attrs ; has_colon?(); ruleset.set_attrs _parse_pairs(), flag_escape when :append ; has_colon?(); ruleset.set_append _parse_exprs(), flag_escape when :remove ; has_colon?(); ruleset.set_remove _parse_strs() when :tagname; has_colon?(); ruleset.set_tagname _parse_str() when :logic ; has_colon?(); ruleset.set_logic _parse_block() when :before ; has_colon?(); ruleset.set_before _parse_block() when :after ; has_colon?(); ruleset.set_after _parse_block() when :begin ; has_colon?(); ruleset.set_before _parse_block() when :end ; has_colon?(); ruleset.set_after _parse_block() else raise parse_error("'#{@value}': unexpected token.") #' end end return ruleset end
# File kwartz/parser.rb, line 796 def parse_import_command c = @ch c = getch() while is_whitespace(c) t = scan_string() t == :string or raise parse_error("@import: requires filename.") filename = @value if @filename && !@filename.empty? dir = File.dirname(@filename) filename = dir + '/' + filename if dir != '.' end test(?f, filename) or raise parse_error("'#{filename}': import file not found.") _linenum, _column = @linenum, @column c = @ch c = getch() while is_whitespace(c) c == ?; or raise parse_error("';' required.") c = getch() scan() parser = self.class.new(@properties) begin ruleset_list = parser.parse(File.read(filename), filename) rescue => ex parse_error(ex.message, _linenum, _column) end return ruleset_list end
# File kwartz/parser.rb, line 749 def parse_selectors assert unless @token == :selector start_linenum = @linenum selectors = [ @value ] scan() while @token == ','',' scan() unless @token == :selector raise parse_error("'#{@value}': selector is expected (or additional comma exists).") #' end selectors << @value scan() end return selectors end
return false when not hooked
# File kwartz/parser.rb, line 658 def scan_hook ## comment c = @ch if c == ?/ c = getch() if c == ?/ # line comment scan_line() getch() return scan() elsif c == ?* # region comment start_linenum = @linenum while true c = getch() while c != ?* break if c == nil c = getch() break if c == ?/ end if c == nil @error = :comment_unclosed @value = start_linenum return @token == :error end getch() return scan() else @value = '/' return @token = ?/ end #if end #if ## if @mode == :selector # '#name' or '.name' if c == ?# || c == ?. start_char = c name = '' while is_identchar(c = getch()) || c == ?- name << c end if name.empty? @error = :invalid_char @value = start_char.chr return @token = :error end @value = start_char.chr + name return @token = :selector end # 'tagname' if is_identchar(c) || c == ?- name = c.chr while is_identchar(c = getch()) || c == ?- || c == ?: name << c end @value = name return @token = :selector end # '@import' if c == ?@ name = '' while is_identchar(c = getch()) name << c end if name.empty? @error = :invalid_char @value = '@' return @token = :error end @value = '@' + name return @token = :command end end return false end