Add compareDocumentPosition (fixes #1794) to Node

This commit is contained in:
Manish Goregaokar 2014-03-11 22:51:44 +05:30
parent 8e16c00367
commit a2e15df4ab
3 changed files with 81 additions and 3 deletions

View file

@ -82,6 +82,7 @@ DOMInterfaces = {
'needsAbstract': [
'appendChild',
'childNodes',
'compareDocumentPosition',
'contains',
'insertBefore',
'isEqualNode',

View file

@ -31,6 +31,7 @@ use std::cast;
use std::cell::{RefCell, Ref, RefMut};
use std::iter::{Map, Filter};
use std::libc::uintptr_t;
use std::ptr;
use std::unstable::raw::Box;
use std::util;
@ -1507,9 +1508,49 @@ impl Node {
}
// http://dom.spec.whatwg.org/#dom-node-comparedocumentposition
pub fn CompareDocumentPosition(&self, _other: &JS<Node>) -> u16 {
// FIXME (#1794) implement.
0
pub fn CompareDocumentPosition(&self, abstract_self: &JS<Node>, other: &JS<Node>) -> u16 {
static DOCUMENT_POSITION_DISCONNECTED: u16 = 0x01u16;
static DOCUMENT_POSITION_PRECEDING: u16 = 0x02u16;
static DOCUMENT_POSITION_FOLLOWING: u16 = 0x04u16;
static DOCUMENT_POSITION_CONTAINS: u16 = 0x08u16;
static DOCUMENT_POSITION_CONTAINED_BY: u16 = 0x10u16;
static DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC: u16 = 0x20u16;
if abstract_self == other {
0
} else {
let mut lastself = abstract_self.clone();
let mut lastother = other.clone();
for ancestor in abstract_self.ancestors() {
if &ancestor == other {
return DOCUMENT_POSITION_CONTAINS + DOCUMENT_POSITION_PRECEDING;
}
lastself = ancestor;
}
for ancestor in other.ancestors() {
if &ancestor == abstract_self {
return DOCUMENT_POSITION_CONTAINED_BY + DOCUMENT_POSITION_FOLLOWING;
}
lastother = ancestor;
}
if lastself != lastother {
let random = if ptr::to_unsafe_ptr(abstract_self.get()) < ptr::to_unsafe_ptr(other.get()) {
DOCUMENT_POSITION_FOLLOWING
} else {
DOCUMENT_POSITION_PRECEDING
};
return random + DOCUMENT_POSITION_DISCONNECTED + DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC;
}
for child in lastself.traverse_preorder() {
if &child == other {
return DOCUMENT_POSITION_PRECEDING;
}
if &child == abstract_self {
return DOCUMENT_POSITION_FOLLOWING;
}
}
unreachable!()
}
}
// http://dom.spec.whatwg.org/#dom-node-contains

View file

@ -0,0 +1,36 @@
<!DOCTYPE html>
<html>
<head>
<script src="harness.js"></script>
<script>
{
var elem = document.createElement("div");
var other = document.createElement("div");
is(elem.compareDocumentPosition(elem),0);
var nonTree = elem.compareDocumentPosition(other);
var prefix = Node.DOCUMENT_POSITION_DISCONNECTED + Node.DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC;
is(nonTree == prefix + Node.DOCUMENT_POSITION_FOLLOWING || nonTree == prefix + Node.DOCUMENT_POSITION_PRECEDING,
true);
elem.appendChild(other);
is(elem.compareDocumentPosition(other), Node.DOCUMENT_POSITION_CONTAINED_BY + Node.DOCUMENT_POSITION_FOLLOWING);
is(other.compareDocumentPosition(elem), Node.DOCUMENT_POSITION_CONTAINS + Node.DOCUMENT_POSITION_PRECEDING);
var another = document.createElement("div");
other.appendChild(another);
is(elem.compareDocumentPosition(another), Node.DOCUMENT_POSITION_CONTAINED_BY + Node.DOCUMENT_POSITION_FOLLOWING);
is(another.compareDocumentPosition(elem), Node.DOCUMENT_POSITION_CONTAINS + Node.DOCUMENT_POSITION_PRECEDING);
var follower = document.createElement("div");
elem.appendChild(follower);
var preceder = document.createElement("div");
another.appendChild(preceder);
is(another.compareDocumentPosition(follower), Node.DOCUMENT_POSITION_FOLLOWING);
is(follower.compareDocumentPosition(another), Node.DOCUMENT_POSITION_PRECEDING);
is(follower.compareDocumentPosition(preceder), Node.DOCUMENT_POSITION_PRECEDING);
finish();
}
</script>
</head>
</html>