Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Complex-Dom] Combine visibility: hidden and display: none for side TreeView hidden elements. #327

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion resources/todomvc/big-dom-generator/dist/index.html

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions resources/todomvc/big-dom-generator/params.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,3 +16,4 @@ export const TARGET_SIZE = 6000;
// at least MIN_NUMBER_OF_MAX_DEPTH_BRANCHES of depth MAX_GENERATED_DOM_DEPTH.
export const MIN_NUMBER_OF_MAX_DEPTH_BRANCHES = 2;
export const MAX_VISIBLE_TREE_VIEW_ITEM_DEPTH = 8;
export const PERCENTAGE_OF_DISPLAY_NONE_TREEVIEW_ELEMENTS = 0.5;
26 changes: 26 additions & 0 deletions resources/todomvc/big-dom-generator/src/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,32 @@ Importing the CSS from the Spectrum CSS library.
min-width: 30px;
}

/*
The visibility of closed spectrum TreeView items is set to hidden
and the spectrum rule making the open TreeView items visible is
.spectrum-TreeView-item.is-open > .spectrum-TreeView {
visibility: visible;
}
This can cause descendants of closed tree view items to be visible.
Our code only closes the TreeView items at the threshold depth of
the tree, so we unset the visibility to let the open itmes inherit
the visibility from their parents.
*/
.spectrum-TreeView-item.is-open > .spectrum-TreeView {
visibility: unset;
}
lpardosixtosMs marked this conversation as resolved.
Show resolved Hide resolved

/*
We've chosen some items of the side TreeView to be hidden using
display: none instead of visibility: hidden. We unset their visibility
and height values set by spectrum CSS.
*/
.display-none {
display: none;
visibility: unset !important;
height: auto !important;
}

/*
Layout CSS for the UI.
*/
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { MAX_VISIBLE_TREE_VIEW_ITEM_DEPTH } from "../../params";
import { generateTreeHead } from "./../tree-generator";
import classNames from "classnames";

import ChevronRight from "./../assets/Smock_ChevronRight_18_N.svg";
import TaskListIcon from "./../assets/Smock_TaskList_18_N.svg";
Expand All @@ -8,10 +9,14 @@ const TreeItem = (props) => {
const { treeNode, currentDepth } = props;

const isExpandableItem = treeNode.type === "expandableItem";
const treeViewItemIsOpen = isExpandableItem && currentDepth < MAX_VISIBLE_TREE_VIEW_ITEM_DEPTH ? "is-open" : "";
/**
* Every expandable TreeItem is open by default unless it is at the MAX_VISIBLE_TREE_VIEW_ITEM_DEPTH threshold
* or it is marked as display:none.
**/
const treeViewItemIsOpen = isExpandableItem && currentDepth !== MAX_VISIBLE_TREE_VIEW_ITEM_DEPTH && !treeNode.isDisplayNone;

return (
<li className={`spectrum-TreeView-item ${treeViewItemIsOpen} nodetype-${treeNode.type}`}>
<li className={classNames("spectrum-TreeView-item", { "display-none": treeNode.isDisplayNone, "is-open": treeViewItemIsOpen }, `nodetype-${treeNode.type}`)}>
{isExpandableItem
? <>
<a className="spectrum-TreeView-itemLink">
Expand Down
68 changes: 63 additions & 5 deletions resources/todomvc/big-dom-generator/src/tree-generator.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,58 @@
import { LCG } from "random-seedable";
import { DEFAULT_SEED_FOR_RANDOM_NUMBER_GENERATOR, MAX_GENERATED_DOM_DEPTH, MAX_NUMBER_OF_CHILDREN, PROBABILITY_OF_HAVING_CHILDREN, TARGET_SIZE, MIN_NUMBER_OF_MAX_DEPTH_BRANCHES } from "./../params";
import { DEFAULT_SEED_FOR_RANDOM_NUMBER_GENERATOR, MAX_GENERATED_DOM_DEPTH, MAX_NUMBER_OF_CHILDREN, PROBABILITY_OF_HAVING_CHILDREN, TARGET_SIZE, MIN_NUMBER_OF_MAX_DEPTH_BRANCHES, PERCENTAGE_OF_DISPLAY_NONE_TREEVIEW_ELEMENTS } from "./../params";

const random = new LCG(DEFAULT_SEED_FOR_RANDOM_NUMBER_GENERATOR);

// Recursively depth-first computing subTreeWeight.
const fillSubtreeWeights = (node, expandableItemWeight, nonExpandableItemWeight) => {
lpardosixtosMs marked this conversation as resolved.
Show resolved Hide resolved
if (node.type === "expandableItem")
node.subTreeWeight = node.children.reduce((acc, child) => acc + fillSubtreeWeights(child, expandableItemWeight, nonExpandableItemWeight), expandableItemWeight);
else
node.subTreeWeight = nonExpandableItemWeight;

return node.subTreeWeight;
};

/*
* Iterate over the exapandableItem nodes in a breadth-first manner until the
* sum of weights of the subtrees with root nodes in the queue is less than
* the target number of elements we want to have display none. Mark the
* nodes in the queue as display none.
* Consider the following example with the weights as displayed in the figure
* and 10 as the target number of display none elements. The iteration will
* stop with the nodes with weights 7 and 2 marked with *.
* 20
* / \
* 12 8
* / \ / \
* 5 *7* *2* 6
* / / \
* 7 1 1
*/
const markDisplayNoneNodes = (node, expandableItemWeight, nonExpandableItemWeight) => {
lpardosixtosMs marked this conversation as resolved.
Show resolved Hide resolved
let currentSubTreesWeights = node.subTreeWeight;
let currentIndex = 0;
let nodeQueue = [node];
while (currentSubTreesWeights >= TARGET_SIZE * PERCENTAGE_OF_DISPLAY_NONE_TREEVIEW_ELEMENTS) {
const currentNode = nodeQueue[currentIndex];
nodeQueue[currentIndex] = null;
const expandableChildren = currentNode.children.filter((child) => child.type === "expandableItem");
if (expandableChildren.length) {
nodeQueue.push(...expandableChildren);
currentSubTreesWeights -= expandableItemWeight;
let numberOfNonExpandableChildren = currentNode.children.length - expandableChildren.length;
currentSubTreesWeights -= numberOfNonExpandableChildren * nonExpandableItemWeight;
} else {
currentSubTreesWeights -= currentNode.subTreeWeight;
}
currentIndex++;
}
nodeQueue.forEach((node) => {
if (node)
node.isDisplayNone = true;
});
};

/**
* Generates the blueprint of the tree-view side panel for the complex DOM shell with expandable and non-expandable items.
* It starts with the minimum number of maximum-depth branches and randomly adds
Expand All @@ -21,15 +71,21 @@ const random = new LCG(DEFAULT_SEED_FOR_RANDOM_NUMBER_GENERATOR);
* children: [
* {
* type: "nonExpandableItem",
* children: []
* children: [],
* isDisplayNone: false,
* subTreeWeight: 0,
* }
* ]
* ],
* isDisplayNone: false,
* subTreeWeight: 0,
* }
* ]
* ],
* isDisplayNone: false,
* subTreeWeight: 0,
* }
**/
export const generateTreeHead = ({ expandableItemWeight, nonExpandableItemWeight }) => {
const treeHead = { type: "expandableItem", children: [] };
const treeHead = { type: "expandableItem", children: [], isDisplayNone: false, subTreeWeight: 0 };
const nodeWeight = { expandableItem: expandableItemWeight, nonExpandableItem: nonExpandableItemWeight };

let totalNodes = expandableItemWeight;
Expand Down Expand Up @@ -85,5 +141,7 @@ export const generateTreeHead = ({ expandableItemWeight, nonExpandableItemWeight
}
}

fillSubtreeWeights(treeHead, expandableItemWeight, nonExpandableItemWeight);
markDisplayNoneNodes(treeHead, expandableItemWeight, nonExpandableItemWeight);
return treeHead;
};

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.

Large diffs are not rendered by default.