UNPKG

extjs-gpl

Version:

GPL licensed version of Sencha Ext JS

1,056 lines (861 loc) 189 kB
describe("Ext.dom.Element", function() { describe("instantiation", function() { var element, domEl; beforeEach(function() { domEl = document.createElement('div'); document.body.appendChild(domEl); }); afterEach(function() { var el = Ext.cache[domEl.id]; if (el) { el.destroy(); } else { document.body.removeChild(domEl); } }); it("should set dom element id if it hasn't already one", function() { element = new Ext.dom.Element(domEl); expect(domEl.id).toBeDefined(); }); it("should not set dom element id if it has already one", function() { var id = Ext.id(); domEl.id = id; element = new Ext.dom.Element(domEl); expect(domEl.id).toEqual(id); }); it("should set dom property to dom element", function() { element = new Ext.dom.Element(domEl); expect(element.dom).toBe(domEl); }); it("should set id property to dom id", function() { var id = Ext.id(); domEl.id = id; element = new Ext.dom.Element(domEl); expect(element.id).toEqual(id); }); it("should find a dom element if a string corresponding to it's id is passed as first argument", function() { var id = Ext.id(); domEl.id = id; element = new Ext.dom.Element(id); expect(element.dom).toBe(domEl); }); it("should throw error if the Element has an invalid id", function() { function expectError(id) { var dom = document.createElement('div'); dom.id = id; document.body.appendChild(dom); expect(function() { new Ext.Element(dom); }).toThrow('Invalid Element "id": "' + id + '"'); document.body.removeChild(dom); } expectError('.abcdef'); expectError('0a...'); expectError('12345'); expectError('.abc-def'); expectError('<12345/>'); expectError('1<>234.567'); }); it("should not call initConfig", function() { spyOn(Ext.dom.Element.prototype, 'initConfig').andCallThrough(); element = new Ext.dom.Element(domEl); expect(Ext.dom.Element.prototype.initConfig).not.toHaveBeenCalled(); }); }); describe("element creation", function() { describe("create", function() { describe("hidden", function() { it("should set the display class with hidden", function() { var el = Ext.dom.Element.create({ hidden: true }, true); expect(el.className).toBe('x-hidden-display'); }); describe("with classList/className", function() { it("should use both types of classes with classList first", function() { var el = Ext.dom.Element.create({ classList: ['foo', 'bar'], hidden: true }, true); expect(el.className).toBe('foo bar x-hidden-display'); }); it("should use both types of classes with hidden first", function() { var el = Ext.dom.Element.create({ hidden: true, classList: ['foo', 'bar'] }, true); expect(el.className).toBe('x-hidden-display foo bar'); }); }); describe("className with hidden", function() { it("should use both types of classes with className first", function() { var el = Ext.dom.Element.create({ className: 'foo bar', hidden: true }, true); expect(el.className).toBe('foo bar x-hidden-display'); }); it("should use both types of classes with hidden first", function() { var el = Ext.dom.Element.create({ hidden: true, className: 'foo bar', }, true); expect(el.className).toBe('x-hidden-display foo bar'); }); }); }); }); }); function describeMethods(fly) { describe('methods (using ' + (fly ? 'Ext.fly()' : 'new Ext.dom.Element()') + ')', function(){ var domEl, element; function addElement(tag) { domEl = document.createElement(tag || 'div'); document.body.appendChild(domEl); return fly ? Ext.fly(domEl) : Ext.get(domEl); } afterEach(function() { if (element) { // Prevent console warnings spyOn(Ext.Logger, 'warn'); element.destroy(); element = null; } }); describe('clone', function() { var clone, domElInnerHTML = '<span class="bar" style="color:red">Some Text</span>'; afterEach(function() { if (domEl) { Ext.fly(domEl).destroy(); } if (clone) { clone.destroy(); } }); it('should create an exact copy', function() { domEl = document.createElement('div'); domEl.innerHTML = domElInnerHTML; document.body.appendChild(domEl); clone = Ext.fly(domEl).clone(); // deep != true, so it should not have cloned descendants expect(clone.dom.innerHTML).toBe(''); }); describe('deep', function() { // Comparing innerHTML does not work in all browsers: // Expected '<SPAN style="COLOR: red" class=bar _extData="null">Some Text</SPAN>' // to be '<span class="bar" style="color:red">Some Text</span>'. xit('should create an exact copy', function() { domEl = document.createElement('div'); domEl.innerHTML = domElInnerHTML; document.body.appendChild(domEl); clone = Ext.fly(domEl).clone(true); expect(clone.dom.innerHTML).toBe(domElInnerHTML); }); }); }); describe("classes", function() { describe("addCls", function() { beforeEach(function() { element = addElement(); domEl = element.dom; }); it("should not throw an exception when className is null", function() { expect(function() { element.addCls(null); }).not.toThrow(); }); describe("return type", function() { it("should return the element when the class is null", function() { expect(element.addCls(null)).toBe(element); }); it("should return the element when the class is a string", function() { expect(element.addCls('foo')).toBe(element); }); it("should return the element when the class is an array", function() { expect(element.addCls(['foo', 'bar'])).toBe(element); }); }); describe("synchronization", function() { it("should keep the classList/classMap up to date", function() { element.addCls(['foo', 'bar']); var data = element.getData(); expect(data.classList).toEqual(['foo', 'bar']); expect(data.classMap).toEqual({ foo: true, bar: true }); }); }); describe("argument types", function() { describe("with a string", function() { describe("without spaces", function() { it("should add a class to the element", function() { element.addCls('foo'); expect(domEl.className).toBe('foo'); }); it("should add a class when another class already exists", function() { domEl.className = 'foo'; element.addCls('bar'); expect(domEl.className).toBe('foo bar'); }); it("should not duplicate the class if it exists on the element", function() { domEl.className = 'foo'; element.addCls('foo'); expect(domEl.className).toBe('foo'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attach the prefix to the class", function() { element.addCls('foo', 'a'); expect(domEl.className).toBe('a-foo'); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo', 'a'); expect(domEl.className).toBe('foo a-foo'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { element.addCls('foo', null, 'b'); expect(domEl.className).toBe('foo-b'); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo', null, 'b'); expect(domEl.className).toBe('foo foo-b'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { element.addCls('foo', 'a', 'b'); expect(domEl.className).toBe('a-foo-b'); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo', 'a', 'b'); expect(domEl.className).toBe('foo a-foo-b'); }); }); }); }); describe("with spaces", function() { it("should split class names by string and add them separately", function() { element.addCls('foo bar'); expect(domEl.className).toBe('foo bar'); }); it("should split by multiple spaces", function() { element.addCls('foo bar baz'); expect(domEl.className).toBe('foo bar baz'); }); it("should trim leading spaces", function() { expect(element.addCls(' foo bar')); expect(domEl.className).toBe('foo bar'); }); it("should trim trailing spaces", function() { expect(element.addCls('foo bar ')); expect(domEl.className).toBe('foo bar'); }); it("should only add new classes to the element", function() { element.dom.className = 'bar'; element.addCls('foo bar'); expect(domEl.className).toBe('bar foo'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attach the prefix to the class", function() { element.addCls('foo bar', 'a'); expect(domEl.className).toBe('a-foo a-bar'); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo bar', 'a'); expect(domEl.className).toBe('foo a-foo a-bar'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { element.addCls('foo bar', null, 'b'); expect(domEl.className).toBe('foo-b bar-b'); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo bar', null, 'b'); expect(domEl.className).toBe('foo foo-b bar-b'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { element.addCls('foo bar', 'a', 'b'); expect(domEl.className).toBe('a-foo-b a-bar-b'); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls('foo bar', 'a', 'b'); expect(domEl.className).toBe('foo a-foo-b a-bar-b'); }); }); }); }); }); describe("with an array", function() { it("should add all classes to the element", function() { element.addCls(['foo', 'bar']); expect(domEl.className).toBe('foo bar'); }); it("should only add new classes to the element", function() { element.dom.className = 'bar'; element.addCls(['foo', 'bar']); expect(domEl.className).toBe('bar foo'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attach the prefix to the class", function() { element.addCls(['foo', 'bar'], 'a'); expect(domEl.className).toBe('a-foo a-bar'); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls(['foo', 'bar'], 'a'); expect(domEl.className).toBe('foo a-foo a-bar'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { element.addCls(['foo', 'bar'], null, 'b'); expect(domEl.className).toBe('foo-b bar-b'); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls(['foo', 'bar'], null, 'b'); expect(domEl.className).toBe('foo foo-b bar-b'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { element.addCls(['foo', 'bar'], 'a', 'b'); expect(domEl.className).toBe('a-foo-b a-bar-b'); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.addCls(['foo', 'bar'], 'a', 'b'); expect(domEl.className).toBe('foo a-foo-b a-bar-b'); }); }); }); }); }); describe("matching", function() { it("should not match a leading substring as an existing class", function() { domEl.className = 'foobar'; element.addCls('foo'); expect(domEl.className).toBe('foobar foo'); }); it("should not match a trailing substring as an existing class", function() { domEl.className = 'barfoo'; element.addCls('foo'); expect(domEl.className).toBe('barfoo foo'); }); it("should not match a substring as an existing class", function() { domEl.className = 'xfooy'; element.addCls('foo'); expect(domEl.className).toBe('xfooy foo'); }); }); }); describe("removeCls", function() { beforeEach(function() { element = addElement(); domEl = element.dom; }); it("should not throw an exception when className is null", function() { expect(function() { element.removeCls(null); }).not.toThrow(); }); describe("return type", function() { it("should return the element when the class is null", function() { expect(element.removeCls(null)).toBe(element); }); it("should return the element when the class is a string", function() { expect(element.removeCls('foo')).toBe(element); }); it("should return the element when the class is an array", function() { expect(element.removeCls(['foo', 'bar'])).toBe(element); }); }); describe("synchronization", function() { it("should keep the classList/classMap up to date", function() { domEl.className = 'foo bar baz'; element.removeCls(['foo', 'bar']); var data = element.getData(); expect(data.classList).toEqual(['baz']); expect(data.classMap).toEqual({ baz: true }); }); }); describe("argument types", function() { describe("with a string", function() { describe("without spaces", function() { it("should remove a class from the element", function() { domEl.className = 'foo bar'; element.removeCls('foo'); expect(domEl.className).toBe('bar'); }); it("should do nothing when the class is empty", function() { domEl.className = ''; element.removeCls('bar'); expect(domEl.className).toBe(''); }); it("should only remove the specified class", function() { domEl.className = 'foo bar baz'; element.removeCls('bar'); expect(domEl.className).toBe('foo baz'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attacj the prefix to the class", function() { domEl.className = 'a-foo' element.removeCls('foo', 'a'); expect(domEl.className).toBe(''); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'foo'; element.removeCls('foo', 'a'); expect(domEl.className).toBe('foo'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { domEl.className = 'foo-b'; element.removeCls('foo', null, 'b'); expect(domEl.className).toBe(''); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.removeCls('foo', null, 'b'); expect(domEl.className).toBe('foo'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { domEl.className = 'a-foo-b'; element.removeCls('foo', 'a', 'b'); expect(domEl.className).toBe(''); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo'; element.removeCls('foo', 'a', 'b'); expect(domEl.className).toBe('foo'); }); }); }); }); describe("with spaces", function() { it("should split class names by string and remove them separately", function() { domEl.className = 'bar foo'; element.removeCls('foo bar'); expect(domEl.className).toBe(''); }); it("should split by multiple spaces", function() { domEl.className = 'foo bar baz'; element.removeCls('foo bar baz'); expect(domEl.className).toBe(''); }); it("should trim leading spaces", function() { domEl.className = 'foo bar baz'; expect(element.removeCls(' foo bar')); expect(domEl.className).toBe('baz'); }); it("should trim trailing spaces", function() { domEl.className = 'foo bar baz'; expect(element.removeCls('foo bar ')); expect(domEl.className).toBe('baz'); }); it("should only remove matching classes to the element", function() { element.dom.className = 'foo bar baz'; element.removeCls('foo'); expect(domEl.className).toBe('bar baz'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attach the prefix to the class", function() { domEl.className = 'a-foo a-bar'; element.removeCls('foo bar', 'a'); expect(domEl.className).toBe(''); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'a-foo bar'; element.removeCls('foo bar', 'a'); expect(domEl.className).toBe('bar'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { domEl.className = 'foo-b bar-b'; element.removeCls('foo bar', null, 'b'); expect(domEl.className).toBe(''); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo-b bar'; element.removeCls('foo bar', null, 'b'); expect(domEl.className).toBe('bar'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { domEl.className = 'a-foo-b a-bar-b'; element.removeCls('foo bar', 'a', 'b'); expect(domEl.className).toBe(''); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo a-bar-b'; element.removeCls('foo bar', 'a', 'b'); expect(domEl.className).toBe('foo'); }); }); }); }); }); describe("with an array", function() { it("should remove all classes from the element", function() { domEl.className = 'foo bar baz'; element.removeCls(['foo', 'bar']); expect(domEl.className).toBe('baz'); }); it("should only remove specified classes from the element", function() { domEl.className = 'foo bar baz'; element.removeCls(['foo', 'baz']); expect(domEl.className).toBe('bar'); }); describe("prefix & suffix", function() { describe("prefix only", function() { it("should attach the prefix to the class", function() { domEl.className = 'a-foo a-bar'; element.removeCls(['foo', 'bar'], 'a'); expect(domEl.className).toBe(''); }); it("should use the prefix when comparing if the class exists", function() { domEl.className = 'a-foo bar'; element.removeCls(['foo', 'bar'], 'a'); expect(domEl.className).toBe('bar'); }); }); describe("suffix only", function() { it("should attach the suffix to the class", function() { domEl.className = 'foo-b bar-b'; element.removeCls(['foo', 'bar'], null, 'b'); expect(domEl.className).toBe(''); }); it("should use the suffix when comparing if the class exists", function() { domEl.className = 'foo-b bar'; element.removeCls(['foo', 'bar'], null, 'b'); expect(domEl.className).toBe('bar'); }); }); describe("prefix and suffix", function() { it("should attach the prefix & suffix to the class", function() { domEl.className = 'a-foo-b a-bar-b'; element.removeCls(['foo', 'bar'], 'a', 'b'); expect(domEl.className).toBe(''); }); it("should use the prefix & suffix when comparing if the class exists", function() { domEl.className = 'foo a-bar-b'; element.removeCls(['foo', 'bar'], 'a', 'b'); expect(domEl.className).toBe('foo'); }); }); }); }); }); describe("matching", function() { it("should not match a leading substring as an existing class", function() { domEl.className = 'foobar'; element.removeCls('foo'); expect(domEl.className).toBe('foobar'); }); it("should not match a trailing substring as an existing class", function() { domEl.className = 'barfoo'; element.removeCls('foo'); expect(domEl.className).toBe('barfoo'); }); it("should not match a substring as an existing class", function() { domEl.className = 'xfooy'; element.removeCls('foo'); expect(domEl.className).toBe('xfooy'); }); }); }); describe("setCls", function() { beforeEach(function() { element = addElement(); domEl = element.dom; domEl.className = 'some cls'; }); describe("synchronization", function() { it("should keep the classList/classMap up to date", function() { domEl.className = 'foo bar baz'; element.setCls(['some', 'stuff']); var data = element.getData(); expect(data.classList).toEqual(['some', 'stuff']); expect(data.classMap).toEqual({ some: true, stuff: true }); }); }); describe("argument types", function() { describe("with a string", function() { describe("without spaces", function() { it("should set the className", function() { element.setCls('foo'); expect(domEl.className).toBe('foo'); }); }); describe("with spaces", function() { it("should split on spaces", function() { element.setCls('foo bar baz'); expect(domEl.className).toBe('foo bar baz'); }); }); }); describe("with an array", function() { it("should set all classes", function() { element.setCls(['foo', 'bar', 'baz']); expect(domEl.className).toBe('foo bar baz'); }); }); }); }); describe("toggleCls", function() { beforeEach(function() { element = addElement(); domEl = element.dom; domEl.className = 'foo'; }); describe("synchronization", function() { it("should keep the classList/classMap up to date", function() { element.toggleCls('bar'); var data = element.getData(); expect(data.classList).toEqual(['foo', 'bar']); expect(data.classMap).toEqual({ foo: true, bar: true }); }); }); describe("without state flag", function() { it("should add the class if it does not exist", function() { element.toggleCls('bar'); expect(domEl.className).toBe('foo bar'); }); it("should remove the class if it exists", function() { element.toggleCls('foo'); expect(domEl.className).toBe(''); }); }); describe("with state flag", function() { describe("state: true", function() { it("should add a new class", function() { element.toggleCls('bar', true); expect(domEl.className).toBe('foo bar'); }); it("should not remove an existing class", function() { element.toggleCls('foo', true); expect(domEl.className).toBe('foo'); }); }); describe("state: false", function() { it("should remove an existing class", function() { element.toggleCls('foo', false); expect(domEl.className).toBe(''); }); it("should not add a non-existing class", function() { element.toggleCls('bar', false); expect(domEl.className).toBe('foo'); }); }); }); }); describe("hasCls", function() { beforeEach(function() { element = addElement(); domEl = element.dom; }); it("should match if the class name is the first item", function() { domEl.className = 'foo bar baz'; expect(element.hasCls('foo')).toBe(true); }); it("should match if the class name is the last item", function() { domEl.className = 'foo bar baz'; expect(element.hasCls('baz')).toBe(true); }); it("should match if the class name is a middle item", function() { domEl.className = 'foo bar baz qux'; expect(element.hasCls('baz')).toBe(true); }); it("should match if there is only 1 class name", function() { domEl.className = 'foo'; expect(element.hasCls('foo')).toBe(true); }); it("should not match if there is only 1 class that is not the same", function() { domEl.className = 'foo'; expect(element.hasCls('bar')).toBe(false); }); it("should not match if none of the classes match", function() { domEl.className = 'foo bar baz'; expect(element.hasCls('asdf')).toBe(false); }); it("should not match a leading substring", function() { domEl.className = 'foobar'; expect(element.hasCls('foo')).toBe(false); }); it("should not match a trailing substring", function() { domEl.className = 'barfoo'; expect(element.hasCls('foo')).toBe(false); }); it("should not match a substring as an existing class", function() { domEl.className = 'xfooy'; expect(element.hasCls('foo')).toBe(false); }); it("should be able to match when there's a class that matches both the class & a leading subtring", function() { domEl.className = 'foobar foo'; expect(element.hasCls('foo')).toBe(true); }); it("should be able to match when there's a class that matches both the class & a trailing subtring", function() { domEl.className = 'barfoo foo'; expect(element.hasCls('foo')).toBe(true); }); it("should be able to match when there's a class that matches both the class & a subtring", function() { domEl.className = 'xfooy foo'; expect(element.hasCls('foo')).toBe(true); }); }); }); describe("set", function() { beforeEach(function() { element = addElement('div'); }); it("should call Ext.core.DomHelper.applyStyles if object passed as first argument has style property", function() { var style = {width:'100px'}; spyOn(element, "applyStyles"); element.set({style: style}); expect(element.applyStyles).toHaveBeenCalledWith(style); }); it("should set dom element className if object passed as first argument has cls property", function() { var cls = "x-test-class"; element.set({cls: cls}); expect(element.dom.className).toEqual(cls); }); it("should use setAttribute by default", function() { spyOn(element.dom, "setAttribute"); element.set({align: "center"}); expect(element.dom.setAttribute).toHaveBeenCalledWith("align", "center"); }); it("should be able to use expandos", function() { spyOn(element.dom, "setAttribute"); element.set({align: "center"}, false); expect(element.dom.align).toEqual("center"); }); }); describe("is", function() { beforeEach(function() { element = addElement('div'); }); it("Returns true if this element matches the passed simple selector", function() { element.set({cls: "x-test-class"}); expect(element.is("div.x-test-class")).toBe(true); }); }); describe("focus", function() { beforeEach(function() { element = addElement('div'); }); it("should focus dom element", function() { spyOn(element.dom, "focus"); element.focus(); expect(element.dom.focus).toHaveBeenCalled(); }); it("should be able to defer dom element focus", function() { spyOn(element.dom, "focus"); element.focus(1); waitsFor(function(){ return element.dom.focus.calls.length === 1; }, "element.dom.focus was never called"); runs(function() { expect(element.dom.focus).toHaveBeenCalled(); }); }); if (Ext.isIE8) { it("should ignore any exception", function() { element.dom.focus = function() { throw "error"; }; expect(element.focus.bind(element)).not.toThrow("error"); }); } }); describe("blur", function() { beforeEach(function() { element = addElement('div'); }); it("should blur dom element", function() { spyOn(element.dom, "blur"); element.blur(); expect(element.dom.blur).toHaveBeenCalled(); }); it("should ignore any exception", function() { element.dom.blur = function() { throw "error"; }; expect(element.blur.bind(element)).not.toThrow("error"); }); }); describe("wrap/unwrap", function() { describe("wrap", function() { var wrap; beforeEach(function() { element = addElement('div'); }); afterEach(function() { wrap = Ext.destroy(wrap); }); it("should wrap the element", function() { var parent = element.dom.parentNode; wrap = element.wrap(); expect(element.dom.parentNode.parentNode).toBe(parent); }); it("should wrap the element in place", function() { var el1 = Ext.getBody().createChild(), el2 = Ext.getBody().createChild(); el1.insertBefore(element); wrap = element.wrap(); expect(wrap.prev()).toBe(el1); expect(wrap.next()).toBe(el2); Ext.destroy(el1, el2); }); describe("config", function() { it("should apply the config to the wrapping element", function() { var newId = Ext.id(); wrap = element.wrap({ cls: 'foo', id: newId }); expect(wrap.dom.className).toBe('foo'); expect(wrap.dom.id).toBe(newId); }); }); describe("returnDom", function() { it("should return an Ext.dom.Element by default", function() { wrap = element.wrap(); expect(wrap.isElement).toBe(true); }); it("should return an Ext.dom.Element when passing false", function() { wrap = element.wrap({}, false); expect(wrap.isElement).toBe(true); }); it("should return an DOM element when passing true", function() { wrap = element.wrap({}, true); expect(wrap.isElement).not.toBe(true);