init
This commit is contained in:
250
public/tinymce/classes/ui/FlexLayout.js
Normal file
250
public/tinymce/classes/ui/FlexLayout.js
Normal file
@ -0,0 +1,250 @@
|
||||
/**
|
||||
* FlexLayout.js
|
||||
*
|
||||
* Copyright, Moxiecode Systems AB
|
||||
* Released under LGPL License.
|
||||
*
|
||||
* License: http://www.tinymce.com/license
|
||||
* Contributing: http://www.tinymce.com/contributing
|
||||
*/
|
||||
|
||||
/**
|
||||
* This layout manager works similar to the CSS flex box.
|
||||
*
|
||||
* @setting {String} direction row|row-reverse|column|column-reverse
|
||||
* @setting {Number} flex A positive-number to flex by.
|
||||
* @setting {String} align start|end|center|stretch
|
||||
* @setting {String} pack start|end|justify
|
||||
*
|
||||
* @class tinymce.ui.FlexLayout
|
||||
* @extends tinymce.ui.AbsoluteLayout
|
||||
*/
|
||||
define("tinymce/ui/FlexLayout", [
|
||||
"tinymce/ui/AbsoluteLayout"
|
||||
], function(AbsoluteLayout) {
|
||||
"use strict";
|
||||
|
||||
return AbsoluteLayout.extend({
|
||||
/**
|
||||
* Recalculates the positions of the controls in the specified container.
|
||||
*
|
||||
* @method recalc
|
||||
* @param {tinymce.ui.Container} container Container instance to recalc.
|
||||
*/
|
||||
recalc: function(container) {
|
||||
// A ton of variables, needs to be in the same scope for performance
|
||||
var i, l, items, contLayoutRect, contPaddingBox, contSettings, align, pack, spacing, totalFlex, availableSpace, direction;
|
||||
var ctrl, ctrlLayoutRect, ctrlSettings, flex, maxSizeItems = [], size, maxSize, ratio, rect, pos, maxAlignEndPos;
|
||||
var sizeName, minSizeName, posName, maxSizeName, beforeName, innerSizeName, afterName, deltaSizeName, contentSizeName;
|
||||
var alignAxisName, alignInnerSizeName, alignSizeName, alignMinSizeName, alignMaxSizeName, alignBeforeName, alignAfterName;
|
||||
var alignDeltaSizeName, alignContentSizeName;
|
||||
var max = Math.max, min = Math.min;
|
||||
|
||||
// Get container items, properties and settings
|
||||
items = container.items().filter(':visible');
|
||||
contLayoutRect = container.layoutRect();
|
||||
contPaddingBox = container._paddingBox;
|
||||
contSettings = container.settings;
|
||||
direction = container.isRtl() ? (contSettings.direction || 'row-reversed') : contSettings.direction;
|
||||
align = contSettings.align;
|
||||
pack = container.isRtl() ? (contSettings.pack || 'end') : contSettings.pack;
|
||||
spacing = contSettings.spacing || 0;
|
||||
|
||||
if (direction == "row-reversed" || direction == "column-reverse") {
|
||||
items = items.set(items.toArray().reverse());
|
||||
direction = direction.split('-')[0];
|
||||
}
|
||||
|
||||
// Setup axis variable name for row/column direction since the calculations is the same
|
||||
if (direction == "column") {
|
||||
posName = "y";
|
||||
sizeName = "h";
|
||||
minSizeName = "minH";
|
||||
maxSizeName = "maxH";
|
||||
innerSizeName = "innerH";
|
||||
beforeName = 'top';
|
||||
afterName = 'bottom';
|
||||
deltaSizeName = "deltaH";
|
||||
contentSizeName = "contentH";
|
||||
|
||||
alignBeforeName = "left";
|
||||
alignSizeName = "w";
|
||||
alignAxisName = "x";
|
||||
alignInnerSizeName = "innerW";
|
||||
alignMinSizeName = "minW";
|
||||
alignMaxSizeName = "maxW";
|
||||
alignAfterName = "right";
|
||||
alignDeltaSizeName = "deltaW";
|
||||
alignContentSizeName = "contentW";
|
||||
} else {
|
||||
posName = "x";
|
||||
sizeName = "w";
|
||||
minSizeName = "minW";
|
||||
maxSizeName = "maxW";
|
||||
innerSizeName = "innerW";
|
||||
beforeName = 'left';
|
||||
afterName = 'right';
|
||||
deltaSizeName = "deltaW";
|
||||
contentSizeName = "contentW";
|
||||
|
||||
alignBeforeName = "top";
|
||||
alignSizeName = "h";
|
||||
alignAxisName = "y";
|
||||
alignInnerSizeName = "innerH";
|
||||
alignMinSizeName = "minH";
|
||||
alignMaxSizeName = "maxH";
|
||||
alignAfterName = "bottom";
|
||||
alignDeltaSizeName = "deltaH";
|
||||
alignContentSizeName = "contentH";
|
||||
}
|
||||
|
||||
// Figure out total flex, availableSpace and collect any max size elements
|
||||
availableSpace = contLayoutRect[innerSizeName] - contPaddingBox[beforeName] - contPaddingBox[beforeName];
|
||||
maxAlignEndPos = totalFlex = 0;
|
||||
for (i = 0, l = items.length; i < l; i++) {
|
||||
ctrl = items[i];
|
||||
ctrlLayoutRect = ctrl.layoutRect();
|
||||
ctrlSettings = ctrl.settings;
|
||||
flex = ctrlSettings.flex;
|
||||
availableSpace -= (i < l - 1 ? spacing : 0);
|
||||
|
||||
if (flex > 0) {
|
||||
totalFlex += flex;
|
||||
|
||||
// Flexed item has a max size then we need to check if we will hit that size
|
||||
if (ctrlLayoutRect[maxSizeName]) {
|
||||
maxSizeItems.push(ctrl);
|
||||
}
|
||||
|
||||
ctrlLayoutRect.flex = flex;
|
||||
}
|
||||
|
||||
availableSpace -= ctrlLayoutRect[minSizeName];
|
||||
|
||||
// Calculate the align end position to be used to check for overflow/underflow
|
||||
size = contPaddingBox[alignBeforeName] + ctrlLayoutRect[alignMinSizeName] + contPaddingBox[alignAfterName];
|
||||
if (size > maxAlignEndPos) {
|
||||
maxAlignEndPos = size;
|
||||
}
|
||||
}
|
||||
|
||||
// Calculate minW/minH
|
||||
rect = {};
|
||||
if (availableSpace < 0) {
|
||||
rect[minSizeName] = contLayoutRect[minSizeName] - availableSpace + contLayoutRect[deltaSizeName];
|
||||
} else {
|
||||
rect[minSizeName] = contLayoutRect[innerSizeName] - availableSpace + contLayoutRect[deltaSizeName];
|
||||
}
|
||||
|
||||
rect[alignMinSizeName] = maxAlignEndPos + contLayoutRect[alignDeltaSizeName];
|
||||
|
||||
rect[contentSizeName] = contLayoutRect[innerSizeName] - availableSpace;
|
||||
rect[alignContentSizeName] = maxAlignEndPos;
|
||||
rect.minW = min(rect.minW, contLayoutRect.maxW);
|
||||
rect.minH = min(rect.minH, contLayoutRect.maxH);
|
||||
rect.minW = max(rect.minW, contLayoutRect.startMinWidth);
|
||||
rect.minH = max(rect.minH, contLayoutRect.startMinHeight);
|
||||
|
||||
// Resize container container if minSize was changed
|
||||
if (contLayoutRect.autoResize && (rect.minW != contLayoutRect.minW || rect.minH != contLayoutRect.minH)) {
|
||||
rect.w = rect.minW;
|
||||
rect.h = rect.minH;
|
||||
|
||||
container.layoutRect(rect);
|
||||
this.recalc(container);
|
||||
|
||||
// Forced recalc for example if items are hidden/shown
|
||||
if (container._lastRect === null) {
|
||||
var parentCtrl = container.parent();
|
||||
if (parentCtrl) {
|
||||
parentCtrl._lastRect = null;
|
||||
parentCtrl.recalc();
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// Handle max size elements, check if they will become to wide with current options
|
||||
ratio = availableSpace / totalFlex;
|
||||
for (i = 0, l = maxSizeItems.length; i < l; i++) {
|
||||
ctrl = maxSizeItems[i];
|
||||
ctrlLayoutRect = ctrl.layoutRect();
|
||||
maxSize = ctrlLayoutRect[maxSizeName];
|
||||
size = ctrlLayoutRect[minSizeName] + Math.ceil(ctrlLayoutRect.flex * ratio);
|
||||
|
||||
if (size > maxSize) {
|
||||
availableSpace -= (ctrlLayoutRect[maxSizeName] - ctrlLayoutRect[minSizeName]);
|
||||
totalFlex -= ctrlLayoutRect.flex;
|
||||
ctrlLayoutRect.flex = 0;
|
||||
ctrlLayoutRect.maxFlexSize = maxSize;
|
||||
} else {
|
||||
ctrlLayoutRect.maxFlexSize = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// Setup new ratio, target layout rect, start position
|
||||
ratio = availableSpace / totalFlex;
|
||||
pos = contPaddingBox[beforeName];
|
||||
rect = {};
|
||||
|
||||
// Handle pack setting moves the start position to end, center
|
||||
if (totalFlex === 0) {
|
||||
if (pack == "end") {
|
||||
pos = availableSpace + contPaddingBox[beforeName];
|
||||
} else if (pack == "center") {
|
||||
pos = Math.round(
|
||||
(contLayoutRect[innerSizeName] / 2) - ((contLayoutRect[innerSizeName] - availableSpace) / 2)
|
||||
) + contPaddingBox[beforeName];
|
||||
|
||||
if (pos < 0) {
|
||||
pos = contPaddingBox[beforeName];
|
||||
}
|
||||
} else if (pack == "justify") {
|
||||
pos = contPaddingBox[beforeName];
|
||||
spacing = Math.floor(availableSpace / (items.length - 1));
|
||||
}
|
||||
}
|
||||
|
||||
// Default aligning (start) the other ones needs to be calculated while doing the layout
|
||||
rect[alignAxisName] = contPaddingBox[alignBeforeName];
|
||||
|
||||
// Start laying out controls
|
||||
for (i = 0, l = items.length; i < l; i++) {
|
||||
ctrl = items[i];
|
||||
ctrlLayoutRect = ctrl.layoutRect();
|
||||
size = ctrlLayoutRect.maxFlexSize || ctrlLayoutRect[minSizeName];
|
||||
|
||||
// Align the control on the other axis
|
||||
if (align === "center") {
|
||||
rect[alignAxisName] = Math.round((contLayoutRect[alignInnerSizeName] / 2) - (ctrlLayoutRect[alignSizeName] / 2));
|
||||
} else if (align === "stretch") {
|
||||
rect[alignSizeName] = max(
|
||||
ctrlLayoutRect[alignMinSizeName] || 0,
|
||||
contLayoutRect[alignInnerSizeName] - contPaddingBox[alignBeforeName] - contPaddingBox[alignAfterName]
|
||||
);
|
||||
rect[alignAxisName] = contPaddingBox[alignBeforeName];
|
||||
} else if (align === "end") {
|
||||
rect[alignAxisName] = contLayoutRect[alignInnerSizeName] - ctrlLayoutRect[alignSizeName] - contPaddingBox.top;
|
||||
}
|
||||
|
||||
// Calculate new size based on flex
|
||||
if (ctrlLayoutRect.flex > 0) {
|
||||
size += Math.ceil(ctrlLayoutRect.flex * ratio);
|
||||
}
|
||||
|
||||
rect[sizeName] = size;
|
||||
rect[posName] = pos;
|
||||
ctrl.layoutRect(rect);
|
||||
|
||||
// Recalculate containers
|
||||
if (ctrl.recalc) {
|
||||
ctrl.recalc();
|
||||
}
|
||||
|
||||
// Move x/y position
|
||||
pos += size + spacing;
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
Reference in New Issue
Block a user