2 * Copyright (C) 2004-2008 Geometer Plus <contact@geometerplus.com>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
22 #include <ZLStringUtil.h>
24 #include "StyleSheetParser.h"
26 StyleSheetParser::StyleSheetParser(StyleSheetTable
&table
) : myTable(table
), myReadState(TAG_NAME
), myInsideComment(false) {
29 void StyleSheetParser::reset() {
31 myAttributeName
.erase();
32 myReadState
= TAG_NAME
;
33 myInsideComment
= false;
34 myElement
= StyleSheetTable::Element();
37 void StyleSheetParser::parse(const char *text
, int len
) {
38 const char *start
= text
;
39 const char *end
= text
+ len
;
40 for (const char *ptr
= start
; ptr
!= end
; ++ptr
) {
43 myWord
.append(start
, ptr
- start
);
48 } else if (isControlSymbol(*ptr
)) {
50 myWord
.append(start
, ptr
- start
);
60 bool StyleSheetParser::isControlSymbol(const char symbol
) {
72 void StyleSheetParser::processControl(const char control
) {
75 myReadState
= (myReadState
== TAG_NAME
) ? ATTRIBUTE_NAME
: BROKEN
;
78 if (myReadState
!= BROKEN
) {
79 myTable
.addElement(myElement
);
81 myReadState
= TAG_NAME
;
82 myElement
= StyleSheetTable::Element();
86 ((myReadState
== ATTRIBUTE_VALUE
) ||
87 (myReadState
== ATTRIBUTE_NAME
)) ? ATTRIBUTE_NAME
: BROKEN
;
90 myReadState
= (myReadState
== ATTRIBUTE_NAME
) ? ATTRIBUTE_VALUE
: BROKEN
;
95 void StyleSheetParser::processWord(std::string
&word
) {
96 while (!word
.empty()) {
97 int index
= word
.find(myInsideComment
? "*/" : "/*");
98 if (!myInsideComment
) {
100 processWordWithoutComments(word
);
101 } else if (index
> 0) {
102 processWordWithoutComments(word
.substr(0, index
));
108 myInsideComment
= !myInsideComment
;
109 word
.erase(0, index
+ 2);
113 void StyleSheetParser::processWordWithoutComments(const std::string
&word
) {
114 switch (myReadState
) {
117 int index
= word
.find('.');
119 myElement
.first
.TagName
= word
;
121 myElement
.first
.TagName
= word
.substr(0, index
);
122 myElement
.first
.ClassName
= word
.substr(index
+ 1);
127 myAttributeName
= word
;
128 myElement
.second
[myAttributeName
].clear();
130 case ATTRIBUTE_VALUE
:
131 myElement
.second
[myAttributeName
].push_back(word
);