This is an archived snapshot of W3C's public bugzilla bug tracker, decommissioned in April 2019. Please see the home page for more details.
Specification: http://www.whatwg.org/specs/web-apps/current-work/multipage/webappapis.html Multipage: http://www.whatwg.org/C#the-errorevent-interface Complete: http://www.whatwg.org/c#the-errorevent-interface Referrer: Comment: Should define default values for ErrorEventInit in the IDL, not in the prose Posted from: 98.110.194.132 by bzbarsky@mit.edu User agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:30.0) Gecko/20100101 Firefox/30.0
The dict has no default values. Do you mean the event object?
The event object is created from an ErrorEventInit dictionary, right? Or can it be created via createEvent? If it can't be created via createEvent, then it should be enough to define default values for the dictionary and then lean on http://dom.spec.whatwg.org/#constructing-events for setting the values in the event. If it can be created via createEvent, then we should perhaps still define default values for the dictionary, though, since as far as I can tell http://dom.spec.whatwg.org/#constructing-events assumes all the values are present in the dictionary. But maybe that's just a wording oversight?
Note that as far as I can tell http://dom.spec.whatwg.org/#dom-document-createevent does not have a way to create an ErrorEvent.
bz, I think you are right that the way that section is written assumes default values are defined in IDL. As long as default values can be defined that way that does not seem like a problem.
ErrorEvents can be created by the user agent. The prose that does that doesn't reference the constructor or dictionary (and it'd be kinda weird to do so, IMHO). As far as I can tell, all event interfaces are defined this way currently (at least in HTML, and I did it following directions from Anne, so presumably other specs too). So if there's something wrong in the way the dictionary is used, it would be simplest to fix this there.
> ErrorEvents can be created by the user agent. Fwiw, the way Gecko does that is to create an ErrorEventInit and then call the WebIDL constructor with it. But in any case, as the DOM spec is currently written all event init dictionaries need to have default values for all members. We need to either change the DOM spec somehow or just add default values to those dictionaries.
Unless there is a case where adding the default value to the dictionary does not work (because it depends on some other value, say) I would prefer we go with that as it is the easiest for specification writers and they will undoubtedly get it wrong otherwise.
I thought we specifically didn't do that because of the *Init() methods that some event interfaces have. That is, we specifically defined each event interface attribute as being initialised in prose at creation time, then said that it returns the last value it was initialised to, and then made the dict-using constructor also initialise the values to the given values if present. Did this change at some point?
(And how would you know what dict to use when the object was created without using the dict-using constructor?)
You know what dictionary to use due to argument defaulting. We largely switched away due to the problem I mentioned. Yes, events with init* methods have to do both, but new event classes can be defined much simpler with just dictionaries.
The simplest example from D3E: [Constructor(DOMString typeArg, optional CustomEventInit customEventInitDict] interface CustomEvent : Event { readonly attribute any detail; }; dictionary CustomEventInit : EventInit { any detail = null; }; detail of type any, readonly Specifies some detail information about the Event. The un-initialized value of this attribute MUST be null. partial interface CustomEvent { // Originally introduced (and deprecated) in DOM Level 3 void initCustomEvent (DOMString typeArg, boolean bubblesArg, boolean cancelableArg, any detailArg); }; un-initialized value << value when use Document.createEvent(), before initialize. When initialize with old way we must pass all argument to init*Event(). When invoke constructor new CustomEvent() we can pass or skip dictionary (or some members from dictionary) << much more convenient (init is automatically). This style of description seems appropriate for both, constructor and old init method (if necessary). But if this interface is defined in HTML5 and should support init*Event, this method should be defined too.
So, I'm trying to figure out how this is supposed to work, but I see nothing in the spec that makes this work. Suppose I call createEvent('MessageEvent'). (This works in Chrome and Firefox, and there's evidence to suggest that it's needed for compat, see bug 25491 comment 7.) This "returns a new event". The constructor is not invoked, the dictionary is not referenced. But now I have a MessageEvent object, and its attributes have to have values. Right now they have values because the attributes are initialised in prose. How would it work if I removed that prose and put it in the dictionary? Wouldn't it all be undefined at that point? Similarly, there are parts of the HTML spec that just create new event objects. Again, no mention of constructors or dictionaries. How do the events end up with their initial values in this scenario?
> But now I have a MessageEvent object This would presumably be handled by the spec for createEvent (which also presumably needs to add messageevent to its table of special-cases). In particular, I think the right way to spec createEvent is that it calls the corresponding constructor from the table it has, passing "" as the type and not passing an init dictionary, which causes the default init dictionary to be used.
(In reply to Boris Zbarsky from comment #2) > The event object is created from an ErrorEventInit dictionary, right? Or > can it be created via createEvent? > > If it can't be created via createEvent, then it should be enough to define > default values for the dictionary and then lean on > http://dom.spec.whatwg.org/#constructing-events for setting the values in > the event. > > If it can be created via createEvent, then we should perhaps still define > default values for the dictionary, though, since as far as I can tell > http://dom.spec.whatwg.org/#constructing-events assumes all the values are > present in the dictionary. But maybe that's just a wording oversight? What if we use constructor but not pass dictionary? In the theory prose should cover this case. In practice we don't know how each browser work (of course you know:). Probably too detailed of creating events in HTML spec is unnecessary. It would require a cover constructor or createEvent()/init*Event() cases (in general we have this in DOM, two separate algorithms). Other specifications are not trying to duplicate these schemes. I don't see in HTML spec where you use createEvent(), define init*Event() method, etc... But adding in all IDL dictionary default value probably will not be a mistake (the same what we have in prose)? I see that in some case we have it: dictionary HitRegionOptions { Path2D? path = null; CanvasFillRule fillRule = "nonzero"; DOMString id = ""; DOMString? parentID = null; DOMString cursor = "inherit"; // for control-backed regions: Element? control = null; // for unbacked regions: DOMString? label = null; DOMString? role = null; }; dictionary EventSourceInit { boolean withCredentials = false; }; Then we can take a quick look at the IDL definitions of what we get as default, without searchable text. In DOM/D3E all events dictionary have default value (and still expose initialize value in prose). One exception is MutationObserverInit: http://dom.spec.whatwg.org/#mutationobserverinit Anne explain why (https://www.w3.org/Bugs/Public/show_bug.cgi?id=25099#c7) << algo set some value depending on other values.
> What if we use constructor but not pass dictionary? WebIDL says: If the type of an argument is a dictionary type or a union type that has a dictionary type as one of its flattened member types, and this argument is either the final argument or is followed only by optional arguments, then the argument MUST be specified as optional. Such arguments are always considered to have a default value of an empty dictionary, unless otherwise specified. so not passing the dictionary is by definition the same as passing {} for the dictionary argument: you get default values for all the dictionary members that have default values, and all the other ones will be not present.
(In reply to Boris Zbarsky from comment #13) > I think the right way to spec createEvent is that it calls the > corresponding constructor from the table it has, passing "" as the type and > not passing an init dictionary, which causes the default init dictionary to > be used. It seems at the moment the difference is that an event created through createEvent() cannot be passed to dispatchEvent() as its initialized flag is not set. And it seems we have interoperability on this. It makes little sense, so we could try to remove it.
(In reply to Boris Zbarsky from comment #15) > so not passing the dictionary is by definition the same as passing {} for > the dictionary argument: you get default values for all the dictionary > members that have default values, and all the other ones will be not present. I didn't realize abotu this, thx for the explanation. (In reply to Anne from comment #16) > It seems at the moment the difference is that an event created through > createEvent() cannot be passed to dispatchEvent() as its initialized flag is > not set. And it seems we have interoperability on this. > > It makes little sense, so we could try to remove it. And in practice this flag can be set for createEvent() variant only by init*Event(), even the shortest version, like initEvent(): var ev = document.createEvent('MessageEvent'); ev.initEvent("hello", true, true); // we can dispatch
Hmm. There's a semi-good reason to not allow dispatch of events created with createEvent that aren't inited: they have no useful type. It still feels like createEvent and the event ctors could share some spec language, with createEvent instantiating the appropriate dictionary...
1) Note that new Event("") does work. 2) We could indeed make it work today, by unsetting the initialized flag from the createEvent() algorithm. I guess that would at least be an improvement to the status quo and would allow for removal of some default attribute values.
https://github.com/whatwg/dom/commit/c787c8f9c24e331182039f72802ec9465d2f0070 We can separately argue whether we should remove the "initialized flag" altogether.
This doesn't help all the cases in prose where I say "create a FooEvent event".
Fast solution: Make term like we have for firing/dispatch etc. and refer to DOM. http://www.whatwg.org/specs/web-apps/current-work/#scripting-0 http://www.whatwg.org/specs/web-apps/current-work/#event-firing
> This doesn't help all the cases in prose where I say "create a FooEvent event". How do all those places specify which global the event is created in right now?
They don't, but that's a broader problem that applies to things outside of event objects too. I don't see how anything in this bug would help there, either.
*** Bug 26356 has been marked as a duplicate of this bug. ***
(In reply to Ian 'Hixie' Hickson from comment #21) > This doesn't help all the cases in prose where I say "create a FooEvent > event". Where do you create an actual object rather than firing one? You could just invoke the initial value of the property that returns the constructor there.
Not sure what "You could just invoke the initial value of the property that returns the constructor there" means. Sometimes I create an event in one step, manipulate it in various ways, then fire it later. Or create a bunch of events in a list, then fire them all off at once. I don't really understand what was wrong with the old way of doing things.
Basically we're removing prose in favor of IDL.
I don't see why that's an improvement, especially given the implications here.
Any pointers for comment 21? (So far this has been better for everyone else defining events.)
e.g. http://www.whatwg.org/specs/web-apps/current-work/#fire-a-focus-event http://www.whatwg.org/specs/web-apps/current-work/#the-dragevent-interface:dragevent-5 http://www.whatwg.org/specs/web-apps/current-work/#prompt-to-unload-a-document http://www.whatwg.org/specs/web-apps/current-work/#runtime-script-errors:errorevent ...etc.
So what's the story here? Can we go back to doing this in prose?
It's not clear why those examples cannot use the constructor or language similar to http://xhr.spec.whatwg.org/#concept-event-fire-progress It seems by using the constructor, more details will be defined, such as what global the prototype comes from.
We have to define what global to use when creating objects in prose regardless of this, since not everything in the platform is going to have constructors.
I suggest we file a new bug for the issue in comment 33 and comment 34. I don't really see the benefit of not using prose here.
> I don't really see the benefit of not using prose here. For example, if event implementations are entirely defined in IDL, then they can be implemented automatically based on the IDL. Gecko does this for events which have no magic prose.
Well nothing stops you from implementing the prose in custom IDL, right? I don't really understand what the alternative to prose is here, given the way that events are regularly created without invoking a constructor.
https://github.com/whatwg/html/issues/918