Table of Contents
- General
- Coding
- Center a window on screen
- Focus a widget inside a window
- Implement a context-menu
- Disable the browser context menu
- Problems with "this" in event handlers
- Transparent colors
- User-defined data
- Modal windows
- Add a flash movie to a window
- Table Celleditors: Stop editing on value change
- Enabling drag and drop in virtual widgets
- Finding out which qooxdoo widget generated a given DOM element
- Tooling
Snippets
These code snippets have come mainly from the mailing list. If you find a mistake in any of the snippets, or have an improvement, or have a snippet of your own, please Login to this wiki and edit these pages.
General
Demo Browser
The Demo Browser has a large number of simple examples. You can use the online version or if you’ve downloaded and built the SDK, you can use your local copy in application/demobrowser/build subdirectory of your SDK installation.
Show HTML created by qooxdoo
Sometimes you want to see the HTML created by qooxdoo to solve layout problems or track down bugs in qooxdoo.
In Firefox you can use the Firebug extension. “Inspect Element” allows you to click on any part of the page and see the XML and CSS that generated the element.
Otherwise this link will work in all browsers to show the XML tree for the current page:
javascript:if (window.document.body.outerHTML != undefined){'<xmp>'+window.document.body.outerHTML+'</xmp>'} else if (document.getElementsByTagName("html")[0].innerHTML != undefined){'<xmp>'+document.getElementsByTagName("html")[0].innerHTML+'</xmp>'} else if (window.document.documentElement.outerHTML != undefined){'<xmp>'+window.document.documentElement.outerHTML+'</xmp>'} else { alert('Your browser does not support this functionality') };
There is also a simpler form for IE that will open up the XML in a new window:
javascript:void(window.open("javascript:'<xmp>'+opener.window.document.documentElement.outerHTML+'</xmp>'"));
You can create a shortcut for this on the toolbar.
Coding
Center a window on screen
Here is the solution:
var win = new qx.ui.window.Window(); .... // first solution win.addListener("resize", function(){ this.center(); }, win); // second solution win.addListener("resize", win.center); this.getRoot().add(win); win.open();
This solution works even if we don’t know the real size of the window, because it depends on its content.
Before the window is shown and know its real size, we place it at the center. We use the resize event instead of the appear event to prevent any flickering, because when using the appear event the window is already visible and then moved to the center. With the resize you can center the window right after the inserting in the DOM (the widget resizes) and avoid any flickering.
Focus a widget inside a window
Here is the solution:
var win = new qx.ui.window.Window(); var field = new qx.ui.form.TextField; win.add(field) ... field.focus(); this.getRoot().add(win); win.open();
Setting the focus at the textfield widget is done in a post-process, so you do not have to use any event listener methods to achieve this.
Implement a context-menu
Implementing a context-menu is as easy as never before.
var container = new qx.ui.container.Composite(new qx.ui.layout.Canvas); container.setPadding(20); this.getRoot().add(container); ... var list = new qx.ui.form.List; list.setContextMenu(this.getContextMenu()); container.add(list); ... getContextMenu : function() { var menu = new qx.ui.menu.Menu; var cutButton = new qx.ui.menu.Button("Cut", "icon/16/actions/edit-cut.png", this._cutCommand); var copyButton = new qx.ui.menu.Button("Copy", "icon/16/actions/edit-copy.png", this._copyCommand); var pasteButton = new qx.ui.menu.Button("Paste", "icon/16/actions/edit-paste.png", this._pasteCommand); cutButton.addListener("execute", this.debugButton); copyButton.addListener("execute", this.debugButton); pasteButton.addListener("execute", this.debugButton); menu.add(cutButton); menu.add(copyButton); menu.add(pasteButton); return menu; }
This little code snippet is taken from the online demo. Just right-click at the list.
Disable the browser context menu
qooxdoo does show the default right-click browser menu. How can I disable it?
qx.core.Init.getApplication().getRoot().setNativeContextMenu(false);
Problems with "this" in event handlers
How do I ensure that the correct “this” is referred to in an event handler? Say you have an event-handler within a custom widget which looks like this:
_someHandler : function(e) { alert(this); }
and then later within the same class definition, register a handler with another class instance:
var anotherWidget = new AnotherWidget(); anotherWidget.addEventListener("changeSomething", this._someHandler);
When the handler gets triggered by a “changeSomething” event, the alert of the handler is being called. However, there is a problem in that ‘this’ now refers to an object of class AnotherWidget and not to the instance of MyWidget. To solve this problem, use:
anotherWidget.addEventListener("changeSomething", this._handler, this);
Transparent colors
To set a transparent color for any widget do the following:
// text color myWidget.setTextColor("transparent"); // background color myWidget.setBackgroundColor("transparent");
As the transparent color is part of every color theme in qooxdoo, you set this color by simply use this string.
User-defined data
Storing any arbitrary value in a qooxdoo object.
You can store arbitrary user-defined data in any qooxdoo object using the setUserData and getUserData methods. These are guaranteed not to conflict with qooxdoo or javascript properties of the object. Note that as qooxdoo events are derived from qx.event.type.Event which extends qx.core.Object, you can store user-defined data in events as well.
For example:
MyObject.setUserData("MyData", "123"); MyObject.debug("MyData = " + MyObject.getUserData("MyData"));
Modal windows
Modal windows are windows which have to be closed (e.g. via it’s buttons like “OK” or “Cancel”) before any other UI element can be used. In qooxdoo a special blocker element is used to prevent user actions on other elements than the open modal window. The blocker element can be styled (e.g. it can have an semi-transparent background) to accent that the window is a modal one. The blocker included in every root widget (qx.ui.root.Application, qx.ui.root.Inline, qx.ui.root.Page) and in qx.ui.window.Desktop.
this.getApplicationRoot().set({ blockerColor: '#bfbfbf', blockerOpacity: 0.8 });
Add a flash movie to a window
This short snippet also applies if just want to add a flash movie to your qooxdoo application.
var doc = this.getRoot(); var win = new qx.ui.window.Window("Window"); win.setLayout(new qx.ui.layout.Canvas()); doc.add(win, {top: 20, left: 20}); var layout = new qx.ui.layout.Basic(); var container = new qx.ui.container.Composite(layout); container.set({ width: 400, height: 400 }); win.add(container); win.addListener("appear", function() { var domElement = container.getContentElement().getDomElement(); var flash = qx.bom.Flash.create(domElement, FLASH_URL, "flashMovie"); }); win.open();
Table Celleditors: Stop editing on value change
As default behaviour the cell editors of the table widget are stop the editing mode whenever the user clicks at any other cell. Anyway sometimes the users want to be able to stop the editing whenever the value has changed, e.g. if they pick another item out of the list of a combobox. To achieve this you can add the following to the cell editor classes
// this snippet targets the ComboBox cell editor // this approach should also work for the other cell editors createCellEditor : function(cellInfo) { ... cellEditor.addEventListener("changeValue", function() { cellInfo.table.stopEditing(); }, this); ... }
Enabling drag and drop in virtual widgets
To enable drag and drop features at virtual widgets you currently have to manipulate framework methods directly. The issues with drag and drop in virtual widgets will be addressed with the Bug #1215
// patch the "supportsDrop" method qx.ui.core.Widget.prototype.supportsDrop = function(dragCache) { var supportsDropMethod = this.getSupportsDropMethod(); if (supportsDropMethod !== null) { return supportsDropMethod.call(this, dragCache); } return true; }; // patch the "getDropTarget" method qx.event.handler.DragAndDropHandler.prototype.getDropTarget = qx.core.Variant.select("qx.client", { "gecko" : function(e) { var vCurrent = e.getTarget(); // if (vCurrent == this.__dragCache.sourceWidget) { // vCurrent = qx.event.handler.EventHandler.getTargetObject(qx.html.ElementFromPoint.getElementFromPoint(e.getPageX(), e.getPageY())); // } else { vCurrent = qx.event.handler.EventHandler.getTargetObject(null, vCurrent); // } while (vCurrent != null) { if (!vCurrent.supportsDrop(this.__dragCache)) { return null; } if (this.supportsDrop(vCurrent)) { return vCurrent; } vCurrent = vCurrent.getParent(); } return null; }, "default" : function(e) { var vCurrent = e.getTarget(); while (vCurrent != null) { if (!vCurrent.supportsDrop(this.__dragCache)) { return null; } if (this.supportsDrop(vCurrent)) { return vCurrent; } vCurrent = vCurrent.getParent(); } return null; } }),
Finding out which qooxdoo widget generated a given DOM element
I have found this useful for testing with Selenium. If you have a native DOM element and want to find out which qooxdoo widget it is, use the following code, (I only tried it in qooxdoo 0.8).
getQooxdooClassName: function (domElement) { if (!qx) return; // this is not a qooxdoo frame if (domElement.$$hash) { var qxWrapper = qx.core.ObjectRegistry.__registry[domElement.$$hash]; if (qxWrapper.__attribValues && qxWrapper.__attribValues["$$widget"]) { var wid = qxWrapper.__attribValues["$$widget"]; // widgetId var widget = qx.core.ObjectRegistry.__registry[wid]; return widget.classname } } // the domElement has no qooxdoo counterpart - returns `undefined` };
Tooling
Compress qooxdoo without mod_deflate
This explains how to enable a gzipped qooxdoo.js without having this possibility directly built in to your webserver.
If you have php at the server, you can write in your html file:
<script type="text/javascript" src="<<path>>/qooxdoo.php"></script>
Then you create a file called qooxdoo.php with this content:
<?php /** * @author Oliver Vogel <o.vogel@muv.com> * @since 05.03.2006 */ $encodings = array(); if (isset($_SERVER['HTTP_ACCEPT_ENCODING'])) { // Get all available encodings $encodings = explode(',', strtolower(preg_replace("/\s+/", "", $_SERVER['HTTP_ACCEPT_ENCODING']))); // Check for gzip header if (in_array('gzip', $encodings)) { // found: send the zip-ed file header("Content-Encoding: gzip"); echo file_get_contents(getenv('DOCUMENT_ROOT') . '<<path>>/qooxdoo.js.gz'); die; } } // Encoding not found or gzip not accepted -> send "normal" file echo file_get_contents(getenv('DOCUMENT_ROOT') . '<<path>>/qooxdoo.js'); die; ?>
This page checks if the browser supports gzip. If this is true, the server sends the gzip file to the client. This solution needs no gzip-support at the server-side!
Also, if you are writing your own webserver it is trivial to include this feature directly.
I know, it is NOT JavaScript but maybe it is a good idea to add this to the qooxdoo distribution (and it may be a good idea if one with Python or Perl or other experience ports this script to another server-side programming language).
Contributed by Oliver Vogel, here.
