#9073 ImageUpload callback can not be called cross-domain CKEditor - ckeditor

https://dev.ckeditor.com/ticket/9073
I had a unique scenario that requires my image uploader/image management system to be hosted on a separate sever. Because of this, I ran into the security-error-blocked-a-frame-with-origin-from-accessing-a-cross-origin-frame error.
Through my research I was not able to identify a clear answer to solving this problem; although there may already be a way to do this/better way, I wanted to post my workaround here in case anyone else can use it.

CKEDITOR.on( 'dialogDefinition', function( ev ) {
console.log('dialof def');
var dialogName = ev.data.name,
dialog = ev.data.definition.dialog;
//verify dialog is of name image
if ( dialogName == 'image' ) {
//on show create click event listener
dialog.on('show', function(){
window.addEventListener("click", evalClickEventType, false);
})
//evaluate click event to ensure it is Browse Server button
function evalClickEventType(event){
if(event.srcElement.innerText == 'Browse Server'){
createMessageListener();
}
//if either type of close, or ok, remove clickEventListener
else if (event.srcElement.innerText == 'OK' || event.srcElement.innerText == 'X' || event.srcElement.innerText == 'Cancel'){
window.removeEventListener("click", evalClickEventType, false);
}
}
//add event listener for type message
function createMessageListener()
{
window.addEventListener("message", receiveMessage, false);
}
//set value to txtUrl when event message is emitted.
function receiveMessage(event){
CKEDITOR.dialog.getCurrent().setValueOf( 'info', 'txtUrl', event.data );
window.removeEventListener("message", receiveMessage, false);
}
}});
then simply replace
window.opener.CKEDITOR.tools.callFunction( funcNum, fileUrl );
with this in your image management solution to pass the url from cross-origin server.
var targetWindow = window.opener;
targetWindow.postMessage(imgSrc, "*")
https://developer.mozilla.org/en-US/docs/Web/API/Window/postMessage

Related

Pass the request to server sammyjs

New to sammyjs. We broadly have two modules, one is Server side rendered and another is a de-coupled client app. We have implemented ko and sammy and its working good. But for some requests, I need to pass it on to the server. Is that possible with sammy?
Sammy(function () {
this.get( ".*", function () {
var view = window.location.pathname;
if( view == "/" )
appViewModel.currentView( "home-page" );
else if( view == "/product" )
appViewModel.currentView( "product-page" );
else if( view == "/admin" )
return false; // SSR Page
});
}).run();
The answer turned out to be very simple, just don't capture the request in the first place.
this.get( "^(?!\/admin$).*$", function() {
// Do something
});

Firefox Bootstrapped Add-On Injecting before load

Is it possible to add event listeners for a document before a page has been navigated to using a Bootstrapped add-on? I would like to see what page the user wants to navigate to as well as later after the page loads to inspect the DOM. I need to run code in the HTML content context.
In the past I used a toolbar XUL and included javascript within it and it would load before the HTML page loaded.
i looked into doing stuff before DOMContentLoaded sometime ago and found out there is a document inserted observer.
order of events after running research code at bottom
readystate changes to interactive (i think multiple times, not sure)
readystate changes to complete
DOMContentLoaded event fires
load event fires (Sometimes load doesnt fire, if you might have to change addEventListener with capture arugment (3rd argument) as false or true)
apparently there should be readystate loading before all of this but i can never catch it i dont know why.
after running the code in scratchpad, browser environemnt of course, then load a new page and watch the error console it will throw these reports in this order:
ready state changed! ("interactive") Scratchpad/4:18
02:28:07.873 ready state changed! ("complete") Scratchpad/4:18
02:28:07.874 DOMContentLoaded event fired! Scratchpad/4:53
02:28:07.938 Load event fired! Scratchpad/4:45
here is the research code. it adds a the listeners and observer to see whats firing.
var {classes: Cc, interfaces: Ci, utils: Cu} = Components;
var os = Cc['#mozilla.org/observer-service;1'].getService(Ci.nsIObserverService);
var LMObserver;
function myObserver() {
this.register();
}
myObserver.prototype = {
observe: function (subject, topic, data) {
//Cu.reportError(subject);
//Cu.reportError(data);
//i think subject is window element
subject.onreadystatechange = function () {
//loading
//interactive
//complete
Cu.reportError('ready state changed! ("' + subject.readyState + '")');
//var body = subject.documentElement.querySelector('body')
//you want to change title so you would do that here do something like: if (subject.readystate == 'complete') { subject.title = 'blah blah' }
//Cu.reportError('has body element: ' + body)
}
},
register: function () {
os.addObserver(this, 'document-element-inserted', false);
},
unregister: function () {
os.removeObserver(this, 'document-element-inserted', false);
}
};
//below this is the DOMContentLoaded thing i put this here so we can see what fires in what order
var pageLoad = function(event) {
var win = event.originalTarget.defaultView;
if (win && win.frameElement) {
return;
}
Cu.reportError('Load event fired!');
}
var pageDOMContentLoaded = function(event) {
var win = event.originalTarget.defaultView;
if (win && win.frameElement) {
return;
}
Cu.reportError('DOMContentLoaded event fired!');
}
LMObserver = new myObserver;
gBrowser.addEventListener("load", pageLoad, true);
gBrowser.addEventListener("DOMContentLoaded", pageDOMContentLoaded, true);
//gBrowser.removeEventListener("load", pageLoad, true);
//gBrowser.removeEventListener("DOMContentLoaded", pageDOMContentLoaded, true);
//LMObserver.unregister();
Here's some more indepth research on load events added with true or false as capture argument: https://github.com/Noitidart/event-listener-experiment-DOMC-and-load/blob/master/bootstrap.js

Jquery validator is not un-highlighting "chosen" select box

I am using Chosen with jquery valodation.
you can see this example: http://jsfiddle.net/hfdBF/9/
if you click submit, you see that the validation is working for combo and input.
if you put one letter in the input box you will get an alert that the letter un-highlighted, as it suppose to be.
BUT, if you choose in the select box a value, it wont be alert as un-highlighted.
do you have any idea how to get that to work?
$(function() {
var $form = $("#form1");
$(".chzn-select").chosen({no_results_text: "No results matched"});
$form.validate({
errorLabelContainer: $("#form1 div.error"),
wrapper: 'div',
});
var settings = $.data($form[0], 'validator').settings;
settings.ignore += ':not(.chzn-done)';
settings.unhighlight= function(el){
alert(el.name + " hit unhighlight")
}
});​​
Thanks
You don't need to do the validation manually. You can bind a function to the change event handler that will check if the specific select is valid. This will also clear the error if the select is valid.
$('.chzn-select').change(function () {
$(this).valid();
});
You need to reset the jQuery validation manually:
$(".chzn-select").chosen().change(function () {
var value = $('#UserCompanyIds').val(); // the select element
if (value != "") {
$('.field-validation-error').each(function () {
if ($(this).attr('data-valmsg-for') == 'UserCompanyIds') {
$(this).html("");
$(this).removeClass("field-validation-error").addClass("field-validation-valid");
}
});
}
});
I hope this helps!

Tinymce is (sometimes) undefined

I'm using Tinymce (with jQuery) in a project I'm working at; we use a rich text editor for users to input information; however, sometimes when loading the page Firefox and Chrome will detect a 'tinymce is not defined' error (sometimes at different lines of the code), while other times the page will load just fine. What's weird is that it works perfectly with IE.
Here's a bit of the code I'm using:
view.find('textarea.rich-text').each(function () {
$(this).tinymce( /* ...rules... */);
});
And later on
_variable.find("#summary").tinymce().setContent(content);
This line is where the error (sometimes) gets caught. It seems to me that the problem is a loading issue, even though the tinyMCE plugin is initialized about 5000 lines prior this line.
Update: For now I have managed to 'solve' the problem with a setTimeout, but this seems like a really ugly way to do it.
A few points:
You don't mention whether or not the TinyMCE initialization is done within a jQuery ready event function. It should be of course.
You don't need the each loop. You can just say:
$('textarea.rich-text').tinymce({
script_url : '../js/tinymce/jscripts/tiny_mce/tiny_mce.js',
theme : "advanced",
...
});
You don't need the call to find since you are just selecting by id. Just do:
$("#summary").tinymce().setContent(content);
Your real issue is probably that tinymce has not finished initializing itself when you get the error. You see it has to load a script from the configured script_url. That may take a while. Therefore, you have to make use of a callback such as oninit.
If you do not have control over init method of TinyMCE then, you can follow this solution.
jQuery(document).ready(function($) {
function myCustomSetContent( id, content ) {
// Check if TinyMCE is defined or not.
if( typeof tinymce != "undefined" ) {
var editor = tinymce.get( id );
// Check if TinyMCE is initialized properly or not.
if( editor && editor instanceof tinymce.Editor ) {
editor.setContent( text );
editor.save( { no_events: true } );
} else {
// Fallback
// If TinyMCE is not initialized then directly set the value in textarea.
//TinyMCE will take up this value when it gets initialized.
jQuery( '#'+id ).val( text );
}
return true;
}
return false;
}
function myCustomGetContent( id ) {
// Check if TinyMCE is defined or not.
if( typeof tinymce != "undefined" ) {
var editor = tinymce.get( id );
// Check if TinyMCE is initialized properly or not.
if( editor && editor instanceof tinymce.Editor ) {
return editor.getContent();
} else {
// Fallback
// If TinyMCE is not initialized then directly set the value in textarea.
// TinyMCE will take up this value when it gets initialized.
return jQuery( '#'+id ).val();
}
}
return '';
}
$(".class-to-update-content").on("click", function(e) {
myCustomSetContent( "tinymce-editor-id", "New Content in Editor" );
});
$(".class-to-get-content").on("click", function(e) {
$("div.class-to-display-content").html( myCustomGetContent( "tinymce-editor-id" ) );
});
});
Ref : http://blog.incognitech.in/tinymce-undefined-issue/
EDIT: Solution included

Form validation on Facebook tab

I am using static FBML but I am having trouble debugging a form validation problem. I get the dialog which to me seems like it should return false, but the form submits anyway. I am using Firebug and I see a brief message in Red that I have no chance to read. I appreciate the help :-)
var txt ='Enter Zipcode';
//...
function setError(){
var obj=document.getElementById('mapsearch');
obj.setValue(txt);
obj.setStyle('color', '#FF0000');
}
function valform(){
var obj=document.getElementById('mapsearch');
var val = obj.getValue();
if(val!='' && !isNaN(val) && val.length>2 ){
return true;
} else {
setError();
(new Dialog()).showMessage('Zip Required', 'Please enter your zip code.');
return false;
}
}
//...
Try the "Persist" button if the Firebug/javascript error message in Firebug disappears too quickly. This way all messages are kept between page loads until you click "Clear".

Resources