| Index: tools/dom/templates/html/impl/impl_HTMLDocument.darttemplate
|
| diff --git a/tools/dom/templates/html/impl/impl_HTMLDocument.darttemplate b/tools/dom/templates/html/impl/impl_HTMLDocument.darttemplate
|
| index 3d9e6afb5cedefa436b006eb0483131cdaea4545..bf8f0ffc2c5ef6293eeff7f52d9889876db75987 100644
|
| --- a/tools/dom/templates/html/impl/impl_HTMLDocument.darttemplate
|
| +++ b/tools/dom/templates/html/impl/impl_HTMLDocument.darttemplate
|
| @@ -17,7 +17,7 @@ $else
|
| BodyElement get body => _body;
|
|
|
| @DomName('Document.body')
|
| - void set body(BodyElement value) {
|
| + set body(BodyElement value) {
|
| _body = value;
|
| }
|
| $endif
|
| @@ -90,7 +90,7 @@ $endif
|
|
|
| @DomName('Document.selectedStylesheetSet')
|
| String get selectedStylesheetSet => _selectedStylesheetSet;
|
| - void set selectedStylesheetSet(String value) {
|
| + set selectedStylesheetSet(String value) {
|
| _selectedStylesheetSet = value;
|
| }
|
|
|
| @@ -101,7 +101,7 @@ $endif
|
| String get title => _title;
|
|
|
| @DomName('Document.title')
|
| - void set title(String value) {
|
| + set title(String value) {
|
| _title = value;
|
| }
|
|
|
| @@ -187,6 +187,41 @@ $if DART2JS
|
| $else
|
| String get visibilityState => _webkitVisibilityState;
|
| $endif
|
| +$if DARTIUM
|
| +
|
| + /**
|
| + * Internal routine to find the DOM JS class name being extended for custom
|
| + * elements.
|
| + */
|
| + String _getJSClassName(ClassMirror classMirror) {
|
| + var jsClassName = null;
|
| + var isElement = false;
|
| +
|
| + while (classMirror.superclass != null) {
|
| + var fullName = classMirror.superclass.qualifiedName;
|
| + isElement = isElement || (fullName == #dart.dom.html.Element);
|
| +
|
| + var domLibrary = MirrorSystem.getName(fullName).startsWith('dart.dom.');
|
| + if (jsClassName == null && domLibrary) {
|
| + // Lookup JS class name (if not found).
|
| + var metadatas = classMirror.metadata;
|
| + for (var metadata in metadatas) {
|
| + var metaDataMirror = metadata.reflectee;
|
| + var metaType = reflectClass(metaDataMirror.runtimeType);
|
| + if (MirrorSystem.getName(metaType.simpleName) == 'DomName' &&
|
| + metaDataMirror.name.startsWith('HTML')) {
|
| + jsClassName = metadata.reflectee.name;
|
| + }
|
| + }
|
| + }
|
| +
|
| + classMirror = classMirror.superclass;
|
| + }
|
| +
|
| + // If we're an element then everything is okay.
|
| + return isElement ? jsClassName : null;
|
| + }
|
| +$endif
|
|
|
| @Experimental()
|
| /**
|
| @@ -236,7 +271,73 @@ $if DART2JS
|
| _registerCustomElement(JS('', 'window'), this, tag, customElementClass,
|
| extendsTag);
|
| $else
|
| - _Utils.register(this, tag, customElementClass, extendsTag);
|
| + // TODO(terry): Need to handle the extendsTag.
|
| +
|
| + // Figure out which DOM class is being extended from the user's Dart class.
|
| + var classMirror = reflectClass(customElementClass);
|
| + var jsClassName = _getJSClassName(classMirror);
|
| + if (jsClassName == null) {
|
| + // Only components derived from HTML* can be extended.
|
| + throw new DomException.jsInterop("HierarchyRequestError: Only HTML elements can be customized.");
|
| + }
|
| +
|
| + // Start the hookup the JS way create an <x-foo> element that extends the
|
| + // <x-base> custom element. Inherit its prototype and signal what tag is
|
| + // inherited:
|
| + //
|
| + // var myProto = Object.create(HTMLElement.prototype);
|
| + // var myElement = document.registerElement('x-foo', {prototype: myProto});
|
| + var baseElement = js.context[jsClassName];
|
| + if (baseElement == null) {
|
| + // Couldn't find the HTML element so use a generic one.
|
| + baseElement = js.context['HTMLElement'];
|
| + }
|
| + var elemProto = js.context['Object'].callMethod("create", [baseElement['prototype']]);
|
| +
|
| + // TODO(terry): Hack to stop recursion re-creating custom element when the
|
| + // created() constructor of the custom element does e.g.,
|
| + //
|
| + // MyElement.created() : super.created() {
|
| + // this.innerHtml = "<b>I'm an x-foo-with-markup!</b>";
|
| + // }
|
| + //
|
| + // sanitizing causes custom element to created recursively
|
| + // until stack overflow.
|
| + //
|
| + // See https://github.com/dart-lang/sdk/issues/23666
|
| + int creating = 0;
|
| + elemProto['createdCallback'] = new js.JsFunction.withThis(($this) {
|
| + if (_getJSClassName(reflectClass(customElementClass).superclass) != null && creating < 2) {
|
| + creating++;
|
| +
|
| + var dartClass = _blink.Blink_Utils.constructElement(customElementClass, $this);
|
| +
|
| + // Need to remember the Dart class that was created for this custom so
|
| + // return it and setup the blink_jsObject to the $this that we'll be working
|
| + // with as we talk to blink.
|
| + $this['dart_class'] = dartClass;
|
| +
|
| + creating--;
|
| + }
|
| + });
|
| + elemProto['attributeChangedCallback'] = new js.JsFunction.withThis(($this, attrName, oldVal, newVal) {
|
| + if ($this["dart_class"] != null && $this['dart_class'].attributeChanged != null) {
|
| + $this['dart_class'].attributeChanged(attrName, oldVal, newVal);
|
| + }
|
| + });
|
| + elemProto['attachedCallback'] = new js.JsFunction.withThis(($this) {
|
| + if ($this["dart_class"] != null && $this['dart_class'].attached != null) {
|
| + $this['dart_class'].attached();
|
| + }
|
| + });
|
| + elemProto['detachedCallback'] = new js.JsFunction.withThis(($this) {
|
| + if ($this["dart_class"] != null && $this['dart_class'].detached != null) {
|
| + $this['dart_class'].detached();
|
| + }
|
| + });
|
| + // document.registerElement('x-foo', {prototype: elemProto, extends: extendsTag});
|
| + var jsMap = new js.JsObject.jsify({'prototype': elemProto, 'extends': extendsTag});
|
| + js.context['document'].callMethod('registerElement', [tag, jsMap]);
|
| $endif
|
| }
|
|
|
|
|