Everyone hates the differences between the different major browsers out there. Not to mention the different versions of those browsers. Supporting all of them is a pain in the ass. And here is just one more reason:
Action: Take a Flash Object element on a page, and then move it someplace else (append the element to a different parent node)
Code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
| var newCont = document.createElement( "div" ); var swfOb = document.getElementById( "swf-object-element" ); //already exists on the page print(swfOb.lastChild); //<param name="flashvars" value="name=value" /> swfOb.lastChild.value = "name=value2" ; document.body.appendChild(newCont); newCont.appendChild(swfOb); swfOb = document.getElementById( "swf-object-element" ); var swfExternalFunction = e.setCorner; e.setCorner( "tr" ); //(attempts to) move the corner to the top right (starts in the bottom right) //In NO browser, does that call actually WORK //...wait 100ms swfExternalFunction == null //false IE,FF; true Chrome swfExternalFunction == e.setCorner //false!! all e.setCorner( "tr" ) //Error! IE; works in FF,Chrome swfOb.lastChild //<param name="flashvars" value="name=value" /> FF!! ; <param name="flashvars" value="name=value2" /> Chrome, IE (sometimes) |
Consequences:
SWF is in the bottom right. The call to "setCorner" does nothing. All browsers.
Because::
IE: Will not let you call a Flash External Interface function on a moved element. BUT!!!! the function will still exist on the element. Buggars. And I couldn't get a straight answer from IE when modifying the Object Element before/after the location change. IE seems to have some sort of race condition going on. Sometimes it does, sometimes it doesn't, and sometimes the buggar doesn't even allow ANY External Interface any more. More hate for IE. Tested in IE 10, _but_ in IE8 standards mode. I had similar problems in actual IE8 - I could not get consistant results. I need to create better tests for IE, but that's time I don't have.
FF: FF re-inits the SWF, just like Chrome. Any changes to the "old" element will NOT be reflected in the new one. Whats WORSE is that the reference to the element's External Interface function STILL EXIST (on the Object) while the "new" object is being initialized, BUT!!! those functions STILL REFERENCE THE "OLD" OBJECT!! Talk about craziness...
But wait, I'm not done. Firefox completely IGNORES changes to the object element in the mean time. So you can't, say, change the FlashVars and have them be updated in the "new" Object. Booooooo FF
Chrome: The best of the three. I'd still prefer that the SWF not be re-initialized, but oh well. At LEAST Chrome doesn't lie to you and expose functions that are out of date or don't exist. As well, it recognizes changes to the Object Element and on the "new" Object, those changes are present.
RESULT:
The only sure fire way to move a SWF element is to just set a timeout for after the move, and re-init it then, knowing that all your previous changes are gone. Which means you have to keep state externally, or get the current state from the Object before you move it. There's NO WAY to check to verify that it's "ok yet" to make changes after you've moved it, so you just have to set a long timeout and pray that it's long enough (iff you don't want to make browser specific code, that is).