1 """CSSNamespaceRule currently implements
2 http://www.w3.org/TR/2006/WD-css3-namespace-20060828/
3
4 The following changes have been done:
5 1. the url() syntax is not implemented as it may (?) be deprecated
6 anyway
7 """
8 __all__ = ['CSSNamespaceRule']
9 __docformat__ = 'restructuredtext'
10 __author__ = '$LastChangedBy: cthedot $'
11 __date__ = '$LastChangedDate: 2007-08-20 22:07:12 +0200 (Mo, 20 Aug 2007) $'
12 __version__ = '$LastChangedRevision: 257 $'
13
14 import xml.dom
15
16 import cssrule
17 import cssutils
18
19
21 """
22 Represents an @namespace rule within a CSS style sheet.
23
24 The @namespace at-rule declares a namespace prefix and associates
25 it with a given namespace (a string). This namespace prefix can then be
26 used in namespace-qualified names such as those described in the
27 Selectors Module [SELECT] or the Values and Units module [CSS3VAL].
28
29 Properties
30 ==========
31 cssText: of type DOMString
32 The parsable textual representation of this rule
33 uri: of type DOMString
34 The namespace URI (a simple string!) which is bound to the given
35 prefix. If no prefix is set (``CSSNamespaceRule.prefix==''``)
36 the namespace defined by uri is set as the default namespace.
37 prefix: of type DOMString
38 The prefix used in the stylesheet for the given
39 ``CSSNamespaceRule.nsuri``. If prefix is empty uri sets the default
40 namespace for the stylesheet.
41
42 cssutils only
43 -------------
44 atkeyword:
45 the literal keyword used
46
47 Inherits properties from CSSRule
48
49 Format
50 ======
51 namespace
52 : NAMESPACE_SYM S* [namespace_prefix S*]? [STRING|URI] S* ';' S*
53 ;
54 namespace_prefix
55 : IDENT
56 ;
57 """
58 type = cssrule.CSSRule.NAMESPACE_RULE
59
60 - def __init__(self, uri=None, prefix=u'', readonly=False):
61 """
62 if readonly allows setting of properties in constructor only
63
64 Do not use as positional but as keyword attributes only!
65
66 uri
67 The namespace URI (a simple string!) which is bound to the
68 given prefix. If no prefix is set
69 (``CSSNamespaceRule.prefix==''``) the namespace defined by
70 uri is set as the default namespace
71 prefix
72 The prefix used in the stylesheet for the given
73 ``CSSNamespaceRule.uri``.
74 """
75 super(CSSNamespaceRule, self).__init__()
76
77 self.atkeyword = u'@namespace'
78 self.uri = uri
79 self.prefix = prefix
80 self.seq = [self.prefix, self.uri]
81
82 self._readonly = readonly
83
84
86 """ returns uri as a string """
87 return self._uri
88
90 """
91 DOMException on setting
92
93 - SYNTAX_ERR: (not checked here)
94 Raised if the specified CSS string value has a syntax error and
95 is unparsable.
96 - NO_MODIFICATION_ALLOWED_ERR: (CSSRule)
97 Raised if this rule is readonly.
98 """
99 self._checkReadonly()
100
101
102 for i, x in enumerate(self.seq):
103 if x == self._uri:
104 self.seq[i] = uri
105 break
106 else:
107 self.seq = [uri]
108
109 self._uri = uri
110
111 uri = property(_getURI, _setURI,
112 doc="URI (string!) of the defined namespace.")
113
114
116 """ returns prefix """
117 return self._prefix
118
120 """
121 DOMException on setting
122
123 - SYNTAX_ERR: (not checked here)
124 Raised if the specified CSS string value has a syntax error and
125 is unparsable.
126 - NO_MODIFICATION_ALLOWED_ERR: (CSSRule)
127 Raised if this rule is readonly.
128 """
129 self._checkReadonly()
130
131
132 self._prefix = prefix
133
134 for i, x in enumerate(self.seq):
135 if x == self._prefix:
136 self.seq[i] = prefix
137 break
138 else:
139 self.seq[0] = prefix
140
141 prefix = property(_getPrefix, _setPrefix,
142 doc="Prefix used for the defined namespace.")
143
144
145 - def _getCssText(self):
146 """
147 returns serialized property cssText
148 """
149 return cssutils.ser.do_CSSNamespaceRule(self)
150
151 - def _setCssText(self, cssText):
152 """
153 DOMException on setting
154
155 - HIERARCHY_REQUEST_ERR: (CSSStylesheet)
156 Raised if the rule cannot be inserted at this point in the
157 style sheet.
158 - INVALID_MODIFICATION_ERR: (self)
159 Raised if the specified CSS string value represents a different
160 type of rule than the current one.
161 - NO_MODIFICATION_ALLOWED_ERR: (CSSRule)
162 Raised if the rule is readonly.
163 - SYNTAX_ERR: (self)
164 Raised if the specified CSS string value has a syntax error and
165 is unparsable.
166 """
167 super(CSSNamespaceRule, self)._setCssText(cssText)
168 tokens = self._tokenize(cssText)
169 valid = True
170
171
172 if not tokens or tokens and tokens[0].type != self._ttypes.NAMESPACE_SYM:
173 self._log.error(u'CSSNamespaceRule: No CSSNamespaceRule found: %s' %
174 self._valuestr(cssText),
175 error=xml.dom.InvalidModificationErr)
176 return
177 else:
178 newatkeyword = tokens[0].value
179
180 newseq = []
181 newuri = None
182 newprefix = u''
183
184 expected = 'uri or prefix'
185 for i in range(1, len(tokens)):
186 t = tokens[i]
187
188 if self._ttypes.EOF == t.type:
189 expected = 'EOF'
190
191 elif self._ttypes.S == t.type:
192 pass
193
194 elif self._ttypes.COMMENT == t.type:
195 newseq.append(cssutils.css.CSSComment(t))
196
197 elif 'uri or prefix' == expected and\
198 self._ttypes.IDENT == t.type:
199 newprefix = t.value
200 newseq.append(newprefix)
201 expected = 'uri'
202
203 elif expected.startswith('uri') and \
204 t.type in (self._ttypes.URI, self._ttypes.STRING):
205 if t.type == self._ttypes.URI:
206 newuri = t.value[4:-1].strip()
207 if newuri[0] == newuri[-1] == '"' or\
208 newuri[0] == newuri[-1] == "'":
209 newuri = newuri[1:-1]
210 self._log.warn(
211 u'CSSNamespaceRule: Found namespace definition with url(uri), this may be deprecated in the future, use string format "uri" instead.',
212 t, error = None, neverraise=True)
213 else:
214 newuri = t.value[1:-1]
215 newseq.append(newuri)
216 expected = 'semicolon'
217
218 elif self._ttypes.SEMICOLON == t.type:
219 if 'semicolon' != expected:
220 valid = False
221 self._log.error(
222 u'CSSNamespaceRule: No namespace URI found.', t)
223 expected = None
224 continue
225
226 else:
227 valid = False
228 self._log.error(u'CSSNamespaceRule: Syntax Error.', t)
229
230 if expected and expected != 'EOF':
231 valid = False
232 self._log.error(u'CSSNamespaceRule: Syntax Error, no ";" found: %s' %
233 self._valuestr(cssText))
234 return
235
236 if valid:
237 self.atkeyword = newatkeyword
238 self.uri = newuri
239 self.prefix = newprefix
240 self.seq = newseq
241
242 cssText = property(fget=_getCssText, fset=_setCssText,
243 doc="(DOM attribute) The parsable textual representation.")
244
246 return "cssutils.css.%s(uri=%r, prefix=%r)" % (
247 self.__class__.__name__, self.uri, self.prefix)
248
250 return "<cssutils.css.%s object uri=%r prefix=%r at 0x%x>" % (
251 self.__class__.__name__, self.uri, self.prefix, id(self))
252
253 if __name__ == '__main__':
254 c = CSSNamespaceRule()
255 c.uri = "x"
256 print c.cssText
257 c.prefix = "p"
258 print c.cssText
259 c.cssText = r'''@namespace "\"";'''
260 print c.cssText
261