sync.tabpane.js
来自「echo3 很炫的ajax框架技术 js 演示demo ajax j2ee 里」· JavaScript 代码 · 共 1,019 行 · 第 1/3 页
JS
1,019 行
Echo.Sync.Font.render(this.component.render("font"), this._headerContainerDiv);
Echo.Sync.FillImage.render(this.component.render("tabBackgroundImage"), this._headerContainerDiv);
this._div.appendChild(this._headerContainerDiv);
// Render Content Container
this._contentContainerDiv = document.createElement("div");
this._contentContainerDiv.style.position = "absolute";
this._contentContainerDiv.style.overflow = "hidden";
Echo.Sync.renderComponentDefaults(this.component, this._contentContainerDiv);
// Render Tabs
var activeTabFound = false;
var componentCount = this.component.getComponentCount();
for (var i = 0; i < componentCount; ++i) {
var child = this.component.getComponent(i);
if (this._activeTabId == child.renderId) {
activeTabFound = true;
}
var tab = new Extras.Sync.TabPane.Tab(child, this);
this._addTab(update, tab);
}
if (!activeTabFound) {
this._activeTabId = null;
if (componentCount > 0) {
this._selectTab(this.component.getComponent(0).renderId);
this._setActiveTabId(this._activeTabId);
}
}
this._configureHeaderSizeRequired = true;
if (this._borderType == Extras.TabPane.BORDER_TYPE_NONE) {
this._contentContainerDiv.style.border = "0 none";
} else if (this._borderType == Extras.TabPane.BORDER_TYPE_SURROUND) {
Echo.Sync.Border.render(this._tabActiveBorder, this._contentContainerDiv);
} else if (this._borderType == Extras.TabPane.BORDER_TYPE_PARALLEL_TO_TABS) {
Echo.Sync.Border.render(this._tabActiveBorder, this._contentContainerDiv, "borderTop");
Echo.Sync.Border.render(this._tabActiveBorder, this._contentContainerDiv, "borderBottom");
} else if (this._tabPosition == Extras.TabPane.TAB_POSITION_BOTTOM) {
Echo.Sync.Border.render(this._tabActiveBorder, this._contentContainerDiv, "borderBottom");
} else {
Echo.Sync.Border.render(this._tabActiveBorder, this._contentContainerDiv, "borderTop");
}
this._div.appendChild(this._contentContainerDiv);
parentElement.appendChild(this._div);
},
renderDisplay: function() {
var img, oversize, i;
this._tabContainerWidth = new Core.Web.Measure.Bounds(this._headerContainerDiv).width;
this._totalTabWidth = new Core.Web.Measure.Bounds(this._headerTabContainerDiv.firstChild).width;
Core.Web.VirtualPosition.redraw(this._div);
Core.Web.VirtualPosition.redraw(this._contentContainerDiv);
Core.Web.VirtualPosition.redraw(this._headerContainerDiv);
// Re-bound scroll position.
this.setScrollPosition(this.scrollPosition);
if (this._configureHeaderSizeRequired) {
this._configureHeaderSize();
var imageListener = Core.method(this, function() {
if (this.component) { // Verify component still registered.
this._configureHeaderSize();
}
});
Core.Web.Image.monitor(this._headerContainerDiv, imageListener);
} else {
// Only invoke renderDisplay on tabs if configureHeaderSize() invocation is not required,
// as configureHeaderSize() will do this work as well.
for (i = 0; i < this._tabs.length; ++i) {
this._tabs[i]._renderDisplay();
}
}
},
renderDispose: function(update) {
this._activeTabId = null;
for (var i = 0; i < this._tabs.length; i++) {
this._tabs[i]._dispose();
}
this._tabs = [];
this._div = null;
this._headerContainerDiv = null;
this._headerTabContainerDiv = null;
this._headerTabContainerTable = null;
this._headerTabContainerTr = null;
this._contentContainerDiv = null;
if (this._previousControlDiv) {
Core.Web.Event.removeAll(this._previousControlDiv);
this._previousControlDiv = null;
}
if (this._nextControlDiv) {
Core.Web.Event.removeAll(this._nextControlDiv);
this._nextControlDiv = null;
}
},
renderUpdate: function(update) {
var fullRender = false,
tab,
i;
if (update.hasUpdatedLayoutDataChildren()) {
// Layout data children updated: must full render.
fullRender = true;
}
if (!fullRender) {
if (!Core.Arrays.containsAll(Extras.Sync.TabPane._supportedPartialProperties,
update.getUpdatedPropertyNames(), true)) {
// Update contains property changes that cannot be partially re-rendered.
fullRender = true;
}
}
if (!fullRender) {
var activeTabRemoved = false;
var removedChildren = update.getRemovedChildren();
if (removedChildren) {
// Remove children.
for (i = 0; i < removedChildren.length; ++i) {
tab = this._getTabById(removedChildren[i].renderId);
if (!tab) {
continue;
}
if (tab._childComponent.renderId == this._activeTabId) {
activeTabRemoved = true;
}
this._removeTab(tab);
}
}
var addedChildren = update.getAddedChildren();
if (addedChildren) {
// Add children.
for (i = 0; i < addedChildren.length; ++i) {
tab = new Extras.Sync.TabPane.Tab(addedChildren[i], this);
this._addTab(update, tab, this.component.indexOf(addedChildren[i]));
}
}
if (update.hasUpdatedProperties()) {
// partial update
var activeTabUpdate = update.getUpdatedProperty("activeTab");
if (activeTabUpdate) {
activeTabRemoved = false;
this._selectTab(activeTabUpdate.newValue);
} else {
var activeTabIndexUpdate = update.getUpdatedProperty("activeTabIndex");
if (activeTabIndexUpdate && activeTabIndexUpdate.newValue < this.component.children.length) {
activeTabRemoved = false;
this._selectTab(this.component.children[activeTabIndexUpdate.newValue].renderId);
}
}
}
if ((activeTabRemoved || this._activeTabId == null) && this.component.children.length > 0) {
this._selectTab(this.component.children[0].renderId);
}
this._configureHeaderSizeRequired = true;
}
if (fullRender) {
var div = this._div;
var containerElement = div.parentNode;
Echo.Render.renderComponentDispose(update, update.parent);
containerElement.removeChild(div);
this.renderAdd(update, containerElement);
}
return fullRender;
},
/**
* Selects a specific tab.
*
* @param tabId {String} the id of the tab to select
*/
_selectTab: function(tabId) {
if (tabId == this._activeTabId) {
return;
}
var tab;
if (this._activeTabId) {
tab = this._getTabById(this._activeTabId);
if (tab) {
tab._renderActiveState(false);
}
}
tab = this._getTabById(tabId);
if (tab) {
this._activeTabId = tabId;
tab._renderActiveState(true);
} else {
this._activeTabId = null;
}
},
_setActiveTabId: function(activeTabId) {
this.component.set("activeTab", activeTabId);
var indexSet = false;
for (var i = 0; i < this.component.children.length; ++i) {
if (this.component.children[i].renderId == activeTabId) {
this.component.set("activeTabIndex", i);
indexSet = true;
break;
}
}
if (!indexSet) {
this.component.set("activeTabIndex", null);
}
},
_setOversizeEnabled: function(previous, enabled) {
var controlDiv = previous ? this._previousControlDiv : this._nextControlDiv,
img;
if (enabled) {
if (controlDiv) {
controlDiv.style.display = "block";
} else {
controlDiv = document.createElement("div");
controlDiv.style.cssText = "position:absolute;z-index:2;cursor:pointer;";
controlDiv.style[this._tabPosition === Extras.TabPane.TAB_POSITION_BOTTOM ? "bottom" : "top"] = "5px";
controlDiv.style[previous ? "left" : "right"] = "2px";
img = document.createElement("img");
controlDiv.appendChild(img);
Core.Web.Event.add(controlDiv, "mousedown", Core.method(this, this._processScrollStart));
Core.Web.Event.add(controlDiv, "mouseup", Core.method(this, this._processScrollStop));
Core.Web.Event.Selection.disable(controlDiv);
if (previous) {
img.src = this._icons.previous ? this._icons.previous :
this.client.getResourceUrl("Extras", "image/tabpane/Previous.gif");
img.alt = "<";
this._previousControlDiv = controlDiv;
} else {
img.src = this._icons.next ? this._icons.next :
this.client.getResourceUrl("Extras", "image/tabpane/Next.gif");
img.alt = ">";
this._nextControlDiv = controlDiv;
}
this._div.appendChild(controlDiv);
}
} else if (controlDiv) {
controlDiv.style.display = "none";
}
},
setScrollPosition: function(position) {
var bounded = false,
oversize = this._totalTabWidth > this._tabContainerWidth;
if (position < 0) {
position = 0;
bounded = true;
} else if (position > 0 && position > this._totalTabWidth - this._tabContainerWidth) {
position = this._totalTabWidth - this._tabContainerWidth;
bounded = true;
}
this.scrollPosition = position;
this._headerTabContainerDiv.style.marginLeft = (0 - position) + "px";
if (oversize) {
this._setOversizeEnabled(true, position > 0);
this._setOversizeEnabled(false, position < this._totalTabWidth - this._tabContainerWidth);
} else {
this._setOversizeEnabled(true, false);
this._setOversizeEnabled(false, false);
}
return !bounded;
}
});
/**
* Representation of a single tab (child component) within the tab pane.
* Provides tab-specific rendering functionality, handles setting active state
* on/off for an individual tab.
*/
Extras.Sync.TabPane.Tab = Core.extend({
$construct: function(childComponent, parent) {
// state
this._childComponent = childComponent;
this._parent = parent;
this._rendered = false;
if (parent._tabCloseEnabled) {
var layoutData = this._childComponent.render("layoutData");
this._tabCloseEnabled = layoutData ? layoutData.closeEnabled : false;
} else {
this._tabCloseEnabled = false;
}
// elements
this._headerTd = null;
this._headerContentTable = null;
this._contentDiv = null;
this._leftTd = null;
this._centerTd = null;
this._rightTd = null;
this._closeImageTd = null;
},
_addEventListeners: function() {
Core.Web.Event.add(this._headerTd, "click", Core.method(this, this._processClick), false);
Core.Web.Event.Selection.disable(this._headerTd);
if (this._tabCloseEnabled) {
Core.Web.Event.add(this._headerTd, "mouseover", Core.method(this, this._processEnter), false);
Core.Web.Event.add(this._headerTd, "mouseout", Core.method(this, this._processExit), false);
}
},
_dispose: function() {
Core.Web.Event.removeAll(this._headerTd);
this._parent = null;
this._childComponent = null;
this._headerTd = null;
this._headerContentTable = null;
this._contentDiv = null;
this._leftTd = null;
this._centerTd = null;
this._rightTd = null;
this._closeImageTd = null;
},
_getCloseImage: function(rollover) {
var icons = this._parent._icons;
var icon;
if (this._tabCloseEnabled) {
if (rollover && this._parent.component.render("tabCloseIconRolloverEnabled")) {
icon = icons.rolloverIcon;
}
} else {
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?