comments; work in IE 8; failing test for IE 9

This commit is contained in:
David Greenspan
2013-09-02 14:45:19 -07:00
parent 12a17d3bfe
commit e104d43021
3 changed files with 69 additions and 9 deletions

View File

@@ -65,6 +65,22 @@ var checkId = function (id) {
throw new Error("id may not be empty");
};
var textExpandosOk = (function () {
var tn = document.createTextNode('');
try {
tn.blahblah = true;
return true;
} catch (e) {
// IE 8
return false;
}
})();
var createMarkerNode = (
textExpandosOk ?
function () { return document.createTextNode(""); } :
function () { return document.createComment(""); });
var DomRange = function (component) {
// This code supports IE 8 if `createTextNode` is changed
// to `createComment`. What we really should do is:
@@ -73,9 +89,10 @@ var DomRange = function (component) {
// - keep a list of all DomRanges to avoid IE 9+ GC of
// TextNodes; this will probably help DomRange removal
// detection too.
var start = document.createTextNode("");
var end = document.createTextNode("");
var start = createMarkerNode();
var end = createMarkerNode();
var fragment = DomBackend.newFragment([start, end]);
fragment.$_uiIsOffscreen = true;
if (component) {
this.component = component;
@@ -730,8 +747,9 @@ DomRange.prototype.$ = function (selector) {
// Since jQuery can't run selectors on a DocumentFragment,
// we don't expect findBySelector to work.
if (parentNode.nodeType === 11) // DocumentFragment
throw new Error("Can't use $ on a detached component");
if (parentNode.nodeType === 11 /* DocumentFragment */ ||
parentNode.$_uiIsOffscreen)
throw new Error("Can't use $ on an offscreen component");
var results = DomBackend.findBySelector(selector, parentNode);
@@ -817,8 +835,17 @@ var HandlerRec = function (elem, type, selector, handler, $ui) {
};
})(this);
var tryCapturing = (! eventsToDelegate.hasOwnProperty(
DomBackend.parseEventType(type)));
// WHY CAPTURE AND DELEGATE: jQuery can't delegate
// non-bubbling events, because
// event capture doesn't work in IE 8. However, there
// are all sorts of new-fangled non-bubbling events
// like "play" and "touchenter". We delegate these
// events using capture in all browsers except IE 8.
// IE 8 doesn't support these events anyway.
var tryCapturing = elem.addEventListener &&
(! eventsToDelegate.hasOwnProperty(
DomBackend.parseEventType(type)));
if (tryCapturing) {
this.capturingHandler = (function (h) {

View File

@@ -731,7 +731,7 @@ Tinytest.add("ui - DomRange - contains", function (test) {
test.isTrue(r.contains(span));
test.isTrue(s.contains(span));
test.isTrue(t.contains(span));
test.isFalse(r.contains(r.parentNode));
test.isFalse(r.contains(r.parentNode()));
test.isFalse(r.contains(document.createElement("DIV")));
});
});
@@ -808,6 +808,37 @@ Tinytest.add("ui - DomRange - get", function (test) {
test.isTrue(r.get('x') === x);
});
// This test targets IE 9 and 10, which allow properties
// to be attached to TextNodes but may lose them over time.
// Specifically, the JavaScript view of a TextNode seems to
// be only weakly retained by the TextNode itself, so if you
// hang an object graph off a TextNode, you need some other
// pointer to the TextNode or an object in the graph to
// retain it.
Tinytest.addAsync("ui - DomRange - IE TextNode GC", function (test, onComplete) {
var r = new DomRange;
var B = document.createElement('B');
B.id = 'ie_textnode_gc_test';
document.body.appendChild(B);
DomRange.insert(r, B);
r = null;
B = null;
// trigger GC...
if (typeof CollectGarbage === 'function')
CollectGarbage();
// come back later...
window.setTimeout(function () {
var B = document.getElementById("ie_textnode_gc_test");
test.isTrue(B.firstChild.$ui);
test.isTrue(B.lastChild.$ui);
window.BBB = B;
document.body.removeChild(B);
onComplete();
}, 500);
});
// TO TEST STILL:
// - external remove element
// - double-add, double-remove
@@ -818,4 +849,6 @@ Tinytest.add("ui - DomRange - get", function (test) {
// - can't add multiple members with id, but can add array of 1.
// can add 0 with no id.
// - add a node or range with the same id as an old member
// works if that member is gone.
// works if that member is gone.
// - events get wired if declared before adding; get moved
// when wrapping in TBODY

View File

@@ -12,7 +12,7 @@ Package.on_use(function (api) {
api.use('minimongo'); // for idStringify
api.add_files(['backend.js',
'domrange.js']);
'domrange.js'], 'client');
});
Package.on_test(function (api) {