- From: François REMY <francois.remy.dev@outlook.com>
- Date: Wed, 31 Jul 2013 18:25:06 +0200
- To: Mihnea-Vlad Ovidenie <mihnea@adobe.com>, Boris Zbarsky <bzbarsky@mit.edu>, "www-style@w3.org" <www-style@w3.org>
>>Just another reason why not having getNamedFlow(id) is problematic: >> >>- you may want to ask the NamedFlow for a flow that doesn't exist yet >>because the style hasn't been computed (or, depending on the browser, it >>may or may not have been computed because of different codepaths). > > I am not sure about this use-case. Why would you want to do such thing? > Can you please elaborate? You may want to add listeners to a named flow before the page actually finished loading, and there's no good way to know when all the stylesheets have been downloaded and applied (you don't want to use the "load" event because it waits on images). Also, you may just want to listen to events on a flow that do not exist yet but you suspect some script or media query could make alive depending on conditions you don't want to know about (you just want to know when you should start acting on the flow). > Before moving further with the discussion, would you like to detail the > behavior of getNamedFlow(flow_identifier) method? Is this method supposed > to stay on the Document interface? What should return this method in the > case you are calling with a flow_identified that does not exist at the > call time? The function {document.getNamedFlow(...)} would work the same way as {document.getNamedFlows().namedItem(...)} would, except that you don't need to return the list of all the active flows so if the page is not ready yet or the flow do not exist yet, you can return a dummy flow whose state is NULL according to the spec, at least until the user ask for a property on the flow (at that point, you've to update the flow state anyway), but you avoid these steps altoegether if the user intent was just to add an event listener, which is the most probable use case anyway. By the way, even if Webkit maintains a live list of named flows at all time (ie: recompute the styles on the page after every .className update), that doesn't mean every implementation will have to. I can perfectly imagine some browsers do not recompute the styles on the page before they actually need it. For those browsers, calling getNamedFlows().namedItem('content") would force them to recompute the styles on the whole page to get an accurate static list of active flows, whereas they can skip that stuff if I just call getNamedFlow('content") by returning me the current live NamedFlow object for the flow if it exists. Also, did you know I can easily create an unfixable memory leak using the current NamedFlow API? If I add a listener to a flow that *exists* at time "T", and that the listener holds a reference to some objects on my page because of a closure, and then that the flow stops to be active, I've no way of unregistering the event to the flow because it won't show up in getNamedFlows anymore... while it still exists in memory! You can prove that by using an expando property on it with the following code (assume #region is the only selector affecting the 'abc' flow to an element): // put stuff on a flow f=document.webkitGetNamedFlows()["abc"] f.a="a" f=null // the flow stops to be active region.id='boo' // impossible to get a reference to the flow anymore f=document.webkitGetNamedFlows()["abc"] // undefined // to prove memory leaked, I can reinstanciate the flow boo.id='region' f=document.webkitGetNamedFlows()["abc"] f.a // "a" A solution to this issue would be to return in getNamedFlows() a sequence of all the flows that either: - are active right now - have an expando property on them, or have been mutated in JS in any observable way (including event listeners) -- those NamedFlow objects cannot be GCed without affecting the JS world, which is why they aren't GCed right now. That way, a library can properly clean up his actions by unregistering to all flows, even those that potentially went inactive between the registration and unregistration time. Obviously the best option would be for this library to keep a reference to all flows it registers to, but it may be difficult or unwanted for some reason. It may already be easier to store a list of the flow names that have been listened to, in which case my proposed getNamedFlow function may suffice to clear this issue.
Received on Wednesday, 31 July 2013 16:25:33 UTC