package org.lobobrowser.util;
import java.util.Iterator;
import java.util.function.Consumer;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
public class Nodes {
public static Node getCommonAncestor(final Node node1, final Node node2) {
if ((node1 == null) || (node2 == null)) {
return null;
}
Node checkNode = node1;
while (!isSameOrAncestorOf(checkNode, node2)) {
checkNode = checkNode.getParentNode();
if (checkNode == null) {
return null;
}
}
return checkNode;
}
public static boolean isSameOrAncestorOf(final Node node, final Node child) {
if (child.isSameNode(node)) {
return true;
}
final Node parent = child.getParentNode();
if (parent == null) {
return false;
}
return isSameOrAncestorOf(node, parent);
}
private static Iterable<Node> emptyIterableNode = new Iterable<Node>() {
@Override
public Iterator<Node> iterator() {
return new Iterator<Node>() {
@Override
public boolean hasNext() {
return false;
}
@Override
public Node next() {
throw new IllegalStateException();
}
@Override
public void remove() {
throw new NotImplementedYetException();
}
};
}
};
public static Iterable<Node> makeIterable(final NodeList nodeList) {
if (nodeList == null) {
return emptyIterableNode;
} else {
return new Iterable<Node>() {
@Override
public Iterator<Node> iterator() {
return new Iterator<Node>() {
private int i = 0;
@Override
public boolean hasNext() {
return i < nodeList.getLength();
}
@Override
public Node next() {
return nodeList.item(i++);
}
@Override
public void remove() {
throw new NotImplementedYetException();
}
};
}
};
}
}
private static Iterable<Element> emptyIterableElement = new Iterable<Element>() {
@Override
public Iterator<Element> iterator() {
return new Iterator<Element>() {
@Override
public boolean hasNext() {
return false;
}
@Override
public Element next() {
throw new IllegalStateException();
}
@Override
public void remove() {
throw new NotImplementedYetException();
}
};
}
};
public static Iterable<Element> makeIterableElements(final NodeList nodeList) {
if (nodeList == null) {
return emptyIterableElement;
} else {
return new Iterable<Element>() {
@Override
public Iterator<Element> iterator() {
return new Iterator<Element>() {
private int i = 0;
@Override
public boolean hasNext() {
return i < nodeList.getLength();
}
@Override
public Element next() {
return (Element) nodeList.item(i++);
}
@Override
public void remove() {
throw new NotImplementedYetException();
}
};
}
};
}
}
public static void forEachNode(final Node node, final Consumer<Node> consumer) {
// TODO: Change from recursive to iterative
for (final Node child : Nodes.makeIterable(node.getChildNodes())) {
consumer.accept(child);
forEachNode(child, consumer);
}
}
}