diff --git a/src/frontend/common/stylesheet/dimensions.scss b/src/frontend/common/stylesheet/dimensions.scss
index 2c4d99c6c88e22634778d23a3104161a48a7de5c..d1bea7a2bd4883aae558d63861ec448e950ab2c1 100644
--- a/src/frontend/common/stylesheet/dimensions.scss
+++ b/src/frontend/common/stylesheet/dimensions.scss
@@ -1,3 +1,9 @@
$line-height: 32px;
$font-size-normal: 12px;
-$font-size-large: 14px;
\ No newline at end of file
+$font-size-large: 14px;
+
+:export {
+ lineHeight: $line-height;
+ fontSizeNormal: $font-size-normal;
+ fontSizeLarge: $font-size-large;
+}
\ No newline at end of file
diff --git a/src/frontend/components/App/index.jsx b/src/frontend/components/App/index.jsx
index 601197b9d172ba480ac09776cd1487f104d57920..23d43b04834f323f3de79f046195de89f79748ce 100644
--- a/src/frontend/components/App/index.jsx
+++ b/src/frontend/components/App/index.jsx
@@ -94,13 +94,22 @@ class App extends React.Component {
return categories && categoryKey && algorithmKey && (
- this.navigatorReference.core.setVisible(!this.navigatorReference.core.visible)}
navigatorOpened={navigatorOpened} />
-
+
child.visible);
- const weights = visibleChildren.map(section => section.weight);
- const totalWeight = weights.reduce((sumWeight, weight) => sumWeight + weight, 0);
+ const totalWeight = visibleChildren.reduce((sumWeight, child) => sumWeight + (child.relative ? child.weight : 0), 0);
const elements = [];
- children.forEach((child, i) => {
- if (!child.visible) return;
- const visibleIndex = visibleChildren.findIndex(visibleChild => visibleChild === child);
- const portion = child.weight / totalWeight;
- const style = { flex: portion };
- if (elements.length) {
+ visibleChildren.forEach((child, visibleIndex) => {
+ const index = children.indexOf(child);
+ elements.push(
+ 0 && ((target, dx, dy) => this.handleResize(visibleIndex, target, dx, dy))}
+ onDropTab={tab => this.handleDropTabToContainer(tab, index)}
+ onDropSection={section => this.handleDropSectionToContainer(section, index)} />
+ );
+ const style = child.relative ? {
+ flexGrow: child.weight / totalWeight,
+ } : {
+ flexGrow: 0,
+ flexBasis: child.size,
+ };
+ if (children.length === 1) {
+ elements.push(
+
+ {child.element}
+
+ );
+ } else {
elements.push(
- this.handleResize(visibleIndex - 1, target, x, y)}
- onDropTab={tab => this.handleDropTabToContainer(tab, i)}
- onDropSection={section => this.handleDropSectionToContainer(section, i)} />
+
+
this.handleDropTabToSection(tab, index, true)}
+ onDropSection={section => this.handleDropSectionToSection(section, index, true)} />
+ {child.element}
+ this.handleDropTabToSection(tab, index)}
+ onDropSection={section => this.handleDropSectionToSection(section, index)} />
+
+ );
+ }
+ if (visibleIndex === visibleChildren.length - 1) {
+ elements.push(
+ this.handleDropTabToContainer(tab, index + 1)}
+ onDropSection={section => this.handleDropSectionToContainer(section, index + 1)} />
);
}
- elements.push(
-
-
this.handleDropTabToSection(tab, i, true)}
- onDropSection={section => this.handleDropSectionToSection(section, i, true)} />
- {child.element}
- this.handleDropTabToSection(tab, i)}
- onDropSection={section => this.handleDropSectionToSection(section, i)} />
-
- );
});
- if (elements.length) {
- const firstIndex = children.indexOf(visibleChildren[0]);
- const lastIndex = children.indexOf(visibleChildren[visibleChildren.length - 1]);
- elements.unshift(
- this.handleDropTabToContainer(tab, firstIndex)}
- onDropSection={section => this.handleDropSectionToContainer(section, firstIndex)} />
- );
- elements.push(
- this.handleDropTabToContainer(tab, lastIndex + 1)}
- onDropSection={section => this.handleDropSectionToContainer(section, lastIndex + 1)} />
- );
- } else {
- elements.push(
- this.handleDropTabToContainer(tab)}
- onDropSection={section => this.handleDropSectionToContainer(section)} />
- );
- }
return (
- {elements}
+ {
+ elements.length ?
+ elements : (
+ this.handleDropTabToContainer(tab)}
+ onDropSection={section => this.handleDropSectionToContainer(section)} />
+ )
+ }
);
}
diff --git a/src/frontend/workspace/components/WSTabContainer/stylesheet.scss b/src/frontend/workspace/components/WSTabContainer/stylesheet.scss
index 4a1148162938d19b5d2354171bda57a77aa14df8..0012fdbcae886b917afdb1626103cf7b7dab62f5 100644
--- a/src/frontend/workspace/components/WSTabContainer/stylesheet.scss
+++ b/src/frontend/workspace/components/WSTabContainer/stylesheet.scss
@@ -25,7 +25,7 @@
display: flex;
align-items: stretch;
height: $line-height;
- overflow-x: scroll;
+ overflow-x: auto;
white-space: nowrap;
flex-shrink: 0;
cursor: move;
diff --git a/src/frontend/workspace/core/Child.js b/src/frontend/workspace/core/Child.js
index 7fe6138a871bff65b47233bd84cbbc8973acf830..661417470e9ec38bd07f03676adf4c84067d204a 100644
--- a/src/frontend/workspace/core/Child.js
+++ b/src/frontend/workspace/core/Child.js
@@ -7,6 +7,7 @@ class Child {
return {
reference: Workspace.createReference(),
removable: true,
+ movable: true, // TODO:
};
}
diff --git a/src/frontend/workspace/core/Section.js b/src/frontend/workspace/core/Section.js
index a686af550d452eb1fb7264e20bc6b028dee6bdc4..207c08a5d1f1aaa19c7f3c6c4c1c833cc750255d 100644
--- a/src/frontend/workspace/core/Section.js
+++ b/src/frontend/workspace/core/Section.js
@@ -4,11 +4,22 @@ class Section extends Child {
getDefaultProps() {
return {
...super.getDefaultProps(),
- weight: 1,
visible: true,
+ resizable: true,
+ weight: 1,
+ minWeight: 0,
+ maxWeight: Number.MAX_VALUE,
+ size: -1,
+ minSize: 0,
+ maxSize: Number.MAX_VALUE,
};
}
+ constructor(element) {
+ super(element);
+ this.relative = this.size === -1;
+ }
+
setVisible(visible) {
this.visible = visible;
this.parent.render();
diff --git a/src/frontend/workspace/core/SectionContainer.js b/src/frontend/workspace/core/SectionContainer.js
index a79b77245b1bac8baa883cd7888cea4c603e5b65..3ecf541be81cb33e71e573f848e31a97207ede0f 100644
--- a/src/frontend/workspace/core/SectionContainer.js
+++ b/src/frontend/workspace/core/SectionContainer.js
@@ -37,35 +37,54 @@ class SectionContainer extends parentMixin(Section) {
}
}
- resizeChild(index, position, size) {
+ resizeChild(index, position, containerSize) {
const visibleChildren = this.children.filter(child => child.visible);
- const weights = visibleChildren.map(child => child.weight);
- const totalWeight = weights.reduce((sumWeight, weight) => sumWeight + weight, 0);
-
- const startWeight = weights.slice(0, index).reduce((sumWeight, weight) => sumWeight + weight, 0);
- const endWeight = position / size * totalWeight;
-
- const oldWeight = weights[index];
- const newWeight = endWeight - startWeight;
-
- const oldScale = totalWeight - startWeight - oldWeight;
- const newScale = totalWeight - startWeight - newWeight;
- const ratio = newScale / oldScale;
-
- weights[index] = newWeight;
- for (let i = index + 1; i < weights.length; i++) {
- weights[i] *= ratio;
+ let prevChild = visibleChildren.slice(0, index).reverse().find(child => child.resizable);
+ let nextChild = visibleChildren.slice(index).find(child => child.resizable);
+ if (prevChild && nextChild) {
+ let totalSize = 0;
+ let totalWeight = 0;
+ let subtotalSize = 0;
+ let subtotalWeight = 0;
+ visibleChildren.forEach((child, i) => {
+ if (child.relative) {
+ totalWeight += child.weight;
+ if (i < index) subtotalWeight += child.weight;
+ } else {
+ totalSize += child.size;
+ if (i < index) subtotalSize += child.size;
+ }
+ });
+ const factor = (containerSize - totalSize) / totalWeight;
+ const oldPosition = subtotalSize + subtotalWeight * factor;
+ let deltaSize = position - oldPosition;
+ if (prevChild.relative) {
+ deltaSize = Math.max((prevChild.minWeight - prevChild.weight) * factor, deltaSize);
+ deltaSize = Math.min((prevChild.maxWeight - prevChild.weight) * factor, deltaSize);
+ } else {
+ deltaSize = Math.max(prevChild.minSize - prevChild.size, deltaSize);
+ deltaSize = Math.min(prevChild.maxSize - prevChild.size, deltaSize);
+ }
+ if (nextChild.relative) {
+ deltaSize = Math.min((nextChild.weight - nextChild.minWeight) * factor, deltaSize);
+ deltaSize = Math.max((nextChild.weight - nextChild.maxWeight) * factor, deltaSize);
+ } else {
+ deltaSize = Math.min(nextChild.size - nextChild.minSize, deltaSize);
+ deltaSize = Math.max(nextChild.size - nextChild.maxSize, deltaSize);
+ }
+ const deltaWeight = deltaSize / factor;
+ if (prevChild.relative) {
+ prevChild.weight += deltaWeight;
+ } else {
+ prevChild.size += deltaSize;
+ }
+ if (nextChild.relative) {
+ nextChild.weight -= deltaWeight;
+ } else {
+ nextChild.size -= deltaSize;
+ }
+ this.render();
}
-
- for (let i = index; i < weights.length; i++) {
- if (weights[i] / totalWeight * size < 20) return;
- }
-
- for (let i = index; i < weights.length; i++) {
- visibleChildren[i].weight = weights[i];
- }
-
- this.render();
}
}
diff --git a/src/frontend/workspace/core/TabContainer.js b/src/frontend/workspace/core/TabContainer.js
index 5dbc2d1ca6742ade8201834e277d46b2159f45b4..6f78c1516870181de2e53738250afc9e0c138492 100644
--- a/src/frontend/workspace/core/TabContainer.js
+++ b/src/frontend/workspace/core/TabContainer.js
@@ -22,13 +22,15 @@ class TabContainer extends parentMixin(Section) {
}
addChild(child, index = this.children.length) {
- super.addChild(child, index);
- this.setTabIndex(Math.min(index, this.children.length - 1));
+ super.addChild(child, index, () => {
+ this.setTabIndex(Math.min(index, this.children.length - 1));
+ });
}
removeChild(index) {
- super.removeChild(index);
- this.setTabIndex(Math.min(this.tabIndex, this.children.length - 1));
+ super.removeChild(index, () => {
+ this.setTabIndex(Math.min(this.tabIndex, this.children.length - 1));
+ });
}
setTabIndex(tabIndex) {
diff --git a/src/frontend/workspace/core/mixins/parentMixin.js b/src/frontend/workspace/core/mixins/parentMixin.js
index 643c576035817b352a2fe956b936a5ea5116a881..abc55d93808877663b57f0ff48c473f8a07dd67d 100644
--- a/src/frontend/workspace/core/mixins/parentMixin.js
+++ b/src/frontend/workspace/core/mixins/parentMixin.js
@@ -13,7 +13,7 @@ const parentMixin = (Base = Child) => class Parent extends Base {
return new Child(element);
}
- addChild(child, index = this.children.length) {
+ addChild(child, index = this.children.length, beforeRender) {
if (child.parent === this) {
const oldIndex = this.children.indexOf(child);
this.children[oldIndex] = null;
@@ -23,12 +23,14 @@ const parentMixin = (Base = Child) => class Parent extends Base {
this.children.splice(index, 0, child);
child.setParent(this);
}
+ if(beforeRender) beforeRender();
this.render();
}
- removeChild(index) {
+ removeChild(index, beforeRender) {
this.children.splice(index, 1);
if (this.children.length === 0) this.remove();
+ if(beforeRender) beforeRender();
this.render();
}