OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. |
| 4 |
| 5 class _XMLClassSet extends _CssClassSet { |
| 6 _XMLClassSet(element) : super(element); |
| 7 |
| 8 String _className() { |
| 9 final classStr = _element.getAttribute('class'); |
| 10 return classStr == null ? '' : classStr; |
| 11 } |
| 12 |
| 13 void _write(Set s) => _element.setAttribute('class', _formatSet(s)); |
| 14 } |
| 15 |
| 16 class XMLElementWrappingImplementation extends ElementWrappingImplementation |
| 17 implements XMLElement { |
| 18 XMLElementWrappingImplementation._wrap(ptr) : super._wrap(ptr); |
| 19 |
| 20 factory XMLElementWrappingImplementation.tag(String tag) => |
| 21 LevelDom.wrapElement(dom.document.createElementNS(null, tag)); |
| 22 |
| 23 factory XMLElementWrappingImplementation.xml(String xml) { |
| 24 XMLElement parentTag = new XMLElement.tag('xml'); |
| 25 parentTag.innerHTML = xml; |
| 26 if (parentTag.nodes.length == 1) return parentTag.nodes.removeLast(); |
| 27 |
| 28 throw new IllegalArgumentException('XML had ${parentTag.nodes.length} ' + |
| 29 'top-level nodes but 1 expected'); |
| 30 } |
| 31 |
| 32 Set<String> get classes() { |
| 33 if (_cssClassSet === null) { |
| 34 _cssClassSet = new _XMLClassSet(_ptr); |
| 35 } |
| 36 return _cssClassSet; |
| 37 } |
| 38 |
| 39 ElementList get elements() { |
| 40 if (_elements == null) { |
| 41 _elements = new FilteredElementList(this); |
| 42 } |
| 43 return _elements; |
| 44 } |
| 45 |
| 46 // TODO: The type of value should be Collection<Element>. See http://b/5392897 |
| 47 void set elements(value) { |
| 48 final elements = this.elements; |
| 49 elements.clear(); |
| 50 elements.addAll(value); |
| 51 } |
| 52 |
| 53 String get outerHTML() { |
| 54 final container = new Element.tag("div"); |
| 55 container.elements.add(this.clone(true)); |
| 56 return container.innerHTML; |
| 57 } |
| 58 |
| 59 String get innerHTML() { |
| 60 final container = new Element.tag("div"); |
| 61 container.nodes.addAll(this.clone(true).nodes); |
| 62 return container.innerHTML; |
| 63 } |
| 64 |
| 65 void set innerHTML(String xml) { |
| 66 final xmlDoc = new XMLDocument.xml('<xml>$xml</xml>'); |
| 67 this.nodes = xmlDoc.nodes; |
| 68 } |
| 69 |
| 70 Node _insertAdjacentNode(String where, Node node) { |
| 71 switch (where.toLowerCase()) { |
| 72 case "beforebegin": |
| 73 if (parent == null) return null; |
| 74 parent.insertBefore(node, this); |
| 75 return node; |
| 76 case "afterend": |
| 77 if (parent == null) return null; |
| 78 if (nextNode == null) { |
| 79 parent.nodes.add(node); |
| 80 } else { |
| 81 parent.insertBefore(node, nextNode); |
| 82 } |
| 83 return node; |
| 84 case "afterbegin": |
| 85 this.insertBefore(node, nodes.first); |
| 86 return node; |
| 87 case "beforeend": |
| 88 this.nodes.add(node); |
| 89 return node; |
| 90 default: |
| 91 throw new IllegalArgumentException("Invalid position ${where}"); |
| 92 } |
| 93 } |
| 94 |
| 95 XMLElement insertAdjacentElement([String where = null, |
| 96 XMLElement element = null]) => this._insertAdjacentNode(where, element); |
| 97 |
| 98 void insertAdjacentText([String where = null, String text = null]) { |
| 99 this._insertAdjacentNode(where, new Text(text)); |
| 100 } |
| 101 |
| 102 void insertAdjacentHTML( |
| 103 [String position_OR_where = null, String text = null]) { |
| 104 this._insertAdjacentNode( |
| 105 position_OR_where, new DocumentFragment.xml(text)); |
| 106 } |
| 107 |
| 108 // For HTML elemens, the default value of "contentEditable" is "inherit", so |
| 109 // we'll use that here as well even though it doesn't really make sense. |
| 110 String get contentEditable() => _attr('contentEditable', 'inherit'); |
| 111 |
| 112 void set contentEditable(String value) { |
| 113 attributes['contentEditable'] = value; |
| 114 } |
| 115 |
| 116 // Parentless HTML elements return false regardless of the value of their |
| 117 // contentEditable attribute, so XML elements do the same since they're never |
| 118 // actually editable. |
| 119 bool get isContentEditable() => false; |
| 120 |
| 121 bool get draggable() => attributes['draggable'] == 'true'; |
| 122 |
| 123 void set draggable(bool value) { attributes['draggable'] = value.toString(); } |
| 124 |
| 125 bool get spellcheck() => attributes['spellcheck'] == 'true'; |
| 126 |
| 127 void set spellcheck(bool value) { |
| 128 attributes['spellcheck'] = value.toString(); |
| 129 } |
| 130 |
| 131 bool get hidden() => attributes.containsKey('hidden'); |
| 132 |
| 133 void set hidden(bool value) { |
| 134 if (value) { |
| 135 attributes['hidden'] = ''; |
| 136 } else { |
| 137 attributes.remove('hidden'); |
| 138 } |
| 139 } |
| 140 |
| 141 int get tabIndex() { |
| 142 try { |
| 143 return Math.parseInt(_attr('tabIndex')); |
| 144 } catch (BadNumberFormatException e) { |
| 145 return 0; |
| 146 } |
| 147 } |
| 148 |
| 149 void set tabIndex(int value) { attributes['tabIndex'] = value.toString(); } |
| 150 |
| 151 String get id() => _attr('id'); |
| 152 |
| 153 void set id(String value) { attributes['id'] = value; } |
| 154 |
| 155 String get title() => _attr('title'); |
| 156 |
| 157 void set title(String value) { attributes['title'] = value; } |
| 158 |
| 159 String get webkitdropzone() => _attr('webkitdropzone'); |
| 160 |
| 161 void set webkitdropzone(String value) { |
| 162 attributes['webkitdropzone'] = value; |
| 163 } |
| 164 |
| 165 String get lang() => _attr('lang'); |
| 166 |
| 167 void set lang(String value) { attributes['lang'] = value; } |
| 168 |
| 169 String get dir() => _attr('dir'); |
| 170 |
| 171 void set dir(String value) { attributes['dir'] = value; } |
| 172 |
| 173 String _attr(String name, [String def = '']) => |
| 174 attributes.containsKey(name) ? attributes[name] : def; |
| 175 } |
OLD | NEW |