001: /*
002: * Copyright 1999-2004 The Apache Software Foundation
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016: package org.apache.commons.jxpath.ri.model.jdom;
017:
018: import java.util.ArrayList;
019: import java.util.Collections;
020: import java.util.List;
021:
022: import org.apache.commons.jxpath.ri.QName;
023: import org.apache.commons.jxpath.ri.model.NodeIterator;
024: import org.apache.commons.jxpath.ri.model.NodePointer;
025: import org.jdom.Attribute;
026: import org.jdom.Element;
027: import org.jdom.Namespace;
028:
029: /**
030: * An iterator of attributes of a DOM Node.
031: *
032: * @author Dmitri Plotnikov
033: * @version $Revision: 1.6 $ $Date: 2004/02/29 14:17:40 $
034: */
035: public class JDOMAttributeIterator implements NodeIterator {
036: private NodePointer parent;
037: private QName name;
038: private List attributes;
039: private int position = 0;
040:
041: public JDOMAttributeIterator(NodePointer parent, QName name) {
042: this .parent = parent;
043: this .name = name;
044: if (parent.getNode() instanceof Element) {
045: Element element = (Element) parent.getNode();
046: String prefix = name.getPrefix();
047: Namespace ns;
048: if (prefix != null) {
049: if (prefix.equals("xml")) {
050: ns = Namespace.XML_NAMESPACE;
051: } else {
052: ns = element.getNamespace(prefix);
053: if (ns == null) {
054: // TBD: no attributes
055: attributes = Collections.EMPTY_LIST;
056: return;
057: }
058: }
059: } else {
060: ns = Namespace.NO_NAMESPACE;
061: }
062:
063: String lname = name.getName();
064: if (!lname.equals("*")) {
065: attributes = new ArrayList();
066: if (ns != null) {
067: Attribute attr = element.getAttribute(lname, ns);
068: if (attr != null) {
069: attributes.add(attr);
070: }
071: }
072: } else {
073: attributes = new ArrayList();
074: List allAttributes = element.getAttributes();
075: for (int i = 0; i < allAttributes.size(); i++) {
076: Attribute attr = (Attribute) allAttributes.get(i);
077: if (attr.getNamespace().equals(ns)) {
078: attributes.add(attr);
079: }
080: }
081: }
082: }
083: }
084:
085: /*
086: private boolean testAttr(Attr attr, QName testName) {
087: String nodePrefix = DOMNodePointer.getPrefix(attr);
088: String nodeLocalName = DOMNodePointer.getLocalName(attr);
089:
090: if (nodePrefix != null && nodePrefix.equals("xmlns")) {
091: return false;
092: }
093:
094: if (nodePrefix == null && nodeLocalName.equals("xmlns")) {
095: return false;
096: }
097:
098: String testLocalName = name.getName();
099: if (testLocalName.equals("*") || testLocalName.equals(nodeLocalName)) {
100: String testPrefix = testName.getPrefix();
101:
102: if (equalStrings(testPrefix, nodePrefix)) {
103: return true;
104: }
105:
106: String testNS = null;
107: if (testPrefix != null) {
108: testNS = parent.getNamespaceURI(testPrefix);
109: }
110:
111: String nodeNS = null;
112: if (nodePrefix != null) {
113: nodeNS = parent.getNamespaceURI(nodePrefix);
114: }
115: return equalStrings(testNS, nodeNS);
116: }
117: return false;
118: }
119:
120: private static boolean equalStrings(String s1, String s2) {
121: if (s1 == null && s2 != null) {
122: return false;
123: }
124: if (s1 != null && !s1.equals(s2)) {
125: return false;
126: }
127: return true;
128: }
129:
130: private Attr getAttribute(Element element, QName name) {
131: String testPrefix = name.getPrefix();
132: String testNS = null;
133:
134: if (testPrefix != null) {
135: testNS = parent.getNamespaceURI(testPrefix);
136: }
137:
138: if (testNS != null) {
139: Attr attr = element.getAttributeNodeNS(testNS, name.getName());
140: if (attr == null) {
141: // This may mean that the parser does not support NS for
142: // attributes, example - the version of Crimson bundled
143: // with JDK 1.4.0
144: NamedNodeMap nnm = element.getAttributes();
145: for (int i = 0; i < nnm.getLength(); i++) {
146: attr = (Attr)nnm.item(i);
147: if (testAttr(attr, name)) {
148: return attr;
149: }
150: }
151: }
152: return attr;
153: }
154: else {
155: return element.getAttributeNode(name.getName());
156: }
157: }
158: */
159: public NodePointer getNodePointer() {
160: if (position == 0) {
161: if (!setPosition(1)) {
162: return null;
163: }
164: position = 0;
165: }
166: int index = position - 1;
167: if (index < 0) {
168: index = 0;
169: }
170: return new JDOMAttributePointer(parent, (Attribute) attributes
171: .get(index));
172: }
173:
174: public int getPosition() {
175: return position;
176: }
177:
178: public boolean setPosition(int position) {
179: if (attributes == null) {
180: return false;
181: }
182: this .position = position;
183: return position >= 1 && position <= attributes.size();
184: }
185: }
|