Ticket #321 (closed Bug: fixed)

Opened 8 years ago

Last modified 5 years ago

When FCKeditor loads in a "display:none" container it is not editable (FireFox/Gecko)

Reported by: marcuslum Owned by: alfonsoml
Priority: Normal Milestone: FCKeditor 2.5 Beta
Component: General Version: FCKeditor 2.4.1
Keywords: Cc:

Description

I have a FCKeditor control that is hidden on normal page loads by placing it in a control that is styled with "display:none". The editor is dynamically displayed with script that sets the display back to either "block" or "", which works in Internet Explorer but doesn't in Firefox/Gecko. The focus won't go into the editing box unless you click "Source" and switch it into and out of source mode.

It seems as though the problem is that Gecko unsets the editor's <IFRAME> designMode when it is hidden, but doesn't re-set it when the <IFRAME> is unhidden.

I found a posting here that documents the same problem, which includes an example: http://fckeditor.biz/viewtopic.php?p=2151&sid=7376ab46d4ba8c73ac2d31a0d0f417b7

I poked around a bit more and found this in the FCKeditor Wiki: http://wiki.fckeditor.net/Troubleshooting#head-b3157703eeeef9d287b4c922f9b43eab9d551417

It describes various workarounds, ending in June 2006 with a mention that the problem was fixed for Firefox v2.x with FCKeditor v2.3 (I did not confirm that), but now the problem appears to have resurfaced.

Attachments

mutation.html (7.6 KB) - added by alfonsoml 7 years ago.
This page could evolve to provide bigger understanding of the mutation events. You'll need firefox with Firebug to see the events in the console (or wrap the calls and call FCKDebug for non-firebug tests)

Change History

comment:1 Changed 7 years ago by alfonsoml

  • Keywords Hidden Focus Firefox Editable Source removed
  • Status changed from new to closed
  • Resolution set to invalid
  • Milestone FCKeditor 2.4.2 deleted

In the wiki you can find the proper solution just in the first paragraph:

This is a Gecko specific bug. A sample workaround can be found in the "_testcases" folder. Take a look at the "004.html" file.You just need to "re-enable" the editing when you make the DIV visible.

You just need this code:

function Show()
{
	document.getElementById('eEditor').style.display	= '' ;
	document.getElementById('eNoEditor').style.display	= 'none' ;

	// This is a hack for Gecko... it stops editing when the editor is hidden.
	if ( !document.all )
	{
		var oEditor = FCKeditorAPI.GetInstance( 'FCKeditor1' ) ;

		if (  oEditor.EditMode == FCK_EDITMODE_WYSIWYG )
			oEditor.MakeEditable() ;
	}
}

PS: the forum that you have linked isn't an official forum of FCKeditor.

comment:3 Changed 7 years ago by fredck

#502 has been marked as DUP.

comment:4 Changed 7 years ago by alfonsoml

#776 has been marked as dup

comment:5 Changed 7 years ago by alfonsoml

I've commited in [445] some changes that should make the editor auto-enable itself. At least in my tests using the testcase004 (after disabling there the manual workaround) it does work nicely.

comment:6 Changed 7 years ago by fredck

  • Milestone set to FCKeditor 2.5

Interesting approach Alfonso. I've made some small changes to it with [449]. Just details.

comment:7 Changed 7 years ago by alfonsoml

  • Status changed from closed to reopened
  • Resolution invalid deleted

The update to Firefox 2.0.0.5 seems to have broken this hack.

I'll try to find out if we can do something about it, or we should remove the comment from what's new (and even think about removing the code, although it might work for older versions).

What's new in 2.0.0.5: http://www.mozilla.org/projects/security/known-vulnerabilities.html#firefox2.0.0.5

comment:8 Changed 7 years ago by alfonsoml

  • Owner set to alfonsoml
  • Status changed from reopened to new

comment:9 Changed 7 years ago by alfonsoml

  • Status changed from new to closed
  • Resolution set to fixed

Fixed again with [588].

I've changed the watched object in the editingArea from this.Document to this.Window.frameElement.

Another option would be to get even higher and watch the document where the editor is placed (and where the change of visibility of divs and similar takes place), but then it wouldn't be possible to know which instance we should try to make editable and it should make a loop with all the instances checking that it isn't in source view and then trying to make editable if it isn't already.

comment:10 Changed 7 years ago by fredck

  • Status changed from closed to reopened
  • Resolution fixed deleted

I think that this.Window.frameElement is the right choice. In this way we are working with elements comprised in the FCKEditingArea class, making it independent from the rest.

I've watched the changed attributes when showing and hiding the editor, and I've noted the the "offsetParent" attribute always change on those cases, being set to null when the iframe is hidden.

I was wondering if the logic you have implemented may take advantage of this information, for performance the correct resources usage, possibly avoiding using the timer approach.

comment:11 Changed 7 years ago by alfonsoml

I used the timer because initially the mutation event was fired a lot of times when the editor became visible (but the target of the event were elements outside the normally accesible elements like the components of the scrollbars). I didn't want to try to make the frame editable all those times, only one, so that's where the timer came from.

The comment about getting higher is because now using this.Window.frameElement works fine for the editor, but I did a little test using the raw editingArea and I didn't get the event to fire there, so there might be some situations were it doesn't work, or in 3.0 if the editing area is used in a different way then it might not get editable automatically.

The current resources usages I think that it's quite low: the mutation listener is expensive as I understand it, but we try to disable it as soon as possible, it won't affect the rest of the operation, and the timer is used only for a brief moment. I can try to remove it, but I wanted to run the MakeEditable outside the mutation event because the frame might not be still in a situation were it's possible to make it editable, and that way it gives us a little extra time (and also a little fear of what might happen if we change the properties of the frame inside the event). But the code is prepared to automatically set the mutation event again if it has failed, so we could remove it.

So in the end: Should I try to remove the timer or do I leave the code as it is?

comment:12 Changed 7 years ago by fredck

  • Status changed from reopened to closed
  • Resolution set to fixed

I was not really intended on making changes to the current code you have proposed. I was just opening some discussion over it, to mutually find points for enhancements.

But, after some tests with DOMAttrModified, I've found out that Firefox has quite a limited support of it. Probably this is the reason for this event to still be undocumented there. In my tests, the event has been fired only once, for the "style" attribute and "newValue" was equal to "prevValue". My intention was watching for changes on "offsetParent", but no event is fired for that.

For the timer, I completely understood your proposal when I read it, and I found it correct. With the possible "offsetParent" observation, we could have tried to avoid it to have no delay, but as that attribute mutation is not fired, we should really stay with the timer there, as the real way Firefox does things in quite obscure.

To conclude, let's leave things as is for now. Maybe something else could come at our minds while working for the 3.0.

Thanks again Alfonso.

comment:13 follow-up: ↓ 14 Changed 7 years ago by alfonsoml

Yes, in Firefox there's a bug and the value of the previous style isn't provided in the event: https://bugzilla.mozilla.org/show_bug.cgi?id=338679

But I don't think that changes to offsetParent might ever get reflected with a DOMAttrModified event, because I don't think that offsetParent is an attribute but a property of a node.

The DOM mutation events are documented and are part of the official W3C DOM, but for some reason they are largely unknown, I'll attach a dirty page that I modified to try to make this work, I planned to clean it better and then attach it to the testcases because it might be useful to do somethings that previously seemed too hard (like tracking when an element has been resized or moved), it allows also to know when a new row is added in a table, etc...

As I said the page is set up just for my last test, you'll have to check it and enable/disable what you are interested to look at. It's mostly a merge of testcase 004 and G. Talbot test page at http://gtalbot.org/DHTMLSection/DOM2MutationEvents.html

Changed 7 years ago by alfonsoml

This page could evolve to provide bigger understanding of the mutation events. You'll need firefox with Firebug to see the events in the console (or wrap the calls and call FCKDebug for non-firebug tests)

comment:14 in reply to: ↑ 13 Changed 7 years ago by fredck

Replying to alfonsoml:

But I don't think that changes to offsetParent might ever get reflected with a DOMAttrModified event, because I don't think that offsetParent is an attribute but a property of a node.

Oh... I've said a stupid thing. I think it is happening too often lately. I really need to sleep more.

The DOM mutation events are documented and are part of the official W3C DOM, but for some reason they are largely unknown.

I meant, no so well document in Mozilla's MDC.

What a pity it is not supported by IE.

comment:15 follow-up: ↓ 16 Changed 7 years ago by dieRooie

Not sure if I should add this here: I used your [588] solution and it works if you have one block hidden with display:none. I however have more than one on one page. Then somehow it only works for one of them.

The second one generates this error in my webdeveloper toolbar:

Error: uncaught exception: [Exception... "Component returned failure code: 0x80070057 (NS_ERROR_ILLEGAL_VALUE) [nsISelection.getRangeAt]"  nsresult: "0x80070057 (NS_ERROR_ILLEGAL_VALUE)"  location: "JS frame :: http://ossetws01.oss.intra/OBS-CRT/FCKeditor/editor/js/fckeditorcode_gecko.js :: anonymous :: line 58"  data: no]

Not sure if I miss something...

comment:16 in reply to: ↑ 15 ; follow-up: ↓ 17 Changed 7 years ago by alfonsoml

Replying to dieRooie:

Not sure if I should add this here: I used your [588] solution and it works if you have one block hidden with display:none. I however have more than one on one page. Then somehow it only works for one of them.

The second one generates this error in my webdeveloper toolbar:

Error: uncaught exception: [Exception... "Component returned failure code: 0x80070057 (NS_ERROR_ILLEGAL_VALUE) [nsISelection.getRangeAt]"  nsresult: "0x80070057 (NS_ERROR_ILLEGAL_VALUE)"  location: "JS frame :: http://ossetws01.oss.intra/OBS-CRT/FCKeditor/editor/js/fckeditorcode_gecko.js :: anonymous :: line 58"  data: no]

Not sure if I miss something...

Are you using the nightly or just applied that change in 2.4.3?

Anyway, it will be far easier to debug if you attach a simple example, but I think that a new ticket would be better as this change isn't related to ranges and selections and that seems the problem in your case.

comment:17 in reply to: ↑ 16 Changed 7 years ago by dieRooie

Replying to alfonsoml:

Replying to dieRooie:

Not sure if I should add this here: I used your [588] solution and it works if you have one block hidden with display:none. I however have more than one on one page. Then somehow it only works for one of them.

The second one generates this error in my webdeveloper toolbar:

Error: uncaught exception: [Exception... "Component returned failure code: 0x80070057 (NS_ERROR_ILLEGAL_VALUE) [nsISelection.getRangeAt]"  nsresult: "0x80070057 (NS_ERROR_ILLEGAL_VALUE)"  location: "JS frame :: http://ossetws01.oss.intra/OBS-CRT/FCKeditor/editor/js/fckeditorcode_gecko.js :: anonymous :: line 58"  data: no]

Not sure if I miss something...

Are you using the nightly or just applied that change in 2.4.3?

Anyway, it will be far easier to debug if you attach a simple example, but I think that a new ticket would be better as this change isn't related to ranges and selections and that seems the problem in your case.

I think I see you answered my question since I applied it it 2.4.3. Thanks for the great work.

comment:18 Changed 5 years ago by jmontoya

Here's a way to avoid this problem:

http://cksource.com/forums/viewtopic.php?f=6&t=8700

Note: See TracTickets for help on using tickets.
© 2003 – 2012 CKSource – Frederico Knabben. All rights reserved. | Terms of use | Privacy policy