[qo-modules-dev] [15] more work.

[ Thread Index | Date Index | More lists.tuxfamily.org/qo-modules-dev Archives ]


Revision: 15
Author:   ytorres
Date:     2008-11-12 22:19:53 +0100 (Wed, 12 Nov 2008)

Log Message:
-----------
more work. Use MessageWindows to display TODO mark. Add Folder/Item. Remove Folder/Item

Modified Paths:
--------------
    yannick/index.html
    yannick/php/lib.php
    yannick/php/shortcuts.php
    yannick/shortcuts.css
    yannick/shortcuts.js

Added Paths:
-----------
    yannick/MessageWindow.js
    yannick/img/application_cascade.png
    yannick/img/arrow_refresh.png
    yannick/img/cancel.png
    yannick/img/exclamation.png
    yannick/img/folder_mini.png
    yannick/img/help.png
    yannick/img/information.png
    yannick/img/page_edit.png
    yannick/img/shortcut_mini.png
    yannick/img/star.png


Added: yannick/MessageWindow.js
===================================================================
--- yannick/MessageWindow.js	                        (rev 0)
+++ yannick/MessageWindow.js	2008-11-12 21:19:53 UTC (rev 15)
@@ -0,0 +1,999 @@
+Ext.ns('Ext.ux.window'); 
+
+/**
+ * An object that represents a group of {@link Ext.ux.window.MessageWindow} instances
+ * and provides position management in addition to the standard Window Group features.
+ * @class Ext.ux.window.MessageWindowGroup
+ * @extends Ext.WindowGroup
+ * @constructor
+ */
+Ext.ux.window.MessageWindowGroup = function (config) {
+    config = config || {};
+    var mgr = new Ext.WindowGroup();
+    mgr.positions = [];
+    Ext.apply(mgr, config);
+    return mgr;
+};
+
+/**
+ * The default global Message Window group that is available automatically.  To have
+ * more than one group of Message Windows to utilize separate positioning in addition
+ * to the standard Window Manager features create additional instances of 
+ * {@link Ext.ux.window.MessageWindowGroup} as needed.
+ * @class Ext.ux.window.MessageWindowMgr
+ * @extends Ext.ux.window.MessageWindowGroup
+ * @singleton
+ */
+Ext.ux.window.MessageWindowMgr = Ext.ux.window.MessageWindowGroup(); 
+
+/**
+ * <p>If you are looking for a lightweight implementation of Toast or Notification windows this is
+ * <b>NOT</b> the class you want.  This class builds upon the implementation by <i>Edouard Fattal</i>.
+ * This class creates a specialized Window for notification messages and offers the following features:</p>
+ * 
+ * <br>Demo link: <a href="http://extjs-ux.org/repo/authors/mjlecomte/trunk/Ext/ux/window/msgWindow.html";>here</a>
+ * <br>Forum thread: <a href="http://extjs.com/forum/showthread.php?t=48135";>here</a><br>
+ * 
+ * <b>Features:</b>
+ * <ul>
+ * <li>+ Message windows may be bound to any element through configuration.</li>
+ * <li>+ A single Message Window may be reused or multiple Message Windows may be used simultaneously.</li>
+ * <li>+ Message windows can be managed by groups.</li>
+ * <li>+ Several configurable options.</li>
+ * <li>++ By default, Message Window will not steal focus.</li>
+ * </ul>
+ * <br>
+ * <b>Known issues/caveats/bugs/roadmap:</b>
+ * <ul>
+ * <li>+ config for custom showFx incomplete </li>
+ * <li>+ vertical location of subsequent windows may overlap if height changes.</li>
+ * <li>+ add config to limit drag options (for example lock x or y axis, etc.)</li>
+ * </ul>
+ * @class Ext.ux.window.MessageWindow
+ * @extends Ext.Window
+ * @author Michael LeComte (<a href="http://extjs.com/forum/member.php?u=6834";>mjlecomte</a>), inspired by Ext.ux.Notification\ToastWindow (Edouard Fattal)
+ * @license <a href="http://www.gnu.org/licenses/lgpl.html";>LGPL 3.0</a>
+ * @version 0.08 - Nov 8, 2008 (ALPHA!!!)
+ * @donate <form action="https://www.paypal.com/cgi-bin/webscr"; method="post">
+<input type="hidden" name="cmd" value="_s-xclick">
+<input type="image" src="https://www.paypal.com/en_US/i/btn/btn_donate_LG.gif"; border="0" name="submit" alt="Make a donation to support ongoing development">
+<img alt="" border="0" src="https://www.paypal.com/en_US/i/scr/pixel.gif"; width="1" height="1">
+<input type="hidden" name="encrypted" value="-----BEGIN PKCS7-----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-----END PKCS7-----
+">
+</form>
+ */
+Ext.ux.window.MessageWindow = Ext.extend(Ext.Window, {
+
+    /**
+     * @cfg {Boolean} autoDestroy
+     * The action to take after the message window has been hidden.  The default is true which
+     * will actually remove the window from the DOM and destroy it.  False will simply hide the
+     * window by setting visibility to hidden and applying negative offsets, keeping the window
+     * available to be redisplayed via the {@link #show} method.
+     */
+    autoDestroy: true,
+
+    /**
+     * @cfg {Boolean} autoHide
+     * {@link #autoHide}
+     * True to have message window automatically hide itself (defaults to true).
+     */
+    autoHide: true,
+
+    /**
+     * @cfg {Boolean} autoHeight
+     * True to use height:'auto', false to use fixed height (defaults to false).
+     */
+    autoHeight: false,
+			
+    /**
+     * @cfg {String} bodyStyle
+     * Custom CSS styles to be applied to the body element in the format expected by 
+     * Ext.Element.applyStyles (defaults to 'text-align:left;padding:10px;').
+     */
+    bodyStyle: 'text-align:left;padding:10px;',
+
+    /**
+    * @cfg {String} baseCls
+    * The base CSS class to apply to this panel's element (defaults to 'x-window').
+    */
+
+    /**
+     * @cfg {String} buttonAlign
+     * The alignment of any buttons added to this panel. Valid values are 'right', 'left',
+     * and 'center' (defaults to 'center').
+     */
+    buttonAlign: 'center',
+
+    /**
+     * @cfg {String} cls
+     * An optional extra CSS class that will be added to this component's Element (defaults
+     * to 'x-notification'). This can be useful for adding customized styles to the component
+     * or any of its children using standard CSS rules.
+     */
+    cls: 'x-notification',
+
+    /**
+     * @cfg {Boolean} constrain
+     * True to constrain the window to the viewport, false to allow it to fall outside of
+     * the viewport (defaults to true).  Optionally the header only can be constrained using
+     * {@link #constrainHeader}.
+     */
+    constrain: true,
+
+    /**
+     * @cfg {Boolean} constrainHeader
+     * True to constrain the window header to the viewport, allowing the window body to fall
+     * outside of the viewport, false to allow the header to fall outside the viewport (defaults
+     * to true).  Optionally the entire window can be constrained using {@link #constrain}.
+     */
+    constrainHeader: true,
+
+    /**
+     * @cfg {Boolean} draggable
+     * True to allow the window to be dragged by the header bar, false to disable dragging
+     * (defaults to true).  Note that by default the window will be centered in the viewport,
+     * so if dragging is disabled the window may need to be positioned programmatically after
+     * render (e.g., myWindow.setPosition(100, 100);).
+     */
+    draggable: true,
+
+    /** @cfg {Boolean} floating */
+    /** @private */
+    floating: true,
+
+    /**
+     * @cfg {Boolean} focusOnShow
+     * True to focus the window when shown (defaults to false).
+     */
+
+    /** @cfg {Boolean} frame */
+    /** @private */
+    frame: true,
+    
+    /**
+     * @cfg {Ext.ux.window.MessageWindowGroup} manager
+     * A reference to the MessageWindowGroup that should manage this Message Window (defaults 
+     * to {@link Ext.ux.window.MessageWindowMgr}). Specify a reference to an instance unless
+     * you want a new manager for each instance:
+     * <pre><code>
+     * var group2 = new Ext.ux.window.MessageWindowGroup({
+     *     //override any defaults or add to base class instance
+     *     groupId: 2, //groupId not implemented at this time
+     *     zseed: 2000 //change the zseed (default = 9000)
+     * });
+     * var mw1 = new Ext.ux.window.MessageWindow({
+     *     manager: group2//specify the MessageWindowGroup manager (instead of using default manager)
+     * });
+     * var mw2 = new Ext.ux.window.MessageWindow({
+     *     manager: group2//specify the MessageWindowGroup manager (instead of using default manager)
+     * });
+     * var mw3 = new Ext.ux.window.MessageWindow({
+     *     //will use default manager
+     * });
+     * </pre></code>
+     */
+
+    /**
+     * @cfg {Function} handleHelp
+     * Handler function when the help tool is clicked (defaults to {@link Ext#emptyFn}). 
+     * @param {Object} event The click event.
+     * @param {Object} toolEl The tool Element.
+     * @param {Object} panel The host Panel.
+     */
+    handleHelp: Ext.emptyFn,
+
+    /**
+     * @cfg {Boolean} help
+     * True to display tools for help.  Defaults to true.
+     */
+    help: true,
+
+    /**
+     * @cfg {Object} hideFx
+     * Config object for hide effects settings. An example with defaults shown:
+     * <pre><code>
+     * hideFx: {
+     *     delay: 5000,  //time in milliseconds to delay the start of the effect
+     *     duration: 0.25, //duration of the effect
+     *     mode: 'standard', // null = will not hide
+     *                       // 'standard' = traditional window hide (vanish)
+     *                       // 'standard' = traditional window hide (vanish)
+     *                       // anything else will use the default of ghost
+     *     useProxy: true //default is false to hide window instead
+     * }
+     * </code></pre>
+     */
+    hideFx: {
+        delay: 5000
+    },
+
+    /**
+     * @cfg {String} hoverCls
+     * An extra CSS class that will be added to this component's Element when
+     * hovering over (defaults to 'msg-over').
+     */
+    hoverCls: 'msg-over',
+
+    /**
+     * @cfg {String} iconCls
+     * A CSS class that will provide a background image to be used as the header icon (defaults
+     * to 'x-icon-information'). An example custom icon class would be something like: 
+     * .my-icon { background: url(../images/my-icon.gif) 0 6px no-repeat !important;} 
+     */
+    iconCls: 'x-icon-information',
+
+    /**
+     * @cfg {Boolean} maximizable
+     * True to display the 'maximize' tool button and allow the user to maximize the window, false to hide the button
+     * and disallow maximizing the window (defaults to false).  Note that when a window is maximized, the tool button
+     * will automatically change to a 'restore' button with the appropriate behavior already built-in that will
+     * restore the window to its previous size.
+     */
+
+    /**
+     * @cfg {Boolean} minimizable
+     * True to display the 'minimize' tool button and allow the user to minimize the window, false to hide the button
+     * and disallow minimizing the window (defaults to false).  Note that this button provides no implementation --
+     * the behavior of minimizing a window is implementation-specific, so the minimize event must be handled and a
+     * custom minimize behavior implemented for this option to be useful.
+     */
+
+    /**
+     * @cfg {Number} minHeight
+     * The minimum height in pixels allowed for this window (defaults to 100).  Only applies when resizable = true.
+     */
+    minHeight: 40,
+
+    /**
+     * @cfg {Number} minWidth
+     * The minimum width in pixels allowed for this window (defaults to 200).  Only applies when resizable = true.
+     */
+    minWidth: 200,
+
+    /**
+     * @cfg {Boolean} modal
+     * True to make the window modal and mask everything behind it when displayed, false to display it without
+     * restricting access to other UI elements (defaults to false).
+     */
+
+    /**
+     * @cfg {Array} msgs
+     * An array to hold the message queue for refreshing messages.  Body of the message window will be updated
+     * from the <b>text</b> element.
+     * <b>Example</b>:
+     * <pre><code>
+     * msgs: [
+     *     {text: 'Some text message 1', url:'http://extjs.com/support/training/'},
+     *     {text: 'Some text message 2 &raquo;', url:'http://extjs.com/support/training/'}
+     * ],
+     * </code></pre>
+     * The first message that will be displayed uses the <b>Title</b> and <b>html</b> config options.
+     */
+    msgs: [],
+
+    /**
+     * @cfg {Boolean} monitorResize
+     * This is automatically managed based on the value of constrain and constrainToHeader
+     */
+    monitorResize : true,
+
+    /**
+     * @cfg {Function} onEsc
+     * Allows override of the built-in processing for the escape key. Default action
+     * is to close the Window (performing whatever action is specified in {@link #closeAction}.
+     * To prevent the Window closing when the escape key is pressed, specify this as
+     * Ext.emptyFn (See {@link Ext#emptyFn}).
+     */
+
+    /**
+     * @cfg {Object} origin
+     * Config object for the message origin with the following sample of default properties:
+     * <b>Example</b>:
+     * <pre><code>
+     * //configure a different origin than the default bottom right corner of the window:
+     * origin: {
+     *     //get window's Ext.element:
+     *     el: Ext.get('northRegion'), //element to align to (defaults to document)
+     *     pos: "bl-bl",//position to align to (see {@link Ext.Element#alignTo} for more details defaults to "br-br").
+     *     offX: 10, //amount to offset horizontally (-20 by default)
+     *     offY: 0 //amount to offset vertically (-20 by default)
+     * },
+     * </code></pre>
+     */
+
+    /**
+     * @cfg {Boolean} pinOnClick
+     * True to display the 'pin' tool button and allow the user to pin the window, false
+     * to hide the button and disallow pinning the window (defaults to true).
+     */
+    pinOnClick: true,
+
+    /**
+     * @cfg {String} pinState
+     * Specify the initial pin state when the window is first shown. Specify null, 'pin', or the default
+     * 'unpin'. <pre>
+     * pinState  effect
+     * --------  ------
+     * null      window will show/hide itself, user can not control
+     * 'pin'     window will initially show itself in pinned state, user will need to click unpin to hide
+     * 'unpin'   window will initially show itself in unpinned state, user will need to click pin to keep open
+     * </pre>
+     */
+    pinState: 'unpin',
+
+    /**
+     * @cfg {Boolean} plain
+     * True to render the window body with a transparent background so that it will blend into the framing
+     * elements, false to add a lighter background color to visually highlight the body element and separate it
+     * more distinctly from the surrounding frame (defaults to false).
+     */
+    plain: false,
+    
+    /**
+     * @cfg {Boolean} resizable
+     * True to allow user resizing at each edge and corner of the window, false to disable resizing (defaults to false).
+     */
+    resizable: false,
+
+    /**
+     * @cfg {String} resizeHandles
+     * A valid {@link Ext.Resizable} handles config string (defaults to 'all').  Only applies when resizable = true.
+     */
+
+    /**
+     * @cfg {String} textHelp
+     * Qtip text to display for help tool (defaults to 'Get hel').  Only applicable if help = true. 
+     */
+    textHelp: 'Get help',
+
+    /**
+     * @cfg {String} textPin
+     * Qtip text to display for pin tool.  Only applicable if {@link pinState} == 'pin' or 'unpin'.
+     */
+    textPin: 'Pin this to prevent closing',
+
+    /**
+     * @cfg {String} textUnpin
+     * Qtip text to display for unpin tool.  Only applicable if {@link pinState} == 'pin' or 'unpin'.
+     */
+    textUnpin: 'Unpin this to close',
+
+    /**
+     * @cfg {Number} x
+     * The X position of the left edge of the Window on initial showing. Defaults to centering the Window within
+     * the width of the Window's container {@link Ext.Element Element) (The Element that the Window is rendered to).
+     */
+
+    /**
+     * @cfg {Number} y
+     * The Y position of the top edge of the Window on initial showing. Defaults to centering the Window within
+     * the height of the Window's container {@link Ext.Element Element) (The Element that the Window is rendered to).
+     */
+
+    /** @private */
+    initHidden : true,
+
+    /** @private */
+    initComponent : function () {
+
+        Ext.apply(this, {
+            collapsible: false,
+            footer: false,
+            minHeight: 20,
+            stateful: false
+        });
+        
+        //if interval is specified automatically show message windows
+        if (this.interval) {
+            this.startAutoRefresh();
+        } 
+        //set up automatic hide/close of window if so configured
+        if (this.autoHide) {
+            if (this.pinState === 'unpin') {
+                this.task = new Ext.util.DelayedTask(this.hide, this);
+            }
+        } 
+//new
+        else {
+			this.closable = true;
+		}
+//added this.closable
+        
+        //call parent
+        Ext.ux.window.MessageWindow.superclass.initComponent.call(this);
+
+        //add listeners
+        this.on({
+            hide: {
+                scope: this,
+                fn: function () {
+                    if (this.autoDestroy) {
+                        if (this.fireEvent("beforeclose", this) !== false) {
+                            this.fireEvent('close', this);
+                            this.destroy();
+                        }
+                    }
+                }
+            },
+            mouseout: {
+                scope: this,
+                fn: this.onMouseout
+            }
+        });
+
+        //add events
+        this.addEvents(
+            /**
+             * @event activate
+             * Fires after the window has been visually activated via {@link setActive}.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            /**
+             * @event deactivate
+             * Fires after the window has been visually deactivated via {@link setActive}.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            /**
+             * @event resize
+             * Fires after the window has been resized.
+             * @param {Ext.ux.window.MessageWindow} this
+             * @param {Number} width The window's new width
+             * @param {Number} height The window's new height
+             */
+            /**
+             * @event maximize
+             * Fires after the window has been maximized.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            /**
+             * @event minimize
+             * Fires after the window has been minimized.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            /**
+             * @event restore
+             * Fires after the window has been restored to its original size after being maximized.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            /**
+             * @event pinned
+             * Fires after the window has been pinned.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            'afterpin',
+            /**
+             * @event unpinned
+             * Fires after the window has been unpinned.
+             * @param {Ext.ux.window.MessageWindow} this
+             */
+            'afterunpin',
+            /**
+             * @event click
+             * Fires after the window has been clicked.
+             * @param {Ext.ux.window.MessageWindow} this
+             * @param {Ext.ux.window.MessageWindow} msg The message from the message array if configured.
+             */
+            'click');
+    },
+
+    //override
+    /** @private */
+    initEvents: function () {
+        
+        //use a slighly enhanced Ext.ux.window.MessageWindowMgr instead of the default WindowMgr
+        this.manager = this.manager || Ext.ux.window.MessageWindowMgr;
+
+        //the parent class will register, so no need to do it here:
+        //this.manager = this.manager || Ext.WindowMgr;
+        
+        Ext.ux.window.MessageWindow.superclass.initEvents.call(this);
+    },
+
+    focus: function () {
+        Ext.ux.window.MessageWindow.superclass.focus.call(this);
+    },
+    
+    /** @private */
+    toFront: function () {
+        if(this.manager.bringToFront(this)){
+            //only focus if configured as such
+            if(this.focusOnShow){
+                this.focus();
+            }
+        }
+        return this;
+    },
+
+    /** @private */
+    initTools: function () {
+
+        this.addTool({
+            id: 'unpin', // image points left
+            handler: this.handlePin,
+            //set initial visibility (also check if pinState is null)
+            hidden: (!this.pinState || this.pinState === 'pin'), 
+            qtip: this.textPin,
+            scope: this
+        });
+
+        this.addTool({
+            id: 'pin',// image points down
+            handler: this.handleUnpin,
+            hidden: (!this.pinState || this.pinState === 'unpin'), 
+            qtip: this.textUnpin,
+            scope: this
+        });
+
+        if (this.help) {
+            this.addTool({
+                id: 'help',
+                handler: this.handleHelp,
+                qtip: this.textHelp,
+                scope: this
+            });
+        }
+    },
+
+    /** @private */
+    onRender: function (ct, position) {
+        Ext.ux.window.MessageWindow.superclass.onRender.call(this, ct, position);
+        //after call to parent class onRender this.el exists.
+
+        //clip part of the window (for example the recurring messages that
+        //eject from a border have the bottom rounded edge, etc. clipped off.
+        if (this.clip) {
+            switch (this.clip) {
+            case 'bottom':
+                Ext.destroy(this.getEl().child('.' + this.baseCls + '-bl'));
+                break;
+            }
+        }
+
+        //add a class when hovering over in order to disable
+        //any updates to the window while hovering over
+        if (true) {
+            this.el.addClassOnOver(this.hoverCls);
+        }
+        
+        //add click listener to body
+        Ext.fly(this.body.dom).on('click', this.handleClick, this);
+    },
+
+    /**
+     * Toggles the active pin state.
+     */
+    togglePinState: function (event) {
+        //check which tool is visible
+        if (this.tools.unpin.isVisible()) {
+            this.handlePin(event, this.tools.unpin, this);
+        } else {
+            this.handleUnpin(event, this.tools.pin, this);
+        }
+    },
+
+    /**
+     * Override to the Panel Class createElement method.  This method is called by
+     * Panel Class' onRender().  Normally the panel class will create a header in the
+     * *-tc class, to utilize the default box class for styling we'll move the header
+     * inside the *-mc class to utilize  
+Ext.Element.boxMarkup:
+<div class="{0}-tl">
+    <div class="{0}-tr">
+        <div class="{0}-tc">
+            ##HEADER##
+            <div class="{0}-header {0}-draggable">
+                <div class="x-tool x-tool-close">
+                </div>
+                <span class="{0}-header-text">
+                </span>
+            </div>
+        </div>
+    </div>
+</div>
+<div class="{0}-ml">
+    <div class="{0}-mr">
+        <div class="{0}-mc">
+            <div class="{0}-body">
+                CONTAINER
+                ###############
+            </div>
+        </div>
+    </div>
+</div>
+<div class="{0}-bl">
+    <div class="{0}-br">
+        <div class="{0}-bc">
+        </div>
+    </div>
+</div>   
+
+
+
+ <div class="x-box-bwrap" id="ext-gen117">
+    <div class="x-box-ml">
+        <div class="x-box-mr">
+            <div class="x-box-mc">
+                <div style="-moz-user-select: none;" id="ext-gen116" class="x-box-header x-unselectable x-window-draggable">
+                    <div id="ext-gen128" class="x-tool x-tool-help">
+                    </div>
+                    <span class="x-box-header-text" id="ext-gen126"><h2>Title</h2></span>
+                </div>
+                <div class="x-box-body" id="ext-gen118" style="height: auto; width: 72px;">
+                    Message
+                </div>
+            </div>
+        </div>
+    </div>
+    <div class="x-box-bl x-panel-nofooter">
+        <div class="x-box-br">
+            <div class="x-box-bc"/>
+        </div>
+    </div>
+</div>
+     * @param {Object} name
+     * @param {Object} pnode
+     *///override panel class method:
+    // private
+    createElement : function (name, pnode) {
+        if (this.shiftHeader) {
+            switch (name) {
+            case 'header':
+                //don't create header yet if putting inside mc, do it when tbar is done
+                return;
+            case 'tbar':
+                Ext.ux.window.MessageWindow.superclass.createElement.call(this, 'header', pnode);
+                Ext.ux.window.MessageWindow.superclass.createElement.call(this, name, pnode);
+                return;
+            }
+        }
+        //caught the ones we needed to, call the default implementation
+        Ext.ux.window.MessageWindow.superclass.createElement.call(this, name, pnode);
+    },
+
+    //override/disable focus, see above.
+    focus: Ext.emptyFn, 
+
+    /** @private */
+    getState : function () {
+        return Ext.apply(Ext.ux.window.MessageWindow.superclass.getState.call(this) || {}, this.getBox());
+    },
+
+    /**
+     * Handler for when the message window body is clicked
+     * @param {Object} event The click event.
+     */
+    handleClick: function (event) {
+        this.fireEvent('click', this, this.msg);
+        this.togglePinState(event);
+    },
+
+    /**
+     * Handler for when pin button is clicked
+     * @param {Object} event The click event.
+     * @param {Object} toolEl The tool Element.
+     * @param {Object} panel The host Panel.
+     */
+    handlePin: function (event, toolEl, panel) {
+
+        //hide the unpin button
+        toolEl.hide();
+        
+        //show the pin button
+        this.tools.pin.show();
+
+        this.cancelHiding();
+        
+        this.fireEvent('afterpin', this);
+    },
+
+    /**
+     * Handler for when pin button is clicked
+     * @param {Object} event The click event.
+     * @param {Object} toolEl The tool Element.
+     * @param {Object} panel The host Panel.
+     */
+    handleUnpin: function (event, toolEl, panel) {
+
+        //hide the pin button
+        toolEl.hide();
+        
+        //show the unpin button
+        this.tools.unpin.show();
+
+        this.hide();
+
+        this.fireEvent('afterunpin', this);
+    },
+
+    /**
+     * cancel hiding of the window if {@link #autoHide} is true
+     */
+    cancelHiding: function () {
+        this.addClass('fixed');
+        if (this.autoHide) {
+            if (this.pinState === 'unpin') {
+                this.task.cancel();
+            }
+        }
+        //show the pin button
+        this.tools.pin.show();
+        //make sure the unpin button is hidden
+        this.tools.unpin.hide();
+        
+    },
+
+    //override parent method
+    /** @private */
+    animHide: function () {
+
+        //remove the position of this element from the manager
+        this.manager.positions.remove(this.pos);
+
+        //element to hide and configured Fx
+        var w, fx = this.hideFx || {};
+
+        //animate using a proxy instead of actual element if so configured
+        if (fx.useProxy) {
+            w = this.proxy;
+            this.proxy.setOpacity(0.5);
+            this.proxy.show();
+            var tb = this.getBox(false);
+            this.proxy.setBox(tb);
+            this.el.hide();
+            Ext.apply(fx, tb);
+        } else {
+            w = this.el;
+        }
+        
+        Ext.applyIf(fx, {
+            block: false,//default for window is true
+            callback: this.afterHide,
+            easing: 'easeOut',//'easeNone';
+            remove: true,
+            scope: this
+        });
+        
+        switch (fx.mode) {
+        case 'none':
+            break;
+        case 'slideIn':
+            w[fx.mode]("b", fx);
+//            w.slideIn("b", fx);
+            break;
+        case 'custom':
+            Ext.callback(fx.callback, fx.scope, [this, w, fx]);//callback(cb,scope,args,delay)
+            break;
+        case 'standard':
+            fx.duration = fx.duration || 0.25;
+            fx.opacity = 0;
+            w.shift(fx);
+            break;
+        default:
+            fx.duration = fx.duration || 1;
+            w.ghost("b", fx);
+            break;
+        }
+    },
+
+    //override parent method
+    /** @private */
+    afterShow: function () {
+        Ext.ux.window.MessageWindow.superclass.afterShow.call(this);
+        
+        //if user moves remove from position manager and cancel hiding
+		this.on('move', function(){
+            //remove the position of this element from the manager
+            this.manager.positions.remove(this.pos);
+            this.cancelHiding();
+		}, this);
+
+        if (this.autoHide) {
+           if (this.pinState === 'unpin') {
+                this.task.delay(this.hideFx.delay);
+            }
+        }
+    },
+
+    /**
+     * some cleanup still needed this method
+     * sizing / placement issues when height of windows changes
+     * should recalculate placement based on window height
+     */
+    /** @private */
+    animShow: function () {
+
+        //don't update if hovering over message
+        //check if visible so it will show initially
+        if (this.el.isVisible() && this.el.hasClass(this.hoverCls)) {
+            return;
+        }
+
+        if (this.msgs.length > 1) {
+            this.updateMsg();
+        }
+/*
+//for reference
+this.el.disableShadow();
+this.setPosition(0, 0);
+
+delete this.el.lastXY;
+delete this.el.lastLT;
+if(this.x === undefined || this.y === undefined){
+    var xy = this.el.getAlignToXY(this.container, 'c-c');
+    var pos = this.el.translatePoints(xy[0], xy[1]);
+    this.x = this.x === undefined? pos.left : this.x;
+    this.y = this.y === undefined? pos.top : this.y;
+}
+this.el.setLeftTop(this.x, this.y);
+
+alignTo        : 'tl',
+alignToXY      :  [ 5, (this.el.getComputedHeight() * -1) + 5],
+slideDirection : 'b'
+
+console.info('this.el.lastXY',this.el.lastXY);
+console.info('this.el.lastLT',this.el.lastLT);
+console.info('this.el.x',this.el.x);
+console.info('this.el.y',this.el.y);
+console.info('this.el.getComputedHeight()',this.el.getComputedHeight());
+console.log('====');
+*/
+
+        //element to hide and configured Fx
+        var w = this.el, fx = this.showFx || {};
+
+        this.origin = this.origin || {};
+
+        //apply defaults if not already configured
+        Ext.applyIf(this.origin, {
+            el: Ext.getDoc(), //defaults to document
+            increment: true, //whether to increment position of subsequent messages
+            pos: "br-br",//position to align to (see {@link Ext.Element#alignTo} for more details defaults to "br-br").
+            offX: -20, //amount to offset horizontally
+            offY: -20, //amount to offset vertically
+            spaY: 5    //vertical spacing between adjacent messages
+        });
+       
+        //track positions of each instance
+        this.pos = 0;
+
+        if (this.origin.increment) {
+            while (this.manager.positions.indexOf(this.pos) > -1) {
+                this.pos++;
+            }
+            this.manager.positions.push(this.pos);
+        }
+
+        var y = this.origin.offY - ((this.getSize().height + this.origin.spaY) * this.pos);            
+        
+//unused t (used for debugging)
+//        var t = this.getSize();
+        
+        //set the window size
+        this.setSize(this.width || this.minWidth, this.height || this.minHeight);
+
+        //increment the vertical position of the window
+        if (this.origin.increment) {
+            y = this.origin.offY - ((this.getSize().height + this.origin.spaY) * this.pos);            
+        } else {
+            y = 0;
+        }
+
+        w.alignTo(
+            this.origin.el, // element to align to.
+            this.origin.pos,        // position to align to (see {@link Ext.Element#alignTo} for more details).
+            [ this.origin.offX, y ] // Offset the positioning by [x, y]: 
+        );
+        
+        w.slideIn('b', {
+            duration: fx.duration || 1,
+            callback: this.afterShow,
+            scope: this
+        });
+    },
+
+    onMouseout: function () {
+        //console.info('in onMouseout');
+        //console.info(arguments);
+    },
+
+
+    /**
+     * @param {Object} el
+     * @param {Object} x
+     * @param {Object} y
+     * @private
+     */
+	positionPanel: function (el, x, y) {
+        if(x && typeof x[1] == 'number'){
+            y = x[1];
+            x = x[0];
+        }
+        el.pageX = x;
+        el.pageY = y;
+       	
+        if(x === undefined || y === undefined){ // cannot translate undefined points
+            return;
+        }
+        
+        if(y < 0){ y = 10; }
+        
+        var p = el.translatePoints(x, y);
+        el.setLocation(p.left, p.top);
+        return el;
+    },
+
+    /**
+     * Specify the message to be shown
+     * @param {String} msg Message to update the body with.
+     */
+    setMessage: function (msg) {
+        this.body.update(msg);
+    },
+
+    /**
+     * Set the title of the message window
+     * @param {String} title Title of Window
+     * @param {String} iconCls icon to use in header area
+     */
+    setTitle: function (title, iconCls) {
+        Ext.ux.window.MessageWindow.superclass.setTitle.call(this, title, iconCls || this.iconCls);
+    },
+
+    /**
+     * Start recurring messages
+     * @param {Boolean} update Whether to update the message before starting automatic refreshes.
+     */
+
+    startAutoRefresh : function(update){
+        if(update){
+            this.updateMsg(true);
+        }
+        if(this.autoRefreshProcId){
+            clearInterval(this.autoRefreshProcId);
+        }
+        // native javascript function to delay for a specified time before triggering the
+        // execution of a specific function. After triggering the called function the command
+        // doesn't complete. Instead it waits for the specified time again and then triggers
+        // the function again and continues to repeat this process of triggering the function
+        // at the specified intervals until either the web page is unloaded or the clearInterval
+        // function is called.
+        this.autoRefreshProcId = setInterval(this.animShow.createDelegate(this, []), this.interval);
+    },
+
+    /**
+     * Stop recurring messages
+     */
+    stopAutoRefresh : function(){
+        if(this.autoRefreshProcId){
+            clearInterval(this.autoRefreshProcId);
+        }
+    },
+
+    /**
+     * Update the message
+     * @param {String} msg The updated msg
+     */
+    updateMsg: function (msg) {
+
+        //don't update if hovering over message
+        if (this.el && !this.el.hasClass(this.hoverCls)) {
+
+            if (msg) {
+//                console.info('message passed');   
+            } else {
+                this.msgIndex = this.msgs[this.msgIndex + 1] ? this.msgIndex + 1 : 0;
+                this.msg = this.msgs[this.msgIndex];
+            }
+
+            //update the innerHTML of element
+            //this.el.dom.update(this.msg.text);
+            this.body.update(this.msg.text);
+        } else {
+            //console.info('hovering');
+        }
+    }    
+});
+
+//register the xtype
+Ext.reg('message-window', Ext.ux.window.MessageWindow);
\ No newline at end of file

Added: yannick/img/application_cascade.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/application_cascade.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/arrow_refresh.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/arrow_refresh.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/cancel.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/cancel.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/exclamation.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/exclamation.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/folder_mini.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/folder_mini.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/help.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/help.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/information.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/information.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/page_edit.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/page_edit.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/shortcut_mini.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/shortcut_mini.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: yannick/img/star.png
===================================================================
(Binary files differ)


Property changes on: yannick/img/star.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Modified: yannick/index.html
===================================================================
--- yannick/index.html	2008-11-11 21:37:06 UTC (rev 14)
+++ yannick/index.html	2008-11-12 21:19:53 UTC (rev 15)
@@ -11,6 +11,10 @@
 
 <!-- shortcuts -->
 <link rel="stylesheet" type="text/css" href="shortcuts.css" />
+
+
+<script src="MessageWindow.js"></script>
+
 <script src="shortcuts.js"></script>
 <script src="main.js"></script>
 </head>

Modified: yannick/php/lib.php
===================================================================
--- yannick/php/lib.php	2008-11-11 21:37:06 UTC (rev 14)
+++ yannick/php/lib.php	2008-11-12 21:19:53 UTC (rev 15)
@@ -73,7 +73,7 @@
 			  'size'=>$size,
 			  'lastmod'=>$lastmod,
 			  'url'=>$this->imgJs.'folder'
-	    );
+	      );
 
 	    }
 	$i ++;
@@ -116,7 +116,64 @@
     public function fs_move_to($FileName, $to) {
       rename($this->desktop.$FileName, $this->desktop.$to.'/'.$FileName);
     }
+    
+    public function fs_remove_item($name, $type) {
+      if( $type == 'folder' ) {
+	@rmdir($this->desktop.$name) or die('{success:false, msg:"dir not empty"}');
+	$o->success = true;
+	echo json_encode($o);
+      }
+    }
 
+    public function fs_new_item($name, $type) {
+    
+      if( $type == 'folder' ) {
+	// New folder
+	if( !is_dir($this->desktop.$name) ) {
+
+	  mkdir($this->desktop.$name, 0777);
+	  $item = array(
+	    'id'=>uniqid(),
+	    'type'=>'folder',
+	    'originName'=>$name,
+	    'name'=>$name,
+	    'size'=>disk_total_space($this->desktop.$name),
+	    'lastmod'=>(filemtime($this->desktop.$name)*1000),
+	    'url'=>$this->imgJs.'folder'
+	  );
+	  $o->success = true;
+	  $o->item = $item;
+	  echo json_encode($o);
+	} else {
+	  $o->success = false;
+	  echo json_encode($o);
+	}
+      } else if ( $type == 'file' ) {
+	// New file
+        if( !is_file($this->desktop.$name) ) {
+
+	touch($this->desktop.$name, 0777);
+	chmod($this->desktop.$name, 0777);
+
+	$item = array(
+	  'id'=>uniqid(),
+	  'type'=>'file',
+	  'originName'=>$name,
+	  'name'=>$name,
+	  'size'=>filesize($this->desktop.$name),
+	  'lastmod'=>(filemtime($this->desktop.$name)*1000),
+	  'url'=>$this->imgJs.'text.png'
+	);
+	$o->success = true;
+	$o->item = $item;
+	echo json_encode($o);
+	} else {
+	  $o->success = false;
+	  echo json_encode($o);
+	}
+      }
+    }
+
     public function fs_update_filename($originName, $newName) {
 
       $o->success = false;

Modified: yannick/php/shortcuts.php
===================================================================
--- yannick/php/shortcuts.php	2008-11-11 21:37:06 UTC (rev 14)
+++ yannick/php/shortcuts.php	2008-11-12 21:19:53 UTC (rev 15)
@@ -25,6 +25,14 @@
   case 'update-fileName' :
 	$o->fs_update_filename($_POST['originName'], $_POST['newName']);
 	break;
+
+  case 'new-item' :
+	$o->fs_new_item($_POST['name'], $_POST['type']);
+	break;
+
+  case 'remove-item' :
+	$o->fs_remove_item($_POST['name'], $_POST['type']);
+	break;
 }
 
 ?>
\ No newline at end of file

Modified: yannick/shortcuts.css
===================================================================
--- yannick/shortcuts.css	2008-11-11 21:37:06 UTC (rev 14)
+++ yannick/shortcuts.css	2008-11-12 21:19:53 UTC (rev 15)
@@ -56,3 +56,43 @@
 .x-view-selected .thumb{
 	background:transparent;
 }
+
+.refresh {
+	background: url('img/arrow_refresh.png') no-repeat;
+}
+
+.about {
+	background: url('img/help.png') no-repeat;
+}
+
+.arrangeBy {
+	background: url('img/application_cascade.png') no-repeat;
+}
+
+.new {
+	background: url('img/star.png') no-repeat;
+}
+
+.new_folder {
+	background: url('img/folder_mini.png') no-repeat;
+}
+
+.new_file {
+	background: url('img/page_edit.png') no-repeat;
+}
+
+.remove {
+	background: url('img/cancel.png') no-repeat;
+}
+
+.new_shortcut {
+	background: url('img/shortcut_mini.png') no-repeat;
+}
+
+.x-icon-error {
+	background: url('img/exclamation.png') no-repeat;
+}
+
+.x-icon-information {
+	background: url('img/information.png') no-repeat;
+}
\ No newline at end of file

Modified: yannick/shortcuts.js
===================================================================
--- yannick/shortcuts.js	2008-11-11 21:37:06 UTC (rev 14)
+++ yannick/shortcuts.js	2008-11-12 21:19:53 UTC (rev 15)
@@ -42,7 +42,7 @@
     prepareData: function(data) {
 	data.shortName = Ext.util.Format.ellipsis(data.name, 15);
 	data.sizeString = Ext.util.Format.fileSize(data.size);
-	data.dateString = data.lastmod.format("m/d/Y g:i a");
+	//data.dateString = data.lastmod.format("m/d/Y g:i a");
 	return data;
     },
  
@@ -68,6 +68,9 @@
 	// Init contextMenu for shortCut
         this.getEl().on('contextmenu', this.ctxInit, this);
 	
+	// Launcher
+        this.getEl().on('dblclick', this.LaunchApp, this, {delegate: 'div.thumb'});
+	
 	// Move icon
 	this.DDmoveIcon();
 	
@@ -226,6 +229,25 @@
 
     },
 
+    LaunchApp : function(e, target) {
+
+      var item = this.findItemFromChild(target);
+      var record = this.store.getAt(this.indexOf(item));
+
+      if( record.data['type'] == 'folder' ) {
+	this.showMessageWindow('Info', 'Launch the FileExplorer', 'info');
+      }
+
+      if( record.data['type'] == 'file' ) {
+	this.showMessageWindow('Info', 'Launch the FileEditor (need to be done according to the <b>mimeType</b> of this file)', 'info');
+      }
+
+      if( record.data['type'] == 'shortcut' ) {
+	this.showMessageWindow('Info', 'Launch this App', 'info');
+      }
+      
+    },
+
     // LabelEditor
     LabelEditorInit : function(e, target) {
 
@@ -309,14 +331,16 @@
 
 	var menu = new Ext.menu.Menu();
 	menu.add({
+	    scope: this,
             text: 'Open',
             //iconCls: '',
-            handler: function(){}
+            handler: function(){ this.showMessageWindow('Error', 'Not implemented yet', 'error'); }
         });
 	menu.add({
+	    scope: this,
             text: 'Remove',
-            //iconCls: '',
-            handler: function(){}
+            iconCls: 'remove',
+            handler: function(){ this.delItem(record); }
         });
         menu.showAt(e.getXY());
     },
@@ -328,28 +352,38 @@
 
 	menu.add({
 	    text:'New',
+	    iconCls: 'new',
 	    menu: {
 		items: [new Ext.menu.Item({
-			text:'Folder',
-			handler: function() { console.log('new folder'); }
+			  text:'Folder',
+			  iconCls: 'new_folder',
+			  scope: this,
+			  handler: function(btn, e) { this.addItem(e, 'folder'); }
 			}),new Ext.menu.Item({
-			text: 'ShortCut',
-			handler: function() { console.log('new shortCut'); }
+			  scope: this,
+			  text: 'ShortCut',
+			  iconCls: 'new_shortcut',
+			  handler: function() { this.showMessageWindow('Error', 'Not implemented yet', 'error'); }
 			}),new Ext.menu.Item({
-			text: 'Text Document',
-			handler: function() { console.log('new Text document'); }
+			  scope: this,
+			  text: 'Text Document',
+			  iconCls: 'new_file',
+			  handler: function() { this.addItem(e, 'file'); }
 			}
 		)]
 	    }
 	});
 
 	menu.add({
+	    scope: this,
 	    text: 'Refresh',
-	    handler: function() { console.log('refresh the desktop'); }
+	    iconCls: 'refresh',
+	    handler: function() { this.store.reload(); }
 	});
 
 	menu.add({
             text: 'Arrange icons by',
+	    iconCls: 'arrangeBy',
             menu: {
 	      items: [new Ext.menu.Item({
 		scope: this,
@@ -369,7 +403,7 @@
 	menu.addSeparator();
 	menu.add({
             text: 'About this desktop',
-            //iconCls: '',
+            iconCls: 'about',
             handler: function(){}
         });
         menu.showAt(e.getXY());
@@ -457,9 +491,125 @@
 	i ++;
       }, this);
       
-      console.log(Ext.util.JSON.encode(newPosition));
+      //console.log(Ext.util.JSON.encode(newPosition));
       
       }
+    },
+    
+    addItem: function(e, type) {
+      var m1, m2;
+      if( type == 'folder' ) { m1 = 'New Folder'; m2 = 'Please enter the name for this new Folder:'; }
+      if( type == 'file' ) { m1 = 'New File'; m2 = 'Please enter the name for this new File:'; }
+      Ext.MessageBox.prompt(m1, m2, function(btn, text) {
+      
+	if( btn == 'ok' && text != '' ) {
+	
+	  	Ext.Ajax.request({
+		scope: this,
+		url: 'php/shortcuts.php',
+		params: {
+		    name: text,
+		    type: type,
+		    what: 'new-item'
+		},
+		success: function(response, options) {
+		  var o = Ext.util.JSON.decode(response.responseText);
+
+		  if( o.success ) {
+
+		    var RecordDef = Ext.data.Record.create([
+			{name: 'id', mapping: 'id'},
+			{name: 'name', mapping: 'name'},
+			{name: 'originName', mapping: 'originName'},
+			{name: 'url', mapping: 'url'},
+			{name: 'size', type: 'float', mapping: 'size'},
+			{name: 'lastmod', mapping: 'lastmod',  type:'date', dateFormat:'timestamp'},
+			{name: 'type', mapping: 'type'}
+		    ]);
+
+		    var Record = new RecordDef({
+		      id : o.item.id,
+		      name : o.item.name,
+		      originName : o.item.originName,
+		      url : o.item.url,
+		      size : o.item.size,
+		      lastmod : o.item.lastmod,
+		      type : o.item.type
+		    }, o.item.id);
+
+		    this.store.add(Record);
+
+		    // Move to the right position according to the right-click event
+		    Ext.get('shortcuts_'+o.item.id).moveTo(e.getPageX(),e.getPageY(),true);
+
+		    // Re-initialise the drag&drop functionnality
+		    this.DDInit();
+
+		    // TODO
+		    this.showMessageWindow('TODO', 'We must pass the position to update the state\'s file on success. If we reload the page for now, the state of this new item is not restaure.', 'error');
+
+		  } else {
+		    this.showMessageWindow('Error', 'this item allready exist ! Change the name', 'error'); // can be info in 3 parameters
+		  }
+		}
+	      });
+	
+	}
+      }, this);
+
+    },
+    
+    delItem : function(record) {
+    
+		  Ext.Ajax.request({
+		  scope: this,
+		  url: 'php/shortcuts.php',
+		  params: {
+		      name: record.data['originName'],
+		      type: record.data['type'],
+		      what: 'remove-item'
+		  },
+		  success: function(response, options) {
+		    var o = Ext.util.JSON.decode(response.responseText);
+		    if( o.success ) {
+		      this.store.remove(record);
+		      
+		      // TODO
+		      this.showMessageWindow('TODO', 'We must erase this item from the state\'s file on success. Just to keep this file clean', 'error');
+		    } else {
+		      // TODO
+		      this.showMessageWindow('TODO', 'handle error on remove item.<br/>Server message : <b>'+o.msg+'</b>', 'error');
+		    }
+		  }
+		  });
+    },
+
+    showMessageWindow : function(MessageTitle, MessageText, style) {
+
+      new Ext.ux.window.MessageWindow({
+	title: MessageTitle,
+	autoDestroy: true,
+	autoHeight: true,
+	autoHide: true,
+	bodyStyle: 'text-align:center',
+	pinState: null,
+	help: false,
+	hideFx: {
+	  delay: 500,
+	  duration: 0.5,
+	  mode: 'standard',
+	  useProxy: false
+	},
+	html: MessageText,
+	iconCls: (style == 'error' ) ? 'x-icon-error' : 'x-icon-information',
+	showFx: {
+	  delay: 0,
+	  duration: 0.5,
+	  mode: 'standard',
+	  useProxy: false
+	},
+	width: 250
+      }).show(Ext.getDoc());
     }
 
 });


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/