Ext.define("IceCap.component.Selector", {

    xtype: "icecap-selector",

    autoEl: {
        tag: "span"
    },

    alias: [
        "widget-icecap-selector"
    ],

    extend: "Ext.Component",

    hidden: true,

    baseCls: Ext.baseCSSPrefix + "icecap-selector",

    draggable: {
        listeners: {
            beforedragstart: {
                fn: function (i_dragSoruce, i_event) {

                    var i_self = i_dragSoruce.comp;

                    var i_resizer = i_self.getResizer();

                    var a_handles = [
                        "n",
                        "s",
                        "e",
                        "w",
                        "nw",
                        "sw",
                        "se",
                        "ne"
                    ];

                    var b_within = true;

                    Ext.Array.each(a_handles, function (s_handle) {

                        var i_el;

                        switch (s_handle) {
                            case "s":
                                i_el = i_resizer.south;
                                break;
                            case "se":
                                i_el = i_resizer.southeast;
                                break;
                            case "sw":
                                i_el = i_resizer.southwest;
                                break;
                            case "e":
                                i_el = i_resizer.east;
                                break;
                            case "w":
                                i_el = i_resizer.west;
                                break;
                            case "n":
                                i_el = i_resizer.north;
                                break;
                            case "nw":
                                i_el = i_resizer.northwest;
                                break;
                            case "ne":
                                i_el = i_resizer.northeast;
                                break;
                        }

                        if (i_event.within(i_el)) {
                            b_within = false;
                        }
                    });

                    return b_within;
                }
            },
            dragend: {
                fn: function (i_dragSoruce, i_event) {

                    var i_self = i_dragSoruce.comp;

                    var i_region = i_self.getBox(false, true);

                    i_self.suspendEvent();

                    i_self.setLeft(Math.floor(i_region.left));
                    i_self.setTop(Math.floor(i_region.top));
                    i_self.setDragX(Math.floor(i_region.right));
                    i_self.setDragY(Math.floor(i_region.bottom));

                    i_self.resumeEvent();
                }
            }
        }
    },

    listeners: {
        removed: {
            fn: function() {

                var i_self = this;

                var i_resizer = i_self.getResizer();

                if (i_resizer) {
                    i_resizer.destroy();
                }
            }
        },
        beforerender: {
            fn: function () {

                var i_self = this;

                var o_data = i_self.renderData || i_self.data || {};

                Ext.applyIf(o_data, {
                    width: i_self.width || 0,
                    height: i_self.height || 0,
                });

                i_self.renderData = i_self.data = o_data;
            }
        },
        dragcomplete: {
            fn: function() {

                var i_self = this;

                var i_resizer = i_self.getResizer();

                if (!i_resizer) {

                    i_resizer = Ext.create("Ext.resizer.Resizer", {
                        target: i_self.getEl().dom,
                        transparent: true,
                        pinned: true,
                        handles: "all",
                        heightIncrement: IceCap.util.Handler.getHeight(),
                        widthIncrement: IceCap.util.Handler.getWidth(),
                        listeners: {
                            resize: {
                                fn: function() {

                                    var i_region = i_self.getBox(false, true);

                                    i_self.suspendEvent();

                                    i_self.setLeft( Math.floor(i_region.left));
                                    i_self.setTop( Math.floor(i_region.top));
                                    i_self.setDragX( Math.floor(i_region.right));
                                    i_self.setDragY( Math.floor(i_region.bottom));

                                    i_self.resumeEvent();
                                }
                            }
                        }
                    });

                    i_self.setResizer(i_resizer);
                }
            }
        }
    },

    renderTpl: [
        "<span id=\"{id}-selector\" class=\".icecap-selector\" draggable=false role=presentation data-ref=\"selectorEl\">",
        "</span>"
    ],

    childEls: [
        {
            name: "selectorEl",
            itemId: "selector"
        },
    ],

    config: {
        top: 0,
        left: 0,
        selecting: false,
        theme: "",
        dragX: 0,
        dragY: 0,
        dragSource: null,
        resizer: null
    },

    floating: true,

    alwaysOnTop: true,

    initComponent: function () {

        var i_self = this;
        i_self.cls = ["iceCap-selector", i_self.getTheme()].filter(Boolean).join("-");

        i_self.callParent(arguments);
    },

    updateSelecting: function(b_selecting) {

        var i_self = this;

        if (i_self.rendered) {
            i_self.calculateArea();
            if (b_selecting) {
                i_self.show();
            }
        }
    },

    updateLeft: function(value) {

        var i_self = this;

        if (i_self.rendered) {

            i_self.setLocalX(value);
        }
    },

    updateTop: function(value) {

        var i_self = this;

        if (i_self.rendered) {

            i_self.setLocalY(value);
        }
    },

    updateDragX: function(value) {

        var i_self = this;

        if (i_self.rendered) {
            i_self.calculateArea();
        }
    },

    updateDragY: function(value) {

        var i_self = this;

        if (i_self.rendered) {
            i_self.calculateArea();
        }
    },

    calculateArea: function() {

        var i_self = this;

        var n_left = i_self.getLeft();
        var n_top = i_self.getTop();

        var n_dragX = i_self.getDragX();
        var n_dragY = i_self.getDragY();

        var n_xMin = Math.min(n_left, n_dragX);
        var n_xMax = Math.max(n_left, n_dragX);

        var n_yMin = Math.min(n_top, n_dragY);
        var n_yMax = Math.max(n_top, n_dragY);


        var n_width = Math.ceil(n_xMax - n_xMin);
        var n_height = Math.ceil(n_yMax - n_yMin);

        if (i_self.getSelecting()) {

            i_self.setLocalXY([n_xMin, n_yMin]);
        }

        i_self.setSize(n_width, n_height);
    },

    resetPos: function(n_x, n_y) {

        var i_self = this;
        i_self.setSelecting(false);
        i_self.setLeft(n_x);
        i_self.setTop(n_y);
        i_self.setDragX(n_x);
        i_self.setDragY(n_y);
    }
});
