You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
2944 lines
113 KiB
2944 lines
113 KiB
/** |
|
* 布局 |
|
* |
|
* Created by GUY on 2016/2/23. |
|
* @class BI.Arrangement |
|
* @extends BI.Widget |
|
*/ |
|
BI.Arrangement = BI.inherit(BI.Widget, { |
|
|
|
_defaultConfig: function () { |
|
return BI.extend(BI.Arrangement.superclass._defaultConfig.apply(this, arguments), { |
|
baseCls: "bi-arrangement", |
|
layoutType: BI.Arrangement.LAYOUT_TYPE.FREE, |
|
isNeedReLayout: true, |
|
items: [] |
|
}); |
|
}, |
|
|
|
_init: function () { |
|
BI.Arrangement.superclass._init.apply(this, arguments); |
|
var self = this, o = this.options; |
|
this.arrangement = BI.createWidget({ |
|
type: "bi.arrangement_droppable", |
|
cls: "arrangement-block", |
|
invisible: true |
|
}); |
|
this.block = BI.createWidget({ |
|
type: "bi.arrangement_block", |
|
invisible: true |
|
}); |
|
this.droppable = BI.createWidget({ |
|
type: "bi.layout", |
|
cls: "arrangement-drop-container", |
|
invisible: true |
|
}); |
|
this.container = BI.createWidget({ |
|
type: "bi.absolute", |
|
items: o.items.concat([this.block, this.arrangement, { |
|
el: this.droppable, |
|
left: 0, |
|
right: 0, |
|
top: 0, |
|
bottom: 0 |
|
}]) |
|
}); |
|
|
|
this.scrollContainer = BI.createWidget({ |
|
type: "bi.adaptive", |
|
width: "100%", |
|
height: "100%", |
|
scrollable: true, |
|
items: [this.container] |
|
}); |
|
this.scrollContainer.element.scroll(function () { |
|
self.fireEvent(BI.Arrangement.EVENT_SCROLL, { |
|
scrollLeft: self.scrollContainer.element.scrollLeft(), |
|
scrollTop: self.scrollContainer.element.scrollTop(), |
|
clientWidth: self.scrollContainer.element[0].clientWidth, |
|
clientHeight: self.scrollContainer.element[0].clientHeight |
|
}); |
|
}); |
|
|
|
BI.createWidget({ |
|
type: "bi.adaptive", |
|
element: this, |
|
items: [this.scrollContainer] |
|
}); |
|
this.regions = {}; |
|
this.locations = {}; |
|
this.drops = {}; |
|
this.storeDrops = {}; |
|
if (o.items.length > 0) { |
|
BI.nextTick(function () { |
|
self.populate(o.items); |
|
}); |
|
} |
|
}, |
|
|
|
////初始化操作//// |
|
_calculateRegions: function (items) { |
|
var self = this, o = this.options; |
|
this.regions = {}; |
|
this.drops = {}; |
|
BI.each(items, function (i, item) { |
|
var region = self._createOneRegion(item); |
|
self.regions[region.id] = region; |
|
var drop = self._createOneDrop(region); |
|
self.drops[drop.id] = drop; |
|
self.storeDrops[drop.id] = drop; |
|
}); |
|
}, |
|
|
|
//定方位 |
|
_locationRegion: function () { |
|
var self = this, o = this.options; |
|
this.locations = {}; |
|
var reg = []; |
|
BI.each(this.regions, function (id, region) { |
|
var t = new BI.Region(region.left, region.top, region.width, region.height); |
|
t.id = id; |
|
reg.push(t); |
|
self.locations[id] = {top: [], left: [], right: [], bottom: []}; |
|
}); |
|
BI.each(reg, function (i, dim) { |
|
var topRegion = new BI.Region(dim.x, 0, dim.w, dim.y), |
|
bottomRegion = new BI.Region(dim.x, dim.y + dim.h, dim.w, BI.MAX), |
|
leftRegion = new BI.Region(0, dim.y, dim.x, dim.h), |
|
rightRegion = new BI.Region(dim.x + dim.w, dim.y, BI.MAX, dim.h); |
|
BI.each(reg, function (j, tar) { |
|
if (i !== j) { |
|
if (tar.isIntersects(topRegion) && self._isLessThanEqual(tar.y + tar.h, dim.y)) { |
|
self.locations[dim.id].top.push(self.regions[tar.id]); |
|
} |
|
if (tar.isIntersects(bottomRegion) && self._isMoreThanEqual(tar.y, dim.y + dim.h)) { |
|
self.locations[dim.id].bottom.push(self.regions[tar.id]); |
|
} |
|
if (tar.isIntersects(leftRegion) && self._isLessThanEqual(tar.x + tar.w, dim.x)) { |
|
self.locations[dim.id].left.push(self.regions[tar.id]); |
|
} |
|
if (tar.isIntersects(rightRegion) && self._isMoreThanEqual(tar.x, dim.x + dim.w)) { |
|
self.locations[dim.id].right.push(self.regions[tar.id]); |
|
} |
|
} |
|
}); |
|
}); |
|
}, |
|
|
|
_isEqual: function (num1, num2) { |
|
return Math.abs(num1 - num2) < 2; |
|
}, |
|
|
|
_isLessThan: function (num1, num2) { |
|
return num1 < num2 && !this._isEqual(num1, num2); |
|
}, |
|
|
|
_isMoreThan: function (num1, num2) { |
|
return num1 > num2 && !this._isEqual(num1, num2); |
|
}, |
|
|
|
_isLessThanEqual: function (num1, num2) { |
|
return num1 <= num2 || this._isEqual(num1, num2); |
|
}, |
|
|
|
_isMoreThanEqual: function (num1, num2) { |
|
return num1 >= num2 || this._isEqual(num1, num2); |
|
}, |
|
|
|
////方法//// |
|
_isPositionInBounds: function (position, bound) { |
|
var region = new BI.Region(bound.left, bound.top, bound.width, bound.height); |
|
return region.isPointInside(position.left, position.top); |
|
}, |
|
|
|
//获取某区域等量相关联的区域 |
|
_getEquivalentRelativeRegions: function (name, direction) { |
|
var self = this; |
|
direction || (direction = ["top", "bottom", "left", "right"]); |
|
var result = []; |
|
var target = this.regions[name]; |
|
var tops = this.locations[name].top; |
|
var bottoms = this.locations[name].bottom; |
|
var lefts = this.locations[name].left; |
|
var rights = this.locations[name].right; |
|
var finded = direction.contains("top") && BI.some(tops, function (i, region) { |
|
if (self._isEqual(region.top + region.height, target.top) && self._isEqual(region.left, target.left) && self._isEqual(region.width, target.width)) { |
|
var clone = BI.clone(region); |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
return true; |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("bottom") && BI.some(bottoms, function (i, region) { |
|
if (self._isEqual(target.top + target.height, region.top) && self._isEqual(region.left, target.left) && self._isEqual(region.width, target.width)) { |
|
var clone = BI.clone(region); |
|
clone.top = region.top - target.height; |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
return true; |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("left") && BI.some(lefts, function (i, region) { |
|
if (self._isEqual(region.left + region.width, target.left) && self._isEqual(region.top, target.top) && self._isEqual(region.height, target.height)) { |
|
var clone = BI.clone(region); |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
return true; |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("right") && BI.some(rights, function (i, region) { |
|
if (self._isEqual(target.left + target.width, region.left) && self._isEqual(region.top, target.top) && self._isEqual(region.height, target.height)) { |
|
var clone = BI.clone(region); |
|
clone.left = region.left - target.width; |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
return true; |
|
} |
|
}); |
|
if (!finded) { |
|
var findTopRegions = [], findBottomRegions = []; |
|
direction.contains("top") && BI.each(tops, function (i, region) { |
|
if (self._isEqual(region.top + region.height, target.top) |
|
&& self._isMoreThanEqual(region.left, target.left) |
|
&& self._isLessThanEqual(region.left + region.width, target.left + target.width)) { |
|
findTopRegions.push(region); |
|
} |
|
}); |
|
direction.contains("bottom") && BI.each(bottoms, function (i, region) { |
|
if (self._isEqual(target.top + target.height, region.top) |
|
&& self._isMoreThanEqual(region.left, target.left) |
|
&& self._isLessThanEqual(region.left + region.width, target.left + target.width)) { |
|
findBottomRegions.push(region); |
|
} |
|
}); |
|
var topValid = isRegionsValid(findTopRegions, "top"), bottomValid = isRegionsValid(findBottomRegions, "bottom"); |
|
if (topValid && bottomValid) { |
|
BI.each(findTopRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.height = region.height + target.height / 2; |
|
result.push(clone); |
|
}); |
|
BI.each(findBottomRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.top = region.top - target.height / 2; |
|
clone.height = region.height + target.height / 2; |
|
result.push(clone); |
|
}); |
|
} else if (topValid) { |
|
BI.each(findTopRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
}); |
|
} else if (bottomValid) { |
|
BI.each(findBottomRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.top = region.top - target.height; |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
}); |
|
} |
|
if (!topValid && !bottomValid) { |
|
var findLeftRegions = [], findRightRegions = []; |
|
direction.contains("left") && BI.each(lefts, function (i, region) { |
|
if (self._isEqual(region.left + region.width, target.left) |
|
&& self._isMoreThanEqual(region.top, target.top) |
|
&& self._isLessThanEqual(region.top + region.height, target.top + target.height)) { |
|
findLeftRegions.push(region); |
|
} |
|
}); |
|
direction.contains("right") && BI.each(rights, function (i, region) { |
|
if (self._isEqual(target.left + target.width, region.left) |
|
&& self._isMoreThanEqual(region.top, target.top) |
|
&& self._isLessThanEqual(region.top + region.height, target.top + target.height)) { |
|
findRightRegions.push(region); |
|
} |
|
}); |
|
var leftValid = isRegionsValid(findLeftRegions, "left"), rightValid = isRegionsValid(findRightRegions, "right"); |
|
if (leftValid && rightValid) { |
|
BI.each(findLeftRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.width = region.width + target.width / 2; |
|
result.push(clone); |
|
}); |
|
BI.each(findRightRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.left = region.left - target.width / 2; |
|
clone.width = region.width + target.width / 2; |
|
result.push(clone); |
|
}); |
|
} else if (leftValid) { |
|
BI.each(findLeftRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
}); |
|
} else if (rightValid) { |
|
BI.each(findRightRegions, function (i, region) { |
|
var clone = BI.clone(region); |
|
clone.left = region.left - target.width; |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
}); |
|
} |
|
|
|
//上下左右都不可行 |
|
if (!leftValid && !rightValid) { |
|
|
|
} |
|
} |
|
} |
|
} |
|
} |
|
} |
|
return result; |
|
function isRegionsValid(regions, dir) { |
|
var occupied = self._getRegionOccupied(regions); |
|
switch (dir) { |
|
case "top": |
|
case "bottom": |
|
return self._isEqual(occupied.left, target.left) && self._isEqual(occupied.width, target.width); |
|
case "left": |
|
case "right": |
|
return self._isEqual(occupied.top, target.top) && self._isEqual(occupied.height, target.height); |
|
} |
|
return false; |
|
} |
|
}, |
|
|
|
//获取某区域直接相关联的区域 |
|
_getDirectRelativeRegions: function (name, direction) { |
|
var self = this; |
|
direction || (direction = ["top", "bottom", "left", "right"]); |
|
var result = []; |
|
var target = this.regions[name]; |
|
var tops = this.locations[name].top; |
|
var bottoms = this.locations[name].bottom; |
|
var lefts = this.locations[name].left; |
|
var rights = this.locations[name].right; |
|
var finded = direction.contains("top") && BI.some(tops, function (i, region) { |
|
if (self._isEqual(region.top + region.height, target.top) |
|
&& ((self._isMoreThanEqual(region.left, target.left) && self._isLessThan(region.left, target.left + target.width)) |
|
|| (self._isMoreThan(region.left + region.width, target.left) && self._isLessThanEqual(region.left + region.width, target.left + target.width)) |
|
|| (self._isLessThan(region.left, target.left) && self._isMoreThan(region.left + region.width, target.left + target.width)))) { |
|
var clone = BI.clone(region); |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("bottom") && BI.some(bottoms, function (i, region) { |
|
if (self._isEqual(target.top + target.height, region.top) |
|
&& ((self._isMoreThanEqual(region.left, target.left) && self._isLessThan(region.left, target.left + target.width)) |
|
|| (self._isMoreThan(region.left + region.width, target.left) && self._isLessThanEqual(region.left + region.width, target.left + target.width)) |
|
|| (self._isLessThan(region.left, target.left) && self._isMoreThan(region.left + region.width, target.left + target.width)))) { |
|
var clone = BI.clone(region); |
|
clone.top = region.top - target.height; |
|
clone.height = region.height + target.height; |
|
result.push(clone); |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("left") && BI.some(lefts, function (i, region) { |
|
if (self._isEqual(region.left + region.width, target.left) |
|
&& ((self._isMoreThanEqual(region.top, target.top) && self._isLessThan(region.top, target.top + target.height)) |
|
|| (self._isMoreThan(region.top + region.height, target.top) && self._isLessThanEqual(region.top + region.height, target.top + target.height)) |
|
|| (self._isLessThan(region.top, target.top) && self._isMoreThan(region.top + region.height, target.top + target.height)))) { |
|
var clone = BI.clone(region); |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
} |
|
}); |
|
if (!finded) { |
|
finded = direction.contains("right") && BI.some(rights, function (i, region) { |
|
if (self._isEqual(target.left + target.width, region.left) |
|
&& ((self._isMoreThanEqual(region.top, target.top) && self._isLessThan(region.top, target.top + target.height)) |
|
|| (self._isMoreThan(region.top + region.height, target.top) && self._isLessThanEqual(region.top + region.height, target.top + target.height)) |
|
|| (self._isLessThan(region.top, target.top) && self._isMoreThan(region.top + region.height, target.top + target.height)))) { |
|
var clone = BI.clone(region); |
|
clone.left = region.left - target.width; |
|
clone.width = region.width + target.width; |
|
result.push(clone); |
|
} |
|
}); |
|
} |
|
} |
|
} |
|
return result; |
|
}, |
|
|
|
//获取间接相关联的区域,即调整name区域后需要附带调整的所有相关区域(包括自身) |
|
_getInDirectRelativeRegions: function (name, direction) { |
|
var self = this, dict = ["top", "left", "right", "bottom"]; |
|
var result = {}; |
|
direction || (direction = dict); |
|
function recursion(regions, dir, store, cache) { |
|
BI.each(regions, function (i, region) { |
|
if (cache[region.id]) { |
|
return; |
|
} |
|
cache[region.id] = true; |
|
if (!store[dict[3 - dir]]) { |
|
store[dict[3 - dir]] = []; |
|
} |
|
store[dict[3 - dir]].push(region); |
|
recursion(self._getDirectRelativeRegions(region.id, [dict[dir]]), 3 - dir, store, cache); |
|
}) |
|
} |
|
|
|
if (direction.contains("top")) { |
|
var store = {}, cache = {}; |
|
recursion([this.regions[name]], dict.indexOf("top"), store, cache); |
|
store["top"] = BI.sortBy(store["top"], "left"); |
|
store["bottom"] = BI.sortBy(store["bottom"], "left"); |
|
result["top"] = store; |
|
} |
|
if (direction.contains("bottom")) { |
|
var store = {}, cache = {}; |
|
recursion([this.regions[name]], dict.indexOf("bottom"), store, cache); |
|
store["top"] = BI.sortBy(store["top"], "left"); |
|
store["bottom"] = BI.sortBy(store["bottom"], "left"); |
|
result["bottom"] = store; |
|
} |
|
if (direction.contains("left")) { |
|
var store = {}, cache = {}; |
|
recursion([this.regions[name]], dict.indexOf("left"), store, cache); |
|
store["left"] = BI.sortBy(store["left"], "top"); |
|
store["right"] = BI.sortBy(store["right"], "top"); |
|
result["left"] = store; |
|
} |
|
if (direction.contains("right")) { |
|
var store = {}, cache = {}; |
|
recursion([this.regions[name]], dict.indexOf("right"), store, cache); |
|
store["left"] = BI.sortBy(store["left"], "top"); |
|
store["right"] = BI.sortBy(store["right"], "top"); |
|
result["right"] = store; |
|
} |
|
return result; |
|
}, |
|
|
|
_getLeftAlignRegions: function (name) { |
|
var self = this; |
|
var tops = this._getDirectRelativeRegions(name, ["top"]); |
|
var bottoms = this._getDirectRelativeRegions(name, ["bottom"]); |
|
var current = this.regions[name]; |
|
var rtop = [], rbottom = []; |
|
BI.each(tops, function (i, region) { |
|
if (self._isEqual(region.left, current.left)) { |
|
rtop.push(region); |
|
} |
|
}); |
|
BI.each(bottoms, function (i, region) { |
|
if (self._isEqual(region.left, current.left)) { |
|
rbottom.push(region); |
|
} |
|
}); |
|
return { |
|
top: rtop, |
|
bottom: rbottom |
|
} |
|
}, |
|
|
|
_getRightAlignRegions: function (name) { |
|
var self = this; |
|
var tops = this._getDirectRelativeRegions(name, ["top"]); |
|
var bottoms = this._getDirectRelativeRegions(name, ["bottom"]); |
|
var current = this.regions[name]; |
|
var rtop = [], rbottom = []; |
|
BI.each(tops, function (i, region) { |
|
if (self._isEqual(region.left + region.width, current.left + current.width)) { |
|
rtop.push(region); |
|
} |
|
}); |
|
BI.each(bottoms, function (i, region) { |
|
if (self._isEqual(region.left + region.width, current.left + current.width)) { |
|
rbottom.push(region); |
|
} |
|
}); |
|
return { |
|
top: rtop, |
|
bottom: rbottom |
|
} |
|
}, |
|
|
|
_getTopAlignRegions: function (name) { |
|
var self = this; |
|
var lefts = this._getDirectRelativeRegions(name, ["left"]); |
|
var rights = this._getDirectRelativeRegions(name, ["right"]); |
|
var current = this.regions[name]; |
|
var rleft = [], rright = []; |
|
BI.each(lefts, function (i, region) { |
|
if (self._isEqual(region.top, current.top)) { |
|
rleft.push(region); |
|
} |
|
}); |
|
BI.each(rights, function (i, region) { |
|
if (self._isEqual(region.top, current.top)) { |
|
rright.push(region); |
|
} |
|
}); |
|
return { |
|
left: rleft, |
|
right: rright |
|
} |
|
}, |
|
|
|
_getBottomAlignRegions: function (name) { |
|
var self = this; |
|
var lefts = this._getDirectRelativeRegions(name, ["left"]); |
|
var rights = this._getDirectRelativeRegions(name, ["right"]); |
|
var current = this.regions[name]; |
|
var rleft = [], rright = []; |
|
BI.each(lefts, function (i, region) { |
|
if (self._isEqual(region.top + region.height, current.top + current.height)) { |
|
rleft.push(region); |
|
} |
|
}); |
|
BI.each(rights, function (i, region) { |
|
if (self._isEqual(region.top + region.height, current.top + current.height)) { |
|
rright.push(region); |
|
} |
|
}); |
|
return { |
|
left: rleft, |
|
right: rright |
|
} |
|
}, |
|
|
|
//获取占有的最大Region |
|
_getRegionOccupied: function (regions) { |
|
var self = this, o = this.options; |
|
if (BI.size(regions || this.regions) <= 0) { |
|
return { |
|
left: 0, |
|
top: 0, |
|
width: 0, |
|
height: 0 |
|
} |
|
} |
|
var minLeft = BI.MAX, maxLeft = BI.MIN, minTop = BI.MAX, maxTop = BI.MIN; |
|
BI.each(regions || this.regions, function (id, region) { |
|
minLeft = Math.min(minLeft, region.left); |
|
maxLeft = Math.max(maxLeft, region.left + region.width); |
|
minTop = Math.min(minTop, region.top); |
|
maxTop = Math.max(maxTop, region.top + region.height); |
|
}); |
|
return { |
|
left: minLeft, |
|
top: minTop, |
|
width: maxLeft - minLeft, |
|
height: maxTop - minTop |
|
} |
|
}, |
|
|
|
//两个区域的交叉面积 |
|
_getCrossArea: function (region1, region2) { |
|
if (region1.left <= region2.left) { |
|
if (region1.top <= region2.top) { |
|
if (region1.top + region1.height > region2.top && region1.left + region1.width > region2.left) { |
|
if (this._isEqual(region1.top + region1.height, region2.top) || this._isEqual(region1.left + region1.width, region2.left)) { |
|
return 0; |
|
} |
|
return (region1.top + region1.height - region2.top) * (region1.left + region1.width - region2.left); |
|
} |
|
} else { |
|
if (region2.top + region2.height > region1.top && region1.left + region1.width > region2.left) { |
|
if (this._isEqual(region2.top + region2.height, region1.top) || this._isEqual(region1.left + region1.width, region2.left)) { |
|
return 0; |
|
} |
|
return (region2.top + region2.height - region1.top) * (region1.left + region1.width - region2.left); |
|
} |
|
} |
|
} else { |
|
if (region1.top <= region2.top) { |
|
if (region1.top + region1.height > region2.top && region2.left + region2.width > region1.left) { |
|
if (this._isEqual(region1.top + region1.height, region2.top) || this._isEqual(region2.left + region2.width, region1.left)) { |
|
return 0; |
|
} |
|
return (region1.top + region1.height - region2.top) * (region2.left + region2.width - region1.left); |
|
} |
|
} else { |
|
if (region2.top + region2.height > region1.top && region2.left + region2.width > region1.left) { |
|
if (this._isEqual(region2.top + region2.height, region1.top) || this._isEqual(region2.left + region2.width, region1.left)) { |
|
return 0; |
|
} |
|
return (region2.top + region2.height - region1.top) * (region2.left + region2.width - region1.left); |
|
} |
|
} |
|
} |
|
return 0; |
|
}, |
|
|
|
//是否有覆盖的组件 |
|
_isRegionOverlay: function (regions) { |
|
var reg = []; |
|
BI.each(regions || this.regions, function (id, region) { |
|
reg.push(new BI.Region(region.left, region.top, region.width, region.height)); |
|
}); |
|
for (var i = 0, len = reg.length; i < len; i++) { |
|
for (var j = i + 1; j < len; j++) { |
|
var area1 = { |
|
left: reg[i].x, |
|
top: reg[i].y, |
|
width: reg[i].w, |
|
height: reg[i].h |
|
}; |
|
var area2 = { |
|
left: reg[j].x, |
|
top: reg[j].y, |
|
width: reg[j].w, |
|
height: reg[j].h |
|
}; |
|
if (reg[i].isIntersects(reg[j]) && this._getCrossArea(area1, area2) > 1) { |
|
return true; |
|
} |
|
} |
|
} |
|
return false; |
|
}, |
|
|
|
//布局是否是优良的 |
|
_isArrangeFine: function (regions) { |
|
switch (this.options.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (this._isRegionOverlay()) { |
|
return false; |
|
} |
|
var maxRegion = this._getRegionOccupied(regions); |
|
var area = maxRegion.width * maxRegion.height; |
|
var all = 0; |
|
BI.each(regions || this.regions, function (id, region) { |
|
all += region.width * region.height; |
|
}); |
|
return Math.abs(area - all) < 8; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
return true; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
if (this._isRegionOverlay()) { |
|
return false; |
|
} |
|
} |
|
return true; |
|
}, |
|
|
|
_getRegionNames: function (regions) { |
|
var names = []; |
|
BI.each(regions || this.regions, function (i, region) { |
|
names.push(region.id || region.attr("id")); |
|
}); |
|
return names; |
|
}, |
|
|
|
_getRegionsByNames: function (names, regions) { |
|
names = BI.isArray(names) ? names : [names]; |
|
regions = regions || this.regions; |
|
if (BI.isArray(regions)) { |
|
var result = []; |
|
BI.each(regions, function (i, region) { |
|
if (names.contains(region.id || region.attr("id"))) { |
|
result.push(region); |
|
} |
|
}); |
|
} else { |
|
var result = {}; |
|
BI.each(names, function (i, name) { |
|
result[name] = regions[name]; |
|
}); |
|
} |
|
return result; |
|
}, |
|
|
|
_cloneRegion: function (regions) { |
|
var clone = {}; |
|
BI.each(regions || this.regions, function (id, region) { |
|
clone[id] = {}; |
|
clone[id].el = region.el; |
|
clone[id].id = region.id; |
|
clone[id].left = region.left; |
|
clone[id].top = region.top; |
|
clone[id].width = region.width; |
|
clone[id].height = region.height; |
|
}); |
|
return clone; |
|
}, |
|
|
|
//测试合法性 |
|
_test: function (regions) { |
|
var self = this; |
|
return !BI.any(regions || this.regions, function (i, region) { |
|
if (BI.isNaN(region.width) || BI.isNaN(region.height) || region.width <= 21 || region.height <= 21) { |
|
return true; |
|
} |
|
}) |
|
}, |
|
|
|
//对区域进行划分 |
|
_splitRegions: function (name) { |
|
var result = []; |
|
var tid = BI.UUID(); |
|
var _left = this._getLeftAlignRegions(name); |
|
var _right = this._getRightAlignRegions(name); |
|
var _top = this._getTopAlignRegions(name); |
|
var _bottom = this._getBottomAlignRegions(name); |
|
if (_left.top.length > 0) { |
|
var upid = _left.top[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].width, clone[upid].width) / 2;//两个组件中较小宽度的一半 |
|
var left = (clone[name].left + clone[upid].left) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
left: left, |
|
top: clone[upid].top, |
|
width: split, |
|
height: clone[name].height + clone[upid].height |
|
}; |
|
BI.extend(clone[name], { |
|
left: left + split, |
|
width: clone[name].width - split - (left - clone[name].left) |
|
}); |
|
BI.extend(clone[upid], { |
|
left: left + split, |
|
width: clone[upid].width - split - (left - clone[upid].left) |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "left-top", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_left.bottom.length > 0) { |
|
var bottomid = _left.bottom[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].width, clone[bottomid].width) / 2; |
|
var left = (clone[name].left + clone[bottomid].left) / 2; |
|
var insert = clone[tid] = {//新增的区域 |
|
left: left, |
|
top: clone[name].top, |
|
width: split, |
|
height: clone[name].height + clone[bottomid].height |
|
}; |
|
BI.extend(clone[name], { |
|
left: left + split, |
|
width: clone[name].width - split - (left - clone[name].left) |
|
}); |
|
BI.extend(clone[bottomid], { |
|
left: left + split, |
|
width: clone[bottomid].width - split - (left - clone[bottomid].left) |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-left", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_right.top.length > 0) { |
|
var upid = _right.top[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].width, clone[upid].width) / 2;//两个组件中较小宽度的一半 |
|
var right = (clone[name].left + clone[name].width + clone[upid].left + clone[upid].width) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
left: right - split, |
|
top: clone[upid].top, |
|
width: split, |
|
height: clone[name].height + clone[upid].height |
|
}; |
|
BI.extend(clone[name], { |
|
width: right - clone[name].left - split |
|
}); |
|
BI.extend(clone[upid], { |
|
width: right - clone[upid].left - split |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top-right", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_right.bottom.length > 0) { |
|
var bottomid = _right.bottom[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].width, clone[bottomid].width) / 2;//两个组件中较小宽度的一半 |
|
var right = (clone[name].left + clone[name].width + clone[bottomid].left + clone[bottomid].width) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
left: right - split, |
|
top: clone[name].top, |
|
width: split, |
|
height: clone[name].height + clone[bottomid].height |
|
}; |
|
BI.extend(clone[name], { |
|
width: right - clone[name].left - split |
|
}); |
|
BI.extend(clone[bottomid], { |
|
width: right - clone[bottomid].left - split |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-right", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_top.left.length > 0) { |
|
var leftid = _top.left[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].height, clone[leftid].height) / 2;//两个组件中较小高度的一半 |
|
var top = (clone[name].top + clone[leftid].top) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
top: top, |
|
left: clone[leftid].left, |
|
height: split, |
|
width: clone[name].width + clone[leftid].width |
|
}; |
|
BI.extend(clone[name], { |
|
top: top + split, |
|
height: clone[name].height - split - (top - clone[name].top) |
|
}); |
|
BI.extend(clone[leftid], { |
|
top: top + split, |
|
height: clone[leftid].height - split - (top - clone[leftid].top) |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top-left", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_top.right.length > 0) { |
|
var rightid = _top.right[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].height, clone[rightid].height) / 2;//两个组件中较小高度的一半 |
|
var top = (clone[name].top + clone[rightid].top) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
top: top, |
|
left: clone[name].left, |
|
height: split, |
|
width: clone[name].width + clone[rightid].width |
|
}; |
|
BI.extend(clone[name], { |
|
top: top + split, |
|
height: clone[name].height - split - (top - clone[name].top) |
|
}); |
|
BI.extend(clone[rightid], { |
|
top: top + split, |
|
height: clone[rightid].height - split - (top - clone[rightid].top) |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top-right-second", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_bottom.left.length > 0) { |
|
var leftid = _bottom.left[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].height, clone[leftid].height) / 2;//两个组件中较小高度的一半 |
|
var bottom = (clone[name].top + clone[name].height + clone[leftid].top + clone[leftid].height) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
left: clone[leftid].left, |
|
top: bottom - split, |
|
height: split, |
|
width: clone[name].width + clone[leftid].width |
|
}; |
|
BI.extend(clone[name], { |
|
height: bottom - clone[name].top - split |
|
}); |
|
BI.extend(clone[leftid], { |
|
height: bottom - clone[leftid].top - split |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-left-second", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
if (_bottom.right.length > 0) { |
|
var rightid = _bottom.right[0].id; |
|
var tid = BI.UUID(); |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var split = Math.min(clone[name].height, clone[rightid].height) / 2;//两个组件中较小高度的一半 |
|
var bottom = (clone[name].top + clone[name].height + clone[rightid].top + clone[rightid].height) / 2;//求平均,减少误差 |
|
var insert = clone[tid] = {//新增的区域 |
|
left: clone[name].left, |
|
top: bottom - split, |
|
height: split, |
|
width: clone[name].width + clone[rightid].width |
|
}; |
|
BI.extend(clone[name], { |
|
height: bottom - clone[name].top - split |
|
}); |
|
BI.extend(clone[rightid], { |
|
height: bottom - clone[rightid].top - split |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-right-second", |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} |
|
} |
|
//有上方居中drop |
|
var lefts = _top.left, rights = _top.right; |
|
if (lefts.length > 0 && rights.length > 0) { |
|
var count = 0; |
|
var store = [this.regions[name]]; |
|
while (lefts.length > 0 || rights.length > 0) { |
|
var clone = this._cloneRegion(); |
|
if (lefts.length > 0) { |
|
store.push(this.regions[lefts[0].id]); |
|
} |
|
if (rights.length > 0) { |
|
store.push(this.regions[rights[0].id]); |
|
} |
|
count++; |
|
var top = BI.average(store, function (i, r) {//求平均,减少误差 |
|
return r.top; |
|
}); |
|
var occupied = this._getRegionOccupied(store); |
|
|
|
var split = BI.min(store, function (i, r) { |
|
return r.height; |
|
}).height / 2; |
|
var insert = clone[tid] = { |
|
left: occupied.left, |
|
width: occupied.width, |
|
top: top, |
|
height: split |
|
}; |
|
BI.each(store, function (i, region) { |
|
BI.extend(clone[region.id], { |
|
top: top + split, |
|
height: region.height - split - (top - region.top) |
|
}); |
|
}); |
|
if (this._test(store)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top-center" + count, |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} else { |
|
break; |
|
} |
|
|
|
if (lefts.length > 0) { |
|
lefts = this._getTopAlignRegions(lefts[0].id).left; |
|
} |
|
if (rights.length > 0) { |
|
rights = this._getTopAlignRegions(rights[0].id).right; |
|
} |
|
} |
|
} |
|
//有下方居中drop |
|
var lefts = _bottom.left, rights = _bottom.right; |
|
if (lefts.length > 0 && rights.length > 0) { |
|
var count = 0; |
|
var store = [this.regions[name]]; |
|
while (lefts.length > 0 || rights.length > 0) { |
|
var clone = this._cloneRegion(); |
|
if (lefts.length > 0) { |
|
store.push(this.regions[lefts[0].id]); |
|
} |
|
if (rights.length > 0) { |
|
store.push(this.regions[rights[0].id]); |
|
} |
|
count++; |
|
var bottom = BI.average(store, function (i, r) {//求平均,减少误差 |
|
return r.top + r.height; |
|
}); |
|
var occupied = this._getRegionOccupied(store); |
|
|
|
var split = BI.min(store, function (i, r) { |
|
return r.height; |
|
}).height / 2; |
|
var insert = clone[tid] = { |
|
left: occupied.left, |
|
width: occupied.width, |
|
top: bottom - split, |
|
height: split |
|
}; |
|
BI.each(store, function (i, region) { |
|
BI.extend(clone[region.id], { |
|
height: bottom - region.top - split |
|
}); |
|
}); |
|
if (this._test(store)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-center" + count, |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} else { |
|
break; |
|
} |
|
|
|
if (lefts.length > 0) { |
|
lefts = this._getBottomAlignRegions(lefts[0].id).left; |
|
} |
|
if (rights.length > 0) { |
|
rights = this._getBottomAlignRegions(rights[0].id).right; |
|
} |
|
} |
|
} |
|
//有左方居中drop |
|
var tops = _left.top, bottoms = _left.bottom; |
|
if (tops.length > 0 && bottoms.length > 0) { |
|
var count = 0; |
|
var store = [this.regions[name]]; |
|
while (tops.length > 0 || bottoms.length > 0) { |
|
var clone = this._cloneRegion(); |
|
if (tops.length > 0) { |
|
store.push(this.regions[tops[0].id]); |
|
} |
|
if (bottoms.length > 0) { |
|
store.push(this.regions[bottoms[0].id]); |
|
} |
|
count++; |
|
var left = BI.average(store, function (i, r) {//求平均,减少误差 |
|
return r.left; |
|
}); |
|
var occupied = this._getRegionOccupied(store); |
|
|
|
var split = BI.min(store, function (i, r) { |
|
return r.width; |
|
}).width / 2; |
|
var insert = clone[tid] = { |
|
left: left, |
|
width: split, |
|
top: occupied.top, |
|
height: occupied.height |
|
}; |
|
BI.each(store, function (i, region) { |
|
BI.extend(clone[region.id], { |
|
left: left + split, |
|
width: region.width - split - (left - region.left) |
|
}); |
|
}); |
|
if (this._test(store)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "left-center" + count, |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} else { |
|
break; |
|
} |
|
|
|
if (tops.length > 0) { |
|
tops = this._getLeftAlignRegions(tops[0].id).top; |
|
} |
|
if (bottoms.length > 0) { |
|
bottoms = this._getLeftAlignRegions(bottoms[0].id).bottom; |
|
} |
|
} |
|
} |
|
//有右方居中drop |
|
var tops = _right.top, bottoms = _right.bottom; |
|
if (tops.length > 0 && bottoms.length > 0) { |
|
var count = 0; |
|
var store = [this.regions[name]]; |
|
while (tops.length > 0 || bottoms.length > 0) { |
|
var clone = this._cloneRegion(); |
|
if (tops.length > 0) { |
|
store.push(this.regions[tops[0].id]); |
|
} |
|
if (bottoms.length > 0) { |
|
store.push(this.regions[bottoms[0].id]); |
|
} |
|
count++; |
|
var right = BI.average(store, function (i, r) {//求平均,减少误差 |
|
return r.left + r.width; |
|
}); |
|
var occupied = this._getRegionOccupied(store); |
|
|
|
var split = BI.min(store, function (i, r) { |
|
return r.width; |
|
}).width / 2; |
|
var insert = clone[tid] = { |
|
left: right - split, |
|
width: split, |
|
top: occupied.top, |
|
height: occupied.height |
|
}; |
|
BI.each(store, function (i, region) { |
|
BI.extend(clone[region.id], { |
|
width: right - region.left - split |
|
}); |
|
}); |
|
if (this._test(store)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "right-center" + count, |
|
regions: clone, |
|
insert: insert |
|
}); |
|
} else { |
|
break; |
|
} |
|
|
|
if (tops.length > 0) { |
|
tops = this._getRightAlignRegions(tops[0].id).top; |
|
} |
|
if (bottoms.length > 0) { |
|
bottoms = this._getRightAlignRegions(bottoms[0].id).bottom; |
|
} |
|
} |
|
} |
|
var lefts = this._getEquivalentRelativeRegions(name, ["left"]); |
|
if (lefts.length === 1) { |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var left = this.regions[lefts[0].id]; |
|
var width = left.width; |
|
var all = left.width + _cur.width; |
|
var ratio = width / all; |
|
var split = all / 3; |
|
var lleft = width - split * ratio, rleft = _cur.width - split * (1 - ratio); |
|
var insert = false; |
|
if (lleft <= 21) { |
|
rleft = _cur.width - split; |
|
if (rleft <= 21) { |
|
|
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left, |
|
width: split, |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left + split, |
|
width: _cur.width - split |
|
}); |
|
} |
|
} else if (rleft <= 21) { |
|
lleft = width - split; |
|
if (lleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left - split, |
|
width: split, |
|
}; |
|
BI.extend(clone[left.id], { |
|
top: left.top, |
|
height: left.height, |
|
left: left.left, |
|
width: left.width - split |
|
}); |
|
} |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: left.left + lleft, |
|
width: split, |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left + _cur.width - rleft, |
|
width: rleft |
|
}); |
|
BI.extend(clone[left.id], { |
|
top: left.top, |
|
height: left.height, |
|
left: left.left, |
|
width: lleft |
|
}); |
|
} |
|
if (insert !== false) { |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "left-line", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
} |
|
} |
|
var rights = this._getEquivalentRelativeRegions(name, ["right"]); |
|
if (rights.length === 1) { |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var right = this.regions[rights[0].id]; |
|
var width = right.width; |
|
var all = right.width + _cur.width; |
|
var ratio = width / all; |
|
var split = all / 3; |
|
var lleft = _cur.width - split * (1 - ratio), rleft = width - split * ratio; |
|
var insert = false; |
|
if (lleft <= 21) { |
|
rleft = width - split; |
|
if (rleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: right.top, |
|
height: right.height, |
|
left: right.left, |
|
width: split |
|
}; |
|
BI.extend(clone[right.id], { |
|
top: right.top, |
|
height: right.height, |
|
left: right.left + split, |
|
width: right.width - split |
|
}) |
|
} |
|
} else if (rleft <= 21) { |
|
lleft = _cur.width - split; |
|
if (lleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left + lleft, |
|
width: split |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left, |
|
width: _cur.width - split |
|
}) |
|
} |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left + lleft, |
|
width: split |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: _cur.height, |
|
left: _cur.left, |
|
width: lleft |
|
}); |
|
BI.extend(clone[right.id], { |
|
top: right.top, |
|
height: right.height, |
|
left: right.left + right.width - rleft, |
|
width: rleft |
|
}); |
|
} |
|
if (insert !== false) { |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "right-line", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
} |
|
} |
|
var tops = this._getEquivalentRelativeRegions(name, ["top"]); |
|
if (tops.length === 1) { |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var top = this.regions[tops[0].id]; |
|
var height = top.height; |
|
var all = top.height + _cur.height; |
|
var ratio = height / all; |
|
var split = all / 3; |
|
var tleft = height - split * ratio, bleft = _cur.height - split * (1 - ratio); |
|
var insert = false; |
|
if (tleft <= 21) { |
|
bleft = _cur.height - split; |
|
if (bleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top, |
|
width: _cur.width, |
|
left: _cur.left, |
|
height: split |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top + split, |
|
height: _cur.height - split, |
|
left: _cur.left, |
|
width: _cur.width |
|
}); |
|
} |
|
} |
|
if (bleft <= 21) { |
|
tleft = height - split; |
|
if (tleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top - split, |
|
height: split, |
|
left: _cur.left, |
|
width: _cur.width |
|
}; |
|
BI.extend(clone[top.id], { |
|
top: top.top, |
|
height: top.height - split, |
|
left: top.left, |
|
width: top.width |
|
}); |
|
} |
|
} else { |
|
insert = clone[tid] = { |
|
top: top.top + tleft, |
|
height: split, |
|
left: _cur.left, |
|
width: _cur.width |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top + _cur.height - bleft, |
|
height: bleft, |
|
left: _cur.left, |
|
width: _cur.width |
|
}); |
|
BI.extend(clone[top.id], { |
|
top: top.top, |
|
height: tleft, |
|
left: top.left, |
|
width: top.width |
|
}); |
|
} |
|
if (insert !== false) { |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top-line", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
} |
|
} |
|
var bottoms = this._getEquivalentRelativeRegions(name, ["bottom"]); |
|
if (bottoms.length === 1) { |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var bottom = this.regions[bottoms[0].id]; |
|
var height = bottom.height; |
|
var all = bottom.height + _cur.height; |
|
var ratio = height / all; |
|
var split = all / 3; |
|
var tleft = _cur.height - split * (1 - ratio), bleft = height - split * ratio; |
|
var insert = false; |
|
if (tleft <= 21) { |
|
bleft = height - split; |
|
if (bleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: bottom.top, |
|
height: bottom.height, |
|
left: bottom.left, |
|
width: split |
|
}; |
|
BI.extend(clone[bottom.id], { |
|
top: bottom.top + split, |
|
height: bottom.height - split, |
|
left: bottom.left, |
|
width: bottom.width |
|
}); |
|
} |
|
} else if (bleft <= 21) { |
|
tleft = _cur.height - split; |
|
if (tleft <= 21) { |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top + tleft, |
|
height: split, |
|
left: _cur.left, |
|
width: _cur.width |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: _cur.height - split, |
|
left: _cur.left, |
|
width: _cur.width |
|
}); |
|
} |
|
} else { |
|
insert = clone[tid] = { |
|
top: _cur.top + tleft, |
|
height: split, |
|
left: _cur.left, |
|
width: _cur.width, |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
height: tleft, |
|
left: _cur.left, |
|
width: _cur.width |
|
}); |
|
BI.extend(clone[bottom.id], { |
|
top: bottom.top + bottom.height - bleft, |
|
height: bleft, |
|
left: bottom.left, |
|
width: bottom.width |
|
}); |
|
} |
|
if (insert !== false) { |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom-line", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
} |
|
} |
|
if (tops.length >= 1) { |
|
result.push({ |
|
type: "top-gap" |
|
}); |
|
} |
|
if (bottoms.length >= 1) { |
|
result.push({ |
|
type: "bottom-gap" |
|
}); |
|
} |
|
//上 |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var insert = clone[tid] = { |
|
top: _cur.top, |
|
left: _cur.left, |
|
width: _cur.width, |
|
height: _cur.height / 2, |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top + _cur.height / 2, |
|
left: _cur.left, |
|
width: _cur.width, |
|
height: _cur.height / 2 |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "top", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
//下 |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var insert = clone[tid] = { |
|
top: _cur.top + _cur.height / 2, |
|
left: _cur.left, |
|
width: _cur.width, |
|
height: _cur.height / 2 |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
left: _cur.left, |
|
width: _cur.width, |
|
height: _cur.height / 2 |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "bottom", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
//左 |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var insert = clone[tid] = { |
|
top: _cur.top, |
|
left: _cur.left, |
|
width: _cur.width / 2, |
|
height: _cur.height |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
left: _cur.left + _cur.width / 2, |
|
width: _cur.width / 2, |
|
height: _cur.height |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "left", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
//右 |
|
var clone = this._cloneRegion(); |
|
var _cur = clone[name]; |
|
var insert = clone[tid] = { |
|
top: _cur.top, |
|
left: _cur.left + _cur.width / 2, |
|
width: _cur.width / 2, |
|
height: _cur.height |
|
}; |
|
BI.extend(clone[name], { |
|
top: _cur.top, |
|
left: _cur.left, |
|
width: _cur.width / 2, |
|
height: _cur.height |
|
}); |
|
if (this._test(clone)) { |
|
delete clone[tid]; |
|
result.push({ |
|
type: "right", |
|
regions: clone, |
|
insert: insert |
|
}) |
|
} |
|
return result; |
|
}, |
|
|
|
_positionAt: function (position, bound) { |
|
var left = position.left - bound.left, top = position.top - bound.top; |
|
var right = bound.width - left, bottom = bound.height - top; |
|
var halfW = bound.width / 2, halfH = bound.height / 2; |
|
if (left < 0 || top < 0 || right < 0 || bottom < 0) { |
|
return; |
|
} |
|
var devides = this._splitRegions(bound.id); |
|
var types = []; |
|
var result = {}; |
|
var topcenterCount = 0, bottomcenterCount = 0, leftcenterCount = 0, rightcenterCount = 0; |
|
BI.each(devides, function (i, devide) { |
|
if (devide.type.indexOf("top-center") > -1) { |
|
topcenterCount++; |
|
} else if (devide.type.indexOf("bottom-center") > -1) { |
|
bottomcenterCount++; |
|
} else if (devide.type.indexOf("left-center") > -1) { |
|
leftcenterCount++; |
|
} else if (devide.type.indexOf("right-center") > -1) { |
|
rightcenterCount++; |
|
} |
|
types.push(devide.type); |
|
result[devide.type] = devide; |
|
}); |
|
//drop |
|
if (top >= 5 && top <= 15 && left >= 5 && left <= 15 && types.contains("left-top")) { |
|
return result["left-top"]; |
|
} |
|
if (top >= 5 && top <= 15 && right >= 5 && right <= 15 && types.contains("top-right")) { |
|
return result["top-right"]; |
|
} |
|
if (bottom >= 5 && bottom <= 15 && left >= 5 && left <= 15 && types.contains("bottom-left")) { |
|
return result["bottom-left"]; |
|
} |
|
if (bottom >= 5 && bottom <= 15 && right >= 5 && right <= 15 && types.contains("bottom-right")) { |
|
return result["bottom-right"]; |
|
} |
|
|
|
if (top >= 5 && top <= 15 && left >= 25 && left <= 35 && types.contains("top-left")) { |
|
return result["top-left"]; |
|
} |
|
if (top >= 5 && top <= 15 && right >= 25 && right <= 35 && types.contains("top-right-second")) { |
|
return result["top-right-second"]; |
|
} |
|
if (bottom >= 5 && bottom <= 15 && left >= 25 && left <= 35 && types.contains("bottom-left-second")) { |
|
return result["bottom-left-second"]; |
|
} |
|
if (bottom >= 5 && bottom <= 15 && right >= 25 && right <= 35 && types.contains("bottom-right-second")) { |
|
return result["bottom-right-second"]; |
|
} |
|
|
|
//topcenter或bottomcenter |
|
if (left >= halfW - 10 && left <= halfW + 10 && (topcenterCount > 0 || bottomcenterCount > 0)) { |
|
for (var i = 1; i <= topcenterCount; i++) { |
|
var s = (topcenterCount - i) * 20 + 5, e = s + 10; |
|
if (top >= s && top <= e) { |
|
return result["top-center" + i]; |
|
} |
|
} |
|
for (var i = 1; i <= bottomcenterCount; i++) { |
|
var s = (bottomcenterCount - i) * 20 + 5, e = s + 10; |
|
if (bottom >= s && bottom <= e) { |
|
return result["bottom-center" + i]; |
|
} |
|
} |
|
} |
|
//leftcenter或rightcenter |
|
if (top >= halfH - 10 && top <= halfH + 10 && (leftcenterCount > 0 || rightcenterCount > 0)) { |
|
for (var i = 1; i <= leftcenterCount; i++) { |
|
var s = (leftcenterCount - i) * 20 + 5, e = s + 10; |
|
if (left >= s && left <= e) { |
|
return result["left-center" + i]; |
|
} |
|
} |
|
for (var i = 1; i <= rightcenterCount; i++) { |
|
var s = (rightcenterCount - i) * 20 + 5, e = s + 10; |
|
if (right >= s && right <= e) { |
|
return result["right-center" + i]; |
|
} |
|
} |
|
} |
|
|
|
//缝隙 |
|
if (top <= 8 && types.contains("top-gap")) { |
|
return result["top-gap"]; |
|
} |
|
if (bottom <= 8 && types.contains("bottom-gap")) { |
|
return result["bottom-gap"]; |
|
} |
|
|
|
//三分 |
|
if (top <= 15 && left >= 15 && right >= 15 && types.contains("top-line")) { |
|
return result["top-line"]; |
|
} |
|
if (left <= 15 && top >= 15 && bottom >= 15 && types.contains("left-line")) { |
|
return result["left-line"]; |
|
} |
|
if (right <= 15 && top >= 15 && bottom >= 15 && types.contains("right-line")) { |
|
return result["right-line"]; |
|
} |
|
if (bottom <= 15 && left >= 15 && right >= 15 && types.contains("bottom-line")) { |
|
return result["bottom-line"]; |
|
} |
|
|
|
//平分 |
|
if (top <= 1 / 4 * bound.height && types.contains("top")) { |
|
return result["top"]; |
|
} |
|
if (top >= 3 / 4 * bound.height && types.contains("bottom")) { |
|
return result["bottom"]; |
|
} |
|
if (left <= bound.width / 2 && types.contains("left")) { |
|
return result["left"]; |
|
} |
|
return result["right"]; |
|
}, |
|
|
|
|
|
_getScrollOffset: function () { |
|
return { |
|
left: this.scrollContainer.element[0].scrollLeft, |
|
top: this.scrollContainer.element[0].scrollTop |
|
} |
|
}, |
|
|
|
////操作//// |
|
_createOneRegion: function (item) { |
|
var el = BI.createWidget(item.el); |
|
el.setVisible(true); |
|
return { |
|
id: el.attr("id"), |
|
left: item.left, |
|
top: item.top, |
|
width: item.width, |
|
height: item.height, |
|
el: el |
|
} |
|
}, |
|
|
|
_createOneDrop: function (region) { |
|
if (this.storeDrops[region.id]) { |
|
var drop = this.storeDrops[region.id].el; |
|
drop.setVisible(true); |
|
} else { |
|
var drop = BI.createWidget({ |
|
type: "bi.layout", |
|
cls: "arrangement-drop-region", |
|
widgetName: region.id |
|
}); |
|
} |
|
return { |
|
id: region.id, |
|
left: region.left, |
|
top: region.top, |
|
width: region.width, |
|
height: region.height, |
|
el: drop |
|
} |
|
}, |
|
|
|
_calculateDrops: function () { |
|
var self = this; |
|
BI.each(this.drops, function (id, drop) { |
|
drop.el.empty(); |
|
var devides = self._splitRegions(id); |
|
var topcenterCount = 0, bottomcenterCount = 0, leftcenterCount = 0, rightcenterCount = 0; |
|
var absolutes = []; |
|
var horizontals = []; |
|
var verticals = []; |
|
BI.each(devides, function (i, devide) { |
|
if (devide.type.indexOf("top-center") > -1) { |
|
topcenterCount++; |
|
} else if (devide.type.indexOf("bottom-center") > -1) { |
|
bottomcenterCount++; |
|
} else if (devide.type.indexOf("left-center") > -1) { |
|
leftcenterCount++; |
|
} else if (devide.type.indexOf("right-center") > -1) { |
|
rightcenterCount++; |
|
} |
|
}); |
|
BI.each(devides, function (i, devide) { |
|
switch (devide.type) { |
|
case "left-top": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
left: 5, |
|
top: 5 |
|
}); |
|
break; |
|
case "top-right": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
right: 5, |
|
top: 5 |
|
}); |
|
break; |
|
case "bottom-left": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
left: 5, |
|
bottom: 5 |
|
}); |
|
break; |
|
case "bottom-right": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
right: 5, |
|
bottom: 5 |
|
}); |
|
break; |
|
case "top-left": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
left: 25, |
|
top: 5 |
|
}); |
|
break; |
|
case "top-right-second": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
right: 25, |
|
top: 5 |
|
}); |
|
break; |
|
case "bottom-left-second": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
left: 25, |
|
bottom: 5 |
|
}); |
|
break; |
|
case "bottom-right-second": |
|
absolutes.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
right: 25, |
|
bottom: 5 |
|
}); |
|
break; |
|
default: |
|
if (devide.type.indexOf("top-center") > -1) { |
|
var num = devide.type.split("top-center")[1]; |
|
horizontals.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 20, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
tgap: 20 * (topcenterCount - BI.parseInt(num)) + 5 |
|
}) |
|
} else if (devide.type.indexOf("bottom-center") > -1) { |
|
var num = devide.type.split("bottom-center")[1]; |
|
horizontals.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 20, |
|
height: 10, |
|
cls: "drop-devider" |
|
}, |
|
bgap: 20 * (bottomcenterCount - BI.parseInt(num)) + 5 |
|
}) |
|
} else if (devide.type.indexOf("left-center") > -1) { |
|
var num = devide.type.split("left-center")[1]; |
|
verticals.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 20, |
|
cls: "drop-devider" |
|
}, |
|
lgap: 20 * (leftcenterCount - BI.parseInt(num)) + 5 |
|
}) |
|
} else if (devide.type.indexOf("right-center") > -1) { |
|
var num = devide.type.split("right-center")[1]; |
|
verticals.push({ |
|
el: { |
|
type: "bi.layout", |
|
width: 10, |
|
height: 20, |
|
cls: "drop-devider" |
|
}, |
|
rgap: 20 * (rightcenterCount - BI.parseInt(num)) + 5 |
|
}) |
|
} |
|
break; |
|
} |
|
|
|
}); |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: drop.el, |
|
items: absolutes |
|
}); |
|
|
|
BI.createWidget({ |
|
type: "bi.absolute_horizontal_adapt", |
|
element: drop.el, |
|
items: horizontals |
|
}); |
|
|
|
BI.createWidget({ |
|
type: "bi.absolute_vertical_adapt", |
|
element: drop.el, |
|
items: verticals |
|
}); |
|
}); |
|
}, |
|
|
|
_applyRegion: function (regions) { |
|
var self = this, o = this.options; |
|
BI.each(regions || this.regions, function (i, region) { |
|
region.el.element.css({ |
|
left: region.left, |
|
top: region.top, |
|
width: region.width, |
|
height: region.height |
|
}); |
|
self.drops[region.id].left = region.left; |
|
self.drops[region.id].top = region.top; |
|
self.drops[region.id].width = region.width; |
|
self.drops[region.id].height = region.height; |
|
}); |
|
BI.each(this.drops, function (i, region) { |
|
region.el.element.css({ |
|
left: region.left, |
|
top: region.top, |
|
width: region.width, |
|
height: region.height |
|
}); |
|
}); |
|
this._applyContainer(); |
|
this._calculateDrops(); |
|
this.ratio = this.getLayoutRatio(); |
|
}, |
|
|
|
_renderRegion: function () { |
|
var self = this; |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: this.container, |
|
items: BI.toArray(this.regions) |
|
}); |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: this.droppable, |
|
items: BI.toArray(this.drops) |
|
}); |
|
}, |
|
|
|
getClientWidth: function () { |
|
return this.scrollContainer.element[0].clientWidth; |
|
}, |
|
|
|
getClientHeight: function () { |
|
return this.scrollContainer.element[0].clientHeight; |
|
}, |
|
|
|
_applyContainer: function () { |
|
//先掩藏后显示能够明确滚动条是否出现 |
|
this.scrollContainer.element.css("overflow", "hidden"); |
|
var occupied = this._getRegionOccupied(); |
|
this.container.element.width(occupied.left + occupied.width).height(occupied.top + occupied.height); |
|
this.scrollContainer.element.css("overflow", "auto"); |
|
return occupied; |
|
}, |
|
|
|
_modifyRegion: function (regions) { |
|
BI.each(this.regions, function (id, region) { |
|
if (regions[id]) { |
|
region.left = regions[id].left; |
|
region.top = regions[id].top; |
|
region.width = regions[id].width; |
|
region.height = regions[id].height; |
|
} |
|
}); |
|
BI.each(this.drops, function (id, region) { |
|
if (regions[id]) { |
|
region.left = regions[id].left; |
|
region.top = regions[id].top; |
|
region.width = regions[id].width; |
|
region.height = regions[id].height; |
|
} |
|
}); |
|
}, |
|
|
|
_addRegion: function (item) { |
|
var region = this._createOneRegion(item); |
|
this.regions[region.id] = region; |
|
var drop = this._createOneDrop(region); |
|
this.drops[drop.id] = drop; |
|
this.storeDrops[drop.id] = drop; |
|
this._locationRegion(); |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: this.container, |
|
items: [region] |
|
}); |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: this.droppable, |
|
items: [drop] |
|
}) |
|
}, |
|
|
|
_deleteRegionByName: function (name) { |
|
this.regions[name].el.setVisible(false); |
|
this.drops[name].el.setVisible(false); |
|
delete this.regions[name]; |
|
delete this.drops[name]; |
|
this._locationRegion(); |
|
}, |
|
|
|
_setArrangeSize: function (size) { |
|
this.arrangement.element.css({ |
|
left: size.left, |
|
top: size.top, |
|
width: size.width, |
|
height: size.height |
|
}) |
|
}, |
|
|
|
//Grid |
|
_getOneWidthPortion: function () { |
|
return this.getClientWidth() / BI.Arrangement.PORTION; |
|
}, |
|
|
|
_getGridPositionAndSize: function (position) { |
|
var perWidth = this._getOneWidthPortion(); |
|
var widthPortion = Math.round(position.width / perWidth); |
|
var leftPortion = Math.round(position.left / perWidth); |
|
var topPortion = Math.round(position.top / BI.Arrangement.GRID_HEIGHT); |
|
var heightPortion = Math.round(position.height / BI.Arrangement.GRID_HEIGHT); |
|
// if (leftPortion > BI.Arrangement.PORTION) { |
|
// leftPortion = BI.Arrangement.PORTION; |
|
// } |
|
// if (widthPortion > BI.Arrangement.PORTION) { |
|
// widthPortion = BI.Arrangement.PORTION; |
|
// } |
|
// if (leftPortion + widthPortion > BI.Arrangement.PORTION) { |
|
// leftPortion = BI.Arrangement.PORTION - widthPortion; |
|
// } |
|
if (widthPortion === 0) { |
|
widthPortion = 1; |
|
} |
|
if (heightPortion === 0) { |
|
heightPortion = 1; |
|
} |
|
return { |
|
x: leftPortion, |
|
y: topPortion, |
|
w: widthPortion, |
|
h: heightPortion |
|
} |
|
}, |
|
|
|
_getBlockPositionAndSize: function (position) { |
|
var perWidth = this._getOneWidthPortion(); |
|
return { |
|
left: position.x * perWidth, |
|
top: position.y * BI.Arrangement.GRID_HEIGHT, |
|
width: position.w * perWidth, |
|
height: position.h * BI.Arrangement.GRID_HEIGHT |
|
}; |
|
}, |
|
|
|
_getLayoutsByRegions: function (regions) { |
|
var self = this; |
|
var result = []; |
|
BI.each(regions || this.regions, function (id, region) { |
|
result.push(BI.extend(self._getGridPositionAndSize(region), { |
|
i: region.id |
|
})) |
|
}); |
|
return result; |
|
}, |
|
|
|
_getLayoutIndexByName: function (layout, name) { |
|
return BI.findIndex(layout, function (i, l) { |
|
return l.i === name; |
|
}); |
|
}, |
|
|
|
_setBlockPositionAndSize: function (size) { |
|
this.block.element.css({ |
|
left: size.left, |
|
top: size.top, |
|
width: size.width, |
|
height: size.height |
|
}); |
|
}, |
|
|
|
_getRegionsByLayout: function (layout) { |
|
var self = this; |
|
var regions = {}; |
|
BI.each(layout, function (i, ly) { |
|
regions[ly.i] = BI.extend(self._getBlockPositionAndSize(ly), { |
|
id: ly.i |
|
}); |
|
}); |
|
return regions; |
|
}, |
|
|
|
_setRegionsByLayout: function (regions, layout) { |
|
var self = this; |
|
regions || (regions = this.regions); |
|
BI.each(layout, function (i, ly) { |
|
if (regions[ly.i]) { |
|
BI.extend(regions[ly.i], self._getBlockPositionAndSize(ly)); |
|
} |
|
}); |
|
return regions; |
|
}, |
|
|
|
_moveElement: function (layout, l, x, y, isUserAction) { |
|
var self = this; |
|
if (l._static) { |
|
return layout; |
|
} |
|
|
|
if (l.y === y && l.x === x) { |
|
return layout; |
|
} |
|
|
|
var movingUp = y && l.y > y; |
|
if (typeof x === 'number') { |
|
l.x = x; |
|
} |
|
if (typeof y === 'number') { |
|
l.y = y; |
|
} |
|
l.moved = true; |
|
|
|
var sorted = this._sortLayoutItemsByRowCol(layout); |
|
if (movingUp) { |
|
sorted = sorted.reverse(); |
|
} |
|
var collisions = getAllCollisions(sorted, l); |
|
|
|
for (var i = 0, len = collisions.length; i < len; i++) { |
|
var collision = collisions[i]; |
|
if (collision.moved) { |
|
continue; |
|
} |
|
|
|
if (l.y > collision.y && l.y - collision.y > collision.h / 4) { |
|
continue; |
|
} |
|
|
|
if (collision._static) { |
|
layout = this._moveElementAwayFromCollision(layout, collision, l, isUserAction); |
|
} else { |
|
layout = this._moveElementAwayFromCollision(layout, l, collision, isUserAction); |
|
} |
|
} |
|
|
|
return layout; |
|
|
|
function getAllCollisions(layout, layoutItem) { |
|
return BI.filter(layout, function (i, l) { |
|
return self._collides(l, layoutItem); |
|
}); |
|
} |
|
}, |
|
|
|
_sortLayoutItemsByRowCol: function (layout) { |
|
return [].concat(layout).sort(function (a, b) { |
|
if (a.y > b.y || (a.y === b.y && a.x > b.x)) { |
|
return 1; |
|
} |
|
return -1; |
|
}); |
|
}, |
|
|
|
_collides: function (l1, l2) { |
|
if (l1 === l2) { |
|
return false; |
|
} // same element |
|
if (l1.x + l1.w <= l2.x) { |
|
return false; |
|
} // l1 is left of l2 |
|
if (l1.x >= l2.x + l2.w) { |
|
return false; |
|
} // l1 is right of l2 |
|
if (l1.y + l1.h <= l2.y) { |
|
return false; |
|
} // l1 is above l2 |
|
if (l1.y >= l2.y + l2.h) { |
|
return false; |
|
} // l1 is below l2 |
|
return true; // boxes overlap |
|
}, |
|
|
|
_getFirstCollision: function (layout, layoutItem) { |
|
for (var i = 0, len = layout.length; i < len; i++) { |
|
if (this._collides(layout[i], layoutItem)) { |
|
return layout[i]; |
|
} |
|
} |
|
}, |
|
|
|
_moveElementAwayFromCollision: function (layout, collidesWith, |
|
itemToMove, isUserAction) { |
|
if (isUserAction) { |
|
var fakeItem = { |
|
x: itemToMove.x, |
|
y: itemToMove.y, |
|
w: itemToMove.w, |
|
h: itemToMove.h, |
|
i: '-1' |
|
}; |
|
fakeItem.y = Math.max(collidesWith.y - itemToMove.h, 0); |
|
if (!this._getFirstCollision(layout, fakeItem)) { |
|
return this._moveElement(layout, itemToMove, undefined, fakeItem.y); |
|
} |
|
} |
|
|
|
return this._moveElement(layout, itemToMove, undefined, itemToMove.y + 1); |
|
}, |
|
|
|
_compactItem: function (compareWith, l, verticalCompact) { |
|
if (verticalCompact) { |
|
while (l.y > 0 && !this._getFirstCollision(compareWith, l)) { |
|
l.y--; |
|
} |
|
} |
|
|
|
var collides; |
|
while ((collides = this._getFirstCollision(compareWith, l))) { |
|
l.y = collides.y + collides.h; |
|
} |
|
return l; |
|
}, |
|
|
|
compact: function (layout, verticalCompact) { |
|
var compareWith = getStatics(layout); |
|
var sorted = this._sortLayoutItemsByRowCol(layout); |
|
var out = []; |
|
|
|
for (var i = 0, len = sorted.length; i < len; i++) { |
|
var l = sorted[i]; |
|
|
|
if (!l._static) { |
|
l = this._compactItem(compareWith, l, verticalCompact); |
|
|
|
compareWith.push(l); |
|
} |
|
|
|
out[layout.indexOf(l)] = l; |
|
|
|
l.moved = false; |
|
} |
|
|
|
return out; |
|
function getStatics(layout) { |
|
return BI.filter(layout, function (i, l) { |
|
return l._static; |
|
}); |
|
} |
|
}, |
|
|
|
////公有方法//// |
|
getRegionByName: function (name) { |
|
var obj = {}; |
|
obj[name] = this.regions[name]; |
|
return this._cloneRegion(obj)[name]; |
|
}, |
|
|
|
getAllRegions: function () { |
|
return BI.toArray(this._cloneRegion()); |
|
}, |
|
|
|
getHelper: function () { |
|
var helper = BI.createWidget({ |
|
type: "bi.layout", |
|
width: 18, |
|
height: 18, |
|
cls: "arrangement-helper" |
|
}); |
|
BI.createWidget({ |
|
type: "bi.absolute", |
|
element: this, |
|
items: [helper] |
|
}); |
|
return helper; |
|
}, |
|
|
|
_start: function (cur) { |
|
this.arrangement.setVisible(true); |
|
this.droppable.setVisible(true); |
|
if (this.options.layoutType === BI.Arrangement.LAYOUT_TYPE.GRID) { |
|
this.block.setVisible(true); |
|
} |
|
BI.each(this.drops, function (i, drop) { |
|
drop.el.setVisible(false); |
|
}); |
|
if (cur) { |
|
if (this.drops[cur]) { |
|
this.drops[cur].el.setVisible(true); |
|
} |
|
} |
|
}, |
|
|
|
_stop: function () { |
|
this.arrangement.setVisible(false); |
|
this.droppable.setVisible(false); |
|
this.block.setVisible(false); |
|
}, |
|
|
|
getDirectRelativeRegions: function (name, direction) { |
|
direction || (direction = ["top", "bottom", "left", "right"]); |
|
var self = this, result = {}; |
|
BI.each(direction, function (i, dir) { |
|
result[dir] = self._getDirectRelativeRegions(name, [dir]); |
|
}); |
|
return result; |
|
}, |
|
|
|
////公有操作//// |
|
setLayoutType: function (type) { |
|
var self = this, o = this.options; |
|
if (type !== o.layoutType) { |
|
o.layoutType = type; |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
this.relayout(); |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
this.relayout(); |
|
break; |
|
} |
|
} |
|
}, |
|
|
|
getLayoutType: function () { |
|
return this.options.layoutType; |
|
}, |
|
|
|
getLayoutRatio: function () { |
|
var occupied = this._getRegionOccupied(); |
|
var width = this.getClientWidth(), height = this.getClientHeight(); |
|
return { |
|
x: BI.parseFloat(BI.contentFormat((occupied.left + occupied.width) / width, "#.##;-#.##")), |
|
y: BI.parseFloat(BI.contentFormat((occupied.top + occupied.height) / height, "#.##;-#.##")) |
|
} |
|
}, |
|
|
|
addRegion: function (region, position) { |
|
if (position) { |
|
this.setPosition(position, region); |
|
} |
|
var self = this, o = this.options; |
|
if (!this.position) { |
|
return false; |
|
} |
|
var test = this._cloneRegion(); |
|
BI.each(this.position.regions, function (i, region) { |
|
test[region.id].left = region.left; |
|
test[region.id].top = region.top; |
|
test[region.id].width = region.width; |
|
test[region.id].height = region.height; |
|
|
|
}); |
|
var item = BI.extend({}, region, { |
|
left: this.position.insert.left, |
|
top: this.position.insert.top, |
|
width: this.position.insert.width, |
|
height: this.position.insert.height |
|
}); |
|
var added = this._createOneRegion(item); |
|
test[added.id] = added; |
|
if (this._test(test)) { |
|
delete test[added.id]; |
|
this._modifyRegion(test); |
|
this._addRegion(item); |
|
this._populate(this.getAllRegions()); |
|
return true; |
|
} |
|
return false; |
|
}, |
|
|
|
deleteRegion: function (name) { |
|
if (!this.regions[name]) { |
|
return false; |
|
} |
|
var self = this, o = this.options; |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
var clone = this._cloneRegion(); |
|
var regions = this._getEquivalentRelativeRegions(name); |
|
if (regions.length > 0) { |
|
BI.each(regions, function (i, region) { |
|
BI.extend(clone[region.id], region); |
|
}); |
|
this._modifyRegion(clone); |
|
} |
|
this._deleteRegionByName(name); |
|
this._populate(this.getAllRegions()); |
|
return true; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
this._deleteRegionByName(name); |
|
this._populate(this.getAllRegions()); |
|
return true; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
this._deleteRegionByName(name); |
|
this._populate(this.getAllRegions()); |
|
this.resize(); |
|
return true; |
|
} |
|
return false; |
|
}, |
|
|
|
setRegionSize: function (name, size) { |
|
var self = this, o = this.options; |
|
var flag = false; |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
var current = this.regions[name]; |
|
if (size.width !== current.width) { |
|
var regions = this._getInDirectRelativeRegions(name, ["right"]).right; |
|
var lefts = regions.left || [], rights = regions.right || []; |
|
var offset = size.width - current.width; |
|
var cloned = this._cloneRegion(); |
|
BI.some(lefts, function (i, left) { |
|
var region = cloned[left.id]; |
|
region.width = region.width + offset; |
|
}); |
|
BI.some(rights, function (i, right) { |
|
var region = cloned[right.id]; |
|
region.width = region.width - offset; |
|
region.left = region.left + offset; |
|
}); |
|
if (this._test(cloned) && this._isArrangeFine(cloned)) { |
|
this._modifyRegion(cloned); |
|
flag = true; |
|
} |
|
} |
|
if (size.height !== current.height) { |
|
var regions = this._getInDirectRelativeRegions(name, ["bottom"]).bottom; |
|
var tops = regions.top || [], bottoms = regions.bottom || []; |
|
var offset = size.height - current.height; |
|
var cloned = this._cloneRegion(); |
|
BI.some(tops, function (i, top) { |
|
var region = cloned[top.id]; |
|
region.height = region.height + offset; |
|
}); |
|
BI.some(bottoms, function (i, bottom) { |
|
var region = cloned[bottom.id]; |
|
region.height = region.height - offset; |
|
region.top = region.top + offset; |
|
}); |
|
if (this._test(cloned) && this._isArrangeFine(cloned)) { |
|
this._modifyRegion(cloned); |
|
flag = true; |
|
} |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
var clone = this._cloneRegion(); |
|
BI.extend(clone[name], { |
|
width: size.width, |
|
height: size.height |
|
}); |
|
if (this._test(clone)) { |
|
this._modifyRegion(clone); |
|
flag = true; |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
var clone = this._cloneRegion(); |
|
BI.extend(clone[name], { |
|
width: size.width, |
|
height: size.height |
|
}); |
|
if (this._test(clone)) { |
|
var layout = this._getLayoutsByRegions(clone); |
|
layout = this.compact(layout, true); |
|
var regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
flag = true; |
|
} |
|
break; |
|
} |
|
this._locationRegion(); |
|
this._applyRegion(); |
|
return flag; |
|
}, |
|
|
|
setPosition: function (position, size) { |
|
var self = this, o = this.options; |
|
var insert, regions = [], cur; |
|
if (position.left < 0 || position.top < 0) { |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
this.resize(); |
|
break; |
|
} |
|
this._stop(); |
|
this.position = null; |
|
return null; |
|
} |
|
var offset = this._getScrollOffset(); |
|
position = { |
|
left: position.left + offset.left, |
|
top: position.top + offset.top |
|
}; |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (BI.isEmpty(this.regions)) { |
|
if (self._isPositionInBounds(position, { |
|
left: 0, |
|
top: 0, |
|
width: this.element[0].clientWidth, |
|
height: this.element[0].clientHeight |
|
})) { |
|
insert = { |
|
left: 0, |
|
top: 0, |
|
width: this.element[0].clientWidth, |
|
height: this.element[0].clientHeight |
|
}; |
|
} |
|
} else { |
|
if (BI.some(this.regions, function (id, region) { |
|
if (self._isPositionInBounds(position, region)) { |
|
var at = self._positionAt(position, region); |
|
if (!at) { |
|
insert = null; |
|
} else { |
|
insert = at.insert; |
|
regions = at.regions; |
|
} |
|
cur = id; |
|
return true; |
|
} |
|
})) { |
|
} |
|
else { |
|
insert = null; |
|
regions = []; |
|
} |
|
} |
|
if (insert == null) { |
|
this._stop(); |
|
self.position = null; |
|
break; |
|
} |
|
|
|
this.position = { |
|
insert: insert, |
|
regions: regions |
|
}; |
|
this._setArrangeSize(insert); |
|
this._start(cur); |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
var insert = { |
|
top: position.top < 0 ? 0 : position.top, |
|
left: position.left < 0 ? 0 : position.left, |
|
width: size.width, |
|
height: size.height |
|
}; |
|
this.position = { |
|
insert: insert |
|
}; |
|
this._setArrangeSize(insert); |
|
this._start(); |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
var p = { |
|
top: position.top < 0 ? 0 : position.top, |
|
left: position.left < 0 ? 0 : position.left, |
|
width: size.width, |
|
height: size.height |
|
}; |
|
this._setArrangeSize(p); |
|
var cur = this._getGridPositionAndSize(p); |
|
var layout = [{ |
|
x: 0, y: BI.MAX, w: cur.w, h: cur.h, i: cur.i |
|
}].concat(this._getLayoutsByRegions()); |
|
layout = this._moveElement(layout, layout[0], cur.x, cur.y, true); |
|
layout = this.compact(layout, true); |
|
var regions = this._setRegionsByLayout(this._cloneRegion(), layout); |
|
var insert = this._getBlockPositionAndSize(layout[0]); |
|
this.position = { |
|
insert: insert, |
|
regions: regions |
|
}; |
|
this._applyRegion(regions); |
|
this._setBlockPositionAndSize(insert); |
|
this._start(); |
|
break; |
|
} |
|
return this.position; |
|
}, |
|
|
|
setRegionPosition: function (name, position) { |
|
var self = this, o = this.options; |
|
var offset = this._getScrollOffset(); |
|
position = BI.extend(position, { |
|
left: position.left + offset.left, |
|
top: position.top + offset.top |
|
}); |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
BI.extend(this.regions[name], { |
|
left: position.left < 0 ? 0 : position.left, |
|
top: position.top < 0 ? 0 : position.top |
|
}); |
|
this._applyRegion(); |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
if (!position.stop) { |
|
BI.extend(this.regions[name], { |
|
left: position.left < 0 ? 0 : position.left, |
|
top: position.top < 0 ? 0 : position.top |
|
}); |
|
var cloned = this._cloneRegion(); |
|
var cur = this._getGridPositionAndSize(BI.extend(cloned[name], { |
|
left: position.left < 0 ? 0 : position.left, |
|
top: position.top < 0 ? 0 : position.top |
|
})); |
|
var x = cur.x, y = cur.y; |
|
cur = BI.extend(cur, { |
|
x: 0, y: BI.MAX, i: -1 |
|
}); |
|
delete cloned[name]; |
|
var layout = this._getLayoutsByRegions(cloned); |
|
layout = this._moveElement([cur].concat(layout), cur, x, y, true); |
|
layout = this.compact(layout, true); |
|
var regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
|
|
this._setBlockPositionAndSize(this._getBlockPositionAndSize(cur)); |
|
this.block.setVisible(true); |
|
} else { |
|
BI.extend(this.regions[name], { |
|
left: position.left < 0 ? 0 : position.left, |
|
top: position.top < 0 ? 0 : position.top |
|
}); |
|
var cloned = this._cloneRegion(); |
|
var layout = this._getLayoutsByRegions(cloned); |
|
layout = this.compact(layout, true); |
|
var regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
this.block.setVisible(false); |
|
} |
|
break; |
|
} |
|
}, |
|
|
|
setContainerSize: function (size) { |
|
var self = this, o = this.options; |
|
var occupied = this._getRegionOccupied(); |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (this._isArrangeFine()) { |
|
var width = size.width, height = size.height; |
|
var regions = this._cloneRegion(); |
|
BI.each(regions, function (i, region) { |
|
region.width = region.width / occupied.width * width; |
|
//region.height = region.height / occupied.height * height; |
|
}); |
|
BI.each(regions, function (id, region) { |
|
var lefts = self.locations[id].left; |
|
var tops = self.locations[id].top; |
|
var bottoms = self.locations[id].bottom; |
|
var maxRegion; |
|
if (lefts.length > 0) { |
|
var ids = self._getRegionNames(lefts); |
|
var rs = self._getRegionsByNames(ids); |
|
maxRegion = self._getRegionOccupied(rs); |
|
region.left = maxRegion.left + maxRegion.width / occupied.width * width; |
|
} else { |
|
region.left = 0; |
|
} |
|
if (bottoms.length === 0) { |
|
region.height = height - region.top; |
|
} |
|
//if (tops.length > 0) { |
|
// var ids = self._getRegionNames(tops); |
|
// var rs = self._getRegionsByNames(ids); |
|
// maxRegion = self._getRegionOccupied(rs); |
|
// region.top = maxRegion.top + maxRegion.height / occupied.height * height; |
|
//} |
|
//if (tops.length === 0) { |
|
// region.top = 0; |
|
//} |
|
}); |
|
if (this._test(regions)) { |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
} |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
break; |
|
} |
|
this.resize(); |
|
}, |
|
|
|
scrollTo: function (top) { |
|
this.scrollContainer.element.scrollTop(top); |
|
}, |
|
|
|
zoom: function (ratio) { |
|
var self = this, o = this.options; |
|
if (!ratio) { |
|
return; |
|
} |
|
var occupied = this._applyContainer(); |
|
switch (this.getLayoutType()) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (this._isArrangeFine()) { |
|
var width = this.getClientWidth(); |
|
var xRatio = (ratio.x || 1) * width / (occupied.left + occupied.width); |
|
//var yRatio = ratio.y * height / (occupied.top + occupied.height); |
|
var regions = this._cloneRegion(); |
|
BI.each(regions, function (i, region) { |
|
region.left = region.left * xRatio; |
|
//region.top = region.top * yRatio; |
|
region.width = region.width * xRatio; |
|
//region.height = region.height * yRatio; |
|
}); |
|
if (this._test(regions)) { |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
} |
|
this.resize(); |
|
// } else { |
|
this.relayout(); |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
if (this._isArrangeFine()) { |
|
var width = this.getClientWidth(); |
|
var xRatio = (ratio.x || 1) * width / (occupied.left + occupied.width); |
|
var regions = this._cloneRegion(); |
|
BI.each(regions, function (i, region) { |
|
region.left = region.left * xRatio; |
|
region.width = region.width * xRatio; |
|
}); |
|
if (this._test(regions)) { |
|
var layout = this._getLayoutsByRegions(regions); |
|
layout = this.compact(layout, true); |
|
regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
} |
|
} else { |
|
this.relayout(); |
|
} |
|
break; |
|
} |
|
}, |
|
|
|
resize: function () { |
|
var self = this, o = this.options; |
|
var occupied = this._applyContainer(); |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (this._isArrangeFine()) { |
|
var width = this.getClientWidth(), height = this.getClientHeight(); |
|
var isHeightAdjust = height > occupied.top + occupied.height; |
|
var regions = this._cloneRegion(); |
|
BI.each(regions, function (i, region) { |
|
region.width = region.width / occupied.width * width; |
|
//if (isHeightAdjust) { |
|
// region.height = region.height / occupied.height * height; |
|
//} |
|
}); |
|
BI.each(regions, function (id, region) { |
|
var lefts = self.locations[id].left; |
|
var tops = self.locations[id].top; |
|
var bottoms = self.locations[id].bottom; |
|
var maxRegion; |
|
if (lefts.length > 0) { |
|
var ids = self._getRegionNames(lefts); |
|
var rs = self._getRegionsByNames(ids); |
|
maxRegion = self._getRegionOccupied(rs); |
|
region.left = maxRegion.left + maxRegion.width / occupied.width * width; |
|
} else { |
|
region.left = 0; |
|
} |
|
if (tops.length === 0) { |
|
region.top = 0; |
|
} |
|
if (isHeightAdjust && bottoms.length === 0) { |
|
region.height = height - region.top; |
|
} |
|
//if (isHeightAdjust && tops.length > 0) { |
|
// var ids = self._getRegionNames(tops); |
|
// var rs = self._getRegionsByNames(ids); |
|
// maxRegion = self._getRegionOccupied(rs); |
|
// region.top = maxRegion.top + maxRegion.height / occupied.height * height; |
|
//} |
|
}); |
|
if (this._test(regions)) { |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
} |
|
} else { |
|
this.relayout(); |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
this.zoom(this.ratio); |
|
var regions = this._cloneRegion(); |
|
var layout = this._getLayoutsByRegions(regions); |
|
layout = this.compact(layout, true); |
|
regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
this._applyRegion(); |
|
break; |
|
} |
|
}, |
|
|
|
relayout: function () { |
|
var self = this, o = this.options; |
|
if (o.isNeedReLayout === false) { |
|
return; |
|
} |
|
//var occupied = this._applyContainer(); |
|
switch (o.layoutType) { |
|
case BI.Arrangement.LAYOUT_TYPE.ADAPTIVE: |
|
if (!this._isArrangeFine()) { |
|
var width = this.getClientWidth(), height = this.getClientHeight(); |
|
var clone = BI.toArray(this._cloneRegion()); |
|
clone.sort(function (r1, r2) { |
|
if (self._isEqual(r1.top, r2.top)) { |
|
return r1.left - r2.left; |
|
} |
|
return r1.top - r2.top; |
|
}); |
|
var count = clone.length; |
|
var cols = 3, rows = Math.floor((count - 1) / 3 + 1); |
|
var w = width / cols, h = height / rows; |
|
var store = {}; |
|
BI.each(clone, function (i, region) { |
|
var row = Math.floor(i / 3), col = i % 3; |
|
BI.extend(region, { |
|
top: row * 380, |
|
left: col * w, |
|
width: w, |
|
height: 380 |
|
}); |
|
if (!store[row]) { |
|
store[row] = {}; |
|
} |
|
store[row][col] = region; |
|
}); |
|
//非3的倍数 |
|
if (count % 3 !== 0) { |
|
var lasts = store[rows - 1]; |
|
var perWidth = width / (count % 3); |
|
BI.each(lasts, function (i, region) { |
|
BI.extend(region, { |
|
left: BI.parseInt(i) * perWidth, |
|
width: perWidth |
|
}); |
|
}); |
|
} |
|
if (this._test(clone)) { |
|
this._populate(clone); |
|
this.resize(); |
|
} |
|
} else { |
|
this.resize(); |
|
} |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.FREE: |
|
break; |
|
case BI.Arrangement.LAYOUT_TYPE.GRID: |
|
var width = this.getClientWidth(), height = this.getClientHeight(); |
|
var regions = this._cloneRegion(); |
|
var clone = BI.toArray(regions); |
|
clone.sort(function (r1, r2) { |
|
if (self._isEqual(r1.top, r2.top)) { |
|
return r1.left - r2.left; |
|
} |
|
return r1.top - r2.top; |
|
}); |
|
var count = clone.length; |
|
var cols = 3, rows = Math.floor((count - 1) / 3 + 1); |
|
var w = width / cols, h = height / rows; |
|
var store = {}; |
|
BI.each(clone, function (i, region) { |
|
var row = Math.floor(i / 3), col = i % 3; |
|
BI.extend(region, { |
|
top: row * 380, |
|
left: col * w, |
|
width: w, |
|
height: 380 |
|
}); |
|
if (!store[row]) { |
|
store[row] = {}; |
|
} |
|
store[row][col] = region; |
|
}); |
|
//非3的倍数 |
|
if (count % 3 !== 0) { |
|
var lasts = store[rows - 1]; |
|
var perWidth = width / (count % 3); |
|
BI.each(lasts, function (i, region) { |
|
BI.extend(region, { |
|
left: BI.parseInt(i) * perWidth, |
|
width: perWidth |
|
}); |
|
}); |
|
} |
|
if (this._test(clone)) { |
|
var layout = this._getLayoutsByRegions(regions); |
|
layout = this.compact(layout, true); |
|
regions = this._getRegionsByLayout(layout); |
|
this._modifyRegion(regions); |
|
this._populate(clone); |
|
} |
|
break; |
|
} |
|
}, |
|
|
|
_populate: function (items) { |
|
this._stop(); |
|
this._calculateRegions(items); |
|
this._locationRegion(); |
|
this._applyRegion(); |
|
}, |
|
|
|
populate: function (items) { |
|
var self = this; |
|
BI.each(this.regions, function (name, region) { |
|
self.regions[name].el.setVisible(false); |
|
self.drops[name].el.setVisible(false); |
|
delete self.regions[name]; |
|
delete self.drops[name]; |
|
}); |
|
this._populate(items); |
|
this._renderRegion(); |
|
} |
|
}); |
|
BI.Arrangement.EVENT_SCROLL = "EVENT_SCROLL"; |
|
BI.extend(BI.Arrangement, { |
|
PORTION: 24, |
|
GRID_HEIGHT: 50, |
|
LAYOUT_TYPE: { |
|
ADAPTIVE: 0, |
|
FREE: 1, |
|
GRID: 2 |
|
} |
|
}); |
|
BI.shortcut('bi.arrangement', BI.Arrangement); |