/*
@version $Id: container.js 270 2009-12-28 13:24:34Z roosit $
@copyright Copyright (C) 2008 Abricos. All rights reserved.
@license http://www.gnu.org/copyleft/gpl.html GNU/GPL, see LICENSE.php
*/
/**
* @module Sys
* @namespace Brick.widget
*/
var Component = new Brick.Component();
Component.requires = {
yahoo: ['container']
};
Component.entryPoint = function(){
Brick.namespace('widget');
var Dom = YAHOO.util.Dom,
E = YAHOO.util.Event,
L = YAHOO.lang;
var TMG = this.template,
TM = TMG.get(),
T = TM.data,
TId = TM.idManager;
var m_oMinimizedIconTemplate,
m_oMaximizedIconTemplate,
m_oNormalIconTemplate,
m_oCloseIconTemplate;
// счетчик глобального идентификатора каждой панели
var _globalIdCounter = 0;
/**
* Панель
*
* @class Panel
* @extends YAHOO.widget.Panel
* @constructor
* @param {Object} config Конфигурация панели.
*/
var Panel = function(config){
/**
* Уникальный идентификатор панели.
*
* @property globalId
* @type String
*/
this.globalId = 'panel'+ (_globalIdCounter++);
config = L.merge({
draggable: true,
visible: false,
autofillheight: "body",
constraintoviewport:true,
// menubar: "",
template: "",
elbody: null,
parentNode: document.body
}, config || {});
var el = this._buildPanel(config);
Panel.superclass.constructor.call(this, el, config);
};
Panel.CONTROLBOX_CLOSE = 0;
Panel.CONTROLBOX_FULL = 1;
Panel.CONTROLBOX_HIDE = 2;
Panel.STATE_NORMAL = 0;
Panel.STATE_MAXIMIZED = 1;
Panel.STATE_MINIMIZED = 2;
DEFAULT_CONFIG = {
"STATE": {
key: "state",
value: Panel.STATE_NORMAL,
validator: L.isNumber,
supercedes: ['x', 'y', 'xy', 'fixedcenter', 'iframe']
},
"CONTROLBOX" : {
key: "controlbox",
value: Panel.CONTROLBOX_CLOSE,
validator: L.isNumber
},
"MINWIDTH" : {
key: "minwidth",
value: 350,
validator: L.isNumber
},
"MINHEIGHT" : {
key: "minheight",
value: 200,
validator: L.isNumber
},
"RESIZE" : {
key: "resize",
value: true,
validator: L.isBoolean
},
"OVERFLOW" : {
key: "overflow",
value: true,
validator: L.isBoolean
},
"RIGHT" : {
key: "right",
value: null,
validator: L.isNumber,
supercedes: ['x','fixedcenter', 'iframe']
},
"BOTTOM" : {
key: "bottom",
value: null,
validator: L.isNumber,
supercedes: ['y','fixedcenter', 'iframe']
}
};
YAHOO.extend(Panel, YAHOO.widget.Panel, {
_actionBlocked: false,
_actionBlockedElements: null,
_actionBlockedIgnore: {},
initDefaultConfig: function () {
Panel.superclass.initDefaultConfig.call(this);
var cfg = this.cfg;
cfg.addProperty(DEFAULT_CONFIG.RESIZE.key, {
handler: this.configResize,
value: DEFAULT_CONFIG.RESIZE.value,
validator: DEFAULT_CONFIG.RESIZE.validator,
supercedes: DEFAULT_CONFIG.RESIZE.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.CONTROLBOX.key, {
handler: this.configControlBox,
value: DEFAULT_CONFIG.CONTROLBOX.value,
validator: DEFAULT_CONFIG.CONTROLBOX.validator,
supercedes: DEFAULT_CONFIG.CONTROLBOX.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.STATE.key, {
handler: this.configState,
value: DEFAULT_CONFIG.STATE.value,
validator: DEFAULT_CONFIG.STATE.validator,
supercedes: DEFAULT_CONFIG.STATE.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.MINWIDTH.key, {
handler: this.configMinWidth,
value: DEFAULT_CONFIG.MINWIDTH.value,
validator: DEFAULT_CONFIG.MINWIDTH.validator,
supercedes: DEFAULT_CONFIG.MINWIDTH.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.MINHEIGHT.key, {
handler: this.configMinHeight,
value: DEFAULT_CONFIG.MINHEIGHT.value,
validator: DEFAULT_CONFIG.MINHEIGHT.validator,
supercedes: DEFAULT_CONFIG.MINHEIGHT.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.OVERFLOW.key, {
handler: this.configOverflow,
value: DEFAULT_CONFIG.OVERFLOW.value,
validator: DEFAULT_CONFIG.OVERFLOW.validator,
supercedes: DEFAULT_CONFIG.OVERFLOW.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.RIGHT.key, {
handler: this.configRight,
value: DEFAULT_CONFIG.RIGHT.value,
validator: DEFAULT_CONFIG.RIGHT.validator,
supercedes: DEFAULT_CONFIG.RIGHT.supercedes
});
cfg.addProperty(DEFAULT_CONFIG.BOTTOM.key, {
handler: this.configBottom,
value: DEFAULT_CONFIG.BOTTOM.value,
validator: DEFAULT_CONFIG.BOTTOM.validator,
supercedes: DEFAULT_CONFIG.BOTTOM.supercedes
});
},
configClose: function (type, args, obj) {},
configControlBox: function (type, args, obj) {
var val = args[0],
elMinimized = this.elMimimized,
elMaximized = this.elMaximized,
elNormal = this.elNormal,
elClose = this.elClose;
if (!elMinimized){
if (!m_oMinimizedIconTemplate){
m_oMinimizedIconTemplate = document.createElement("a");
m_oMinimizedIconTemplate.className = "container-minimized";
m_oMinimizedIconTemplate.href = "#";
}
elMinimized = m_oMinimizedIconTemplate.cloneNode(true);
this.innerElement.appendChild(elMinimized);
elMinimized.innerHTML = "";
E.on(elMinimized, "click", this._doMinimized, this, true);
this.elMinimized = elMinimized;
}
if (!elMaximized){
if (!m_oMaximizedIconTemplate){
m_oMaximizedIconTemplate = document.createElement("a");
m_oMaximizedIconTemplate.className = "container-maximized";
m_oMaximizedIconTemplate.href = "#";
}
elMaximized = m_oMaximizedIconTemplate.cloneNode(true);
this.innerElement.appendChild(elMaximized);
elMaximized.innerHTML = "";
E.on(elMaximized, "click", this._doMaximized, this, true);
this.elMaximized = elMaximized;
}
if (!elNormal){
if (!m_oNormalIconTemplate){
m_oNormalIconTemplate = document.createElement("a");
m_oNormalIconTemplate.className = "container-normal";
m_oNormalIconTemplate.href = "#";
}
elNormal = m_oNormalIconTemplate.cloneNode(true);
this.innerElement.appendChild(elNormal);
elNormal.innerHTML = "";
E.on(elNormal, "click", this._doMaximized, this, true);
this.elNormal = elNormal;
}
if (!elClose){
if (!m_oCloseIconTemplate){
m_oCloseIconTemplate = document.createElement("a");
m_oCloseIconTemplate.className = "container-close";
m_oCloseIconTemplate.href = "#";
}
elClose = m_oCloseIconTemplate.cloneNode(true);
this.innerElement.appendChild(elClose);
elClose.innerHTML = "";
E.on(elClose, "click", this._doClose, this, true);
this.elClose = elClose;
}
if (val == Panel.CONTROLBOX_HIDE){
elMinimized.style.display = "none";
elMaximized.style.display = "none";
elNormal.style.display = "none";
elClose.style.display = "none";
}else if (val == Panel.CONTROLBOX_CLOSE){
elMinimized.style.display = "none";
elMaximized.style.display = "none";
elNormal.style.display = "none";
elClose.style.display = "block";
} else {
elMinimized.style.display = "block";
elMaximized.style.display = "block";
elNormal.style.display = "none";
elClose.style.display = "block";
}
},
_brickFirstPanelInit: true,
_savedState: Panel.STATE_NORMAL,
_savedX: 0, _savedY: 0, _savedW: 0, _savedH: 0,
_setState: function(val){
var cfg = this.cfg,
el = this.element;
if (val == Panel.STATE_MAXIMIZED){
if (this._savedState == Panel.STATE_NORMAL){
this._savedState = val;
this._savedX = cfg.getProperty('x');
this._savedY = cfg.getProperty('y');
this._savedW = cfg.getProperty('width');
this._savedH = cfg.getProperty('height');
}
var rg = Dom.getRegion(el.parentNode);
var w = rg.width - 20;
var h = rg.height - 20;
Dom.setX(el, 0);
cfg.setProperty("xy", [0, 0]);
cfg.setProperty("width", w+'px');
cfg.setProperty("height", h+'px');
cfg.setProperty('draggable', false);
cfg.setProperty('resize', false);
}else if (val == Panel.STATE_NORMAL && this._savedState != Panel.STATE_NORMAL){
this._savedState = val;
cfg.setProperty("x", this._savedX);
cfg.setProperty("y", this._savedY);
cfg.setProperty("width", this._savedW);
cfg.setProperty("height", this._savedY);
cfg.setProperty('draggable', true);
cfg.setProperty('resize', true);
if (cfg.getProperty('fixedcenter')){
this.center();
}
}
},
configState: function (type, args, obj) {
var val = args[0],
cfg = this.cfg,
parentNode = this.element.parentNode;
this._setState(val);
if (cfg.getProperty('controlbox') == Panel.CONTROLBOX_FULL){
if (val == Panel.STATE_MAXIMIZED){
this.elMaximized.style.display = "none";
this.elNormal.style.display = "block";
}else if (val == Panel.STATE_NORMAL){
this.elMaximized.style.display = "block";
this.elNormal.style.display = "none";
}
}
},
configMinWidth: function (type, args, obj) {},
configMinHeight: function (type, args, obj) {},
_initResize: function(){
if (!YAHOO.util.Resize){
return;
}
var cfg = this.cfg;
var resizeconfig = {
minWidth: cfg.getProperty('minwidth'),
minHeight: cfg.getProperty('minheight'),
handles: ['t', 'r','b','br','l'],
autoRatio: false,
status: false,
hiddenHandles: true
};
var el = this.element;
var resize = new YAHOO.util.Resize(el, resizeconfig);
resize.on("startResize", function(args) {
if (cfg.getProperty("constraintoviewport")) {
var clientRegion = Dom.getClientRegion();
var elRegion = Dom.getRegion(el);
resize.set("maxWidth", clientRegion.right - elRegion.left - YAHOO.widget.Overlay.VIEWPORT_OFFSET);
resize.set("maxHeight", clientRegion.bottom - elRegion.top - YAHOO.widget.Overlay.VIEWPORT_OFFSET);
} else {
resize.set("maxWidth", null);
resize.set("maxHeight", null);
}
}, this, true);
resize.on("resize", function(args) {
var w = args.width,
h = args.height;
if (w > 0){
cfg.setProperty("width", args.width + "px");
}
if (h > 0){
cfg.setProperty("height", args.height + "px");
}
this.onResize();
}, this, true);
this.resizeManager = resize;
},
configResize: function (type, args, obj) {
var val = args[0],
resize = this.resizeManager,
cfg = this.cfg;
if (val){
if (!resize){
var __self = this;
setTimeout(function(){
__self._initResize();
}, 300);
}else{
resize.unlock();
}
}else if (resize){
resize.lock();
}
},
configOverflow: function(type, args, obj){
var val = args[0];
if (val){
Dom.addClass(this.body, 'overflow');
}else{
Dom.removeClass(this.body, 'overflow');
}
},
configRight: function(type, args, obj){
var val = args[0];
if (L.isNull(val)){ return; }
var cfg = this.cfg, el = this.element,
viewPortWidth = Dom.getViewportWidth(),
elWidth = el.offsetWidth,
y = cfg.getProperty("y"),
x = viewPortWidth - elWidth - val;
Dom.setX(this.element, x, true);
cfg.setProperty("xy", [x, y], true);
},
configBottom: function(type, args, obj){
var val = args[0];
if (L.isNull(val)){ return; }
var cfg = this.cfg, el = this.element,
viewPortHeight = Dom.getViewportHeight(),
elHeight = el.offsetHeight,
x = cfg.getProperty("x"),
y = viewPortHeight - elHeight - val;
Dom.setY(el, y, true);
cfg.setProperty("xy", [x, y], true);
},
_doMinimized: function(e){
E.preventDefault(e);
this.minimize();
},
_doMaximized: function(e){
E.preventDefault(e);
this.maximize();
},
_doClose: function(e){
E.preventDefault(e);
this.close();
},
minimize: function(){
this.cfg.setProperty('state', Panel.STATE_MINIMIZED);
},
maximize: function(){
var state = this._savedState == Panel.STATE_NORMAL ?
Panel.STATE_MAXIMIZED : Panel.STATE_NORMAL;
this.cfg.setProperty('state', state);
},
close: function(){
this.destroy();
},
init: function(el, config){
Panel.superclass.init.call(this, el, config);
var __self = this;
E.on(el, 'click', function(e){
var el = E.getTarget(e);
if (__self._actionBlocked && !__self._actionBlockedIgnore[el.id]){ return; }
if (__self.onClick(el)){
E.preventDefault(e);
}
});
Panel.superclass.render.call(this, config.parentNode);
this.onLoad();
setTimeout(function () {
__self.show();
__self.onShow();
}, 100);
},
_buildPanel: function(config){
var div = document.createElement('DIV');
div.id = Dom.generateId();
div.innerHTML = TM.replace('panel', {
'body': config.template || this.initTemplate()
});
return div;
},
/*
_initMenuBar: function(el, config){
var elMenuBar = Dom.get(config.menubar);
if (L.isNull(elMenuBar)){ return; }
var oMenuBar = new YAHOO.widget.MenuBar(config.menubar, {
autosubmenudisplay: true,
hidedelay: 750,
lazyload: true
});
oMenuBar.render();
this.menuBar = oMenuBar;
},*/
resizeManager: null,
destroy: function(){
/*if (!L.isNull(this.menuBar)){
this.menuBar.destroy();
}*/
if (!L.isNull(this.resizeManager)){
this.resizeManager.destroy();
}
Panel.superclass.destroy.call(this);
},
/**
* Абстрактный метод, который возвращает HTML код панели.
*
* @method initTemplate
* @return {String} HTML код панели
*/
initTemplate: function(){ return ""; },
onClick: function(el){ return false; },
/**
* Абстрактный метод, который будет вызван когда панель
* будет создана.
*
* @method onLoad
*/
onLoad: function(){},
/**
* Абстрактный метод, который будет вызван когда панель
* будет изменена в размере.
*
* @method onResize
*/
onResize: function(){},
/**
* Абстрактный метод, который будет вызван когда панель
* будет показана.
* @method onShow
*/
onShow: function(){},
/**
* Абстрактный метод, который будет вызван когда панель
* будет закрыта.
*
* @method onClose
*/
onClose: function(){},
/**
* Заблокировать элементы панели на клик, при этом, все элементы типа
* INPUT будут выставлены в disabled.
* Применяется в случаях, когда например отправляется запрос на
* сервер и ожидается ответ.
*
* @method actionDisable
* @param {String} (optional) ignore Список идентификаторов HTML элементов, указанные
* через запятую, которые будет игнорированы.
*/
actionDisable: function(ignore){
if (this._actionBlocked){ return; }
this._actionBlocked = true;
var aIgnore = (ignore || '').split(',');
var oIgnore = {};
for (var i=0;i<aIgnore.length;i++){
var id = L.trim(aIgnore[i]);
if (id != ''){
oIgnore[id] = id;
}
}
this._actionBlockedIgnore = oIgnore;
var els = {};
Dom.getElementsBy(function (el) {
if (el.id in oIgnore){ return; }
switch (el.nodeName.toUpperCase()) {
case "BUTTON": case "INPUT": case "TEXTAREA":
if (el.id == ''){
el.id = Dom.generateId();
}
var attr = (Dom.getAttribute(el, 'disabled') || '').toUpperCase();
if (attr != 'DISABLED'){
els[el.id] = el;
Dom.setAttribute(el, 'disabled', 'disabled');
}
break;
}
}, "*", this.body);
this._actionBlockedElements = els;
},
/**
* Разблокировать элементы панели на клик.
*
* @method actionEnable
*/
actionEnable: function(){
if (!this._actionBlocked){ return; }
var els = this._actionBlockedElements;
for (var n in els){
els[n]['disabled'] = '';
}
this._actionBlocked = false;
this._actionBlockedElements = null;
this._actionBlockedIgnore = {};
},
isActionDisabled: function(){
return this._actionBlocked;
}
});
Brick.widget.Panel = Panel;
/**
* Простой способ создать и отобразить панель. Достаточно в config-е
* указать необходимый шаблон + дополнительные настройки.
*
* @method showPanel
* @static
* @param {Object} config
* @return {Brick.widget.Panel}
*/
Panel.showPanel = function(config){
var panel = new Panel(config);
return panel;
};
};