001: package net.sf.saxon.style;
002:
003: import net.sf.saxon.expr.Expression;
004: import net.sf.saxon.instruct.Executable;
005: import net.sf.saxon.om.AttributeCollection;
006: import net.sf.saxon.om.NamePool;
007: import net.sf.saxon.om.QNameException;
008: import net.sf.saxon.pattern.*;
009: import net.sf.saxon.trans.Mode;
010: import net.sf.saxon.trans.XPathException;
011: import net.sf.saxon.type.Type;
012:
013: import java.util.StringTokenizer;
014:
015: /**
016: * An xsl:preserve-space or xsl:strip-space elements in stylesheet. <br>
017: */
018:
019: public class XSLPreserveSpace extends StyleElement {
020:
021: private String elements;
022:
023: public void prepareAttributes() throws XPathException {
024:
025: AttributeCollection atts = getAttributeList();
026:
027: for (int a = 0; a < atts.getLength(); a++) {
028: int nc = atts.getNameCode(a);
029: String f = getNamePool().getClarkName(nc);
030: if (f == StandardNames.ELEMENTS) {
031: elements = atts.getValue(a);
032: } else {
033: checkUnknownAttribute(nc);
034: }
035: }
036: if (elements == null) {
037: reportAbsence("elements");
038: elements = "*"; // for error recovery
039: }
040: }
041:
042: public void validate() throws XPathException {
043: checkTopLevel(null);
044: }
045:
046: public Expression compile(Executable exec) throws XPathException {
047: Boolean preserve = Boolean
048: .valueOf(getFingerprint() == StandardNames.XSL_PRESERVE_SPACE);
049: Mode stripperRules = getPrincipalStylesheet()
050: .getStripperRules();
051:
052: // elements is a space-separated list of element names
053:
054: StringTokenizer st = new StringTokenizer(elements);
055: while (st.hasMoreTokens()) {
056: String s = st.nextToken();
057: NodeTestPattern pat = new NodeTestPattern();
058: // following information is used in conflict warnings
059: pat.setOriginalText(s);
060: pat.setSystemId(getSystemId());
061: pat.setLineNumber(getLineNumber());
062: NodeTest nt;
063: if (s.equals("*")) {
064: nt = AnyNodeTest.getInstance();
065: pat.setNodeTest(nt);
066: stripperRules.addRule(pat, preserve, getPrecedence(),
067: -0.5);
068:
069: } else if (s.endsWith(":*")) {
070: if (s.length() == 2) {
071: compileError("No prefix before ':*'");
072: }
073: String prefix = s.substring(0, s.length() - 2);
074: String uri = getURIForPrefix(prefix, false);
075: nt = new NamespaceTest(getTargetNamePool(),
076: Type.ELEMENT, uri);
077: pat.setNodeTest(nt);
078: stripperRules.addRule(pat, preserve, getPrecedence(),
079: -0.25);
080: } else if (s.startsWith("*:")) {
081: if (s.length() == 2) {
082: compileError("No local name after '*:'");
083: }
084: String localname = s.substring(2);
085: nt = new LocalNameTest(getTargetNamePool(),
086: Type.ELEMENT, localname);
087: pat.setNodeTest(nt);
088: stripperRules.addRule(pat, preserve, getPrecedence(),
089: -0.25);
090: } else {
091: String prefix;
092: String localName = null;
093: String uri = null;
094: try {
095: String[] parts = getConfiguration()
096: .getNameChecker().getQNameParts(s);
097: prefix = parts[0];
098: uri = getURIForPrefix(prefix, false);
099: if (uri == null) {
100: undeclaredNamespaceError(prefix, "XTSE0280");
101: return null;
102: }
103: localName = parts[1];
104: } catch (QNameException err) {
105: compileError("Element name " + s
106: + " is not a valid QName", "XTSE0280");
107: return null;
108: }
109: NamePool target = getTargetNamePool();
110: int nameCode = target.allocate("", uri, localName);
111: nt = new NameTest(Type.ELEMENT, nameCode, getNamePool());
112: pat.setNodeTest(nt);
113: stripperRules
114: .addRule(pat, preserve, getPrecedence(), 0);
115: }
116:
117: }
118: return null;
119: }
120:
121: }
122:
123: //
124: // The contents of this file are subject to the Mozilla Public License Version 1.0 (the "License");
125: // you may not use this file except in compliance with the License. You may obtain a copy of the
126: // License at http://www.mozilla.org/MPL/
127: //
128: // Software distributed under the License is distributed on an "AS IS" basis,
129: // WITHOUT WARRANTY OF ANY KIND, either express or implied.
130: // See the License for the specific language governing rights and limitations under the License.
131: //
132: // The Original Code is: all this file.
133: //
134: // The Initial Developer of the Original Code is Michael H. Kay.
135: //
136: // Portions created by (your name) are Copyright (C) (your legal entity). All Rights Reserved.
137: //
138: // Contributor(s): none.
139: //
|