Skip to content

Commit c6a0c4c

Browse files
committed
Random item placement so things don’t get too small.
Add opacity to prevent optimizations based on occlusion.
1 parent dbbe344 commit c6a0c4c

File tree

2 files changed

+20
-136
lines changed

2 files changed

+20
-136
lines changed

MotionMark/tests/dev/stories/resources/stories.js

Lines changed: 19 additions & 136 deletions
Original file line numberDiff line numberDiff line change
@@ -255,131 +255,6 @@ class BoxItem {
255255
}
256256
}
257257

258-
class LayoutState {
259-
constructor(position, size)
260-
{
261-
this.currentPosition = position;
262-
this.remainingSize = size;
263-
}
264-
}
265-
266-
class TreeMapLayout {
267-
constructor(areaSize, data)
268-
{
269-
this.areaSize = areaSize;
270-
this.originalData = data;
271-
this.data = this.#normalizeData(this.originalData);
272-
}
273-
274-
#normalizeData(data)
275-
{
276-
const factor = (this.areaSize.width * this.areaSize.height) / data.sum();
277-
return data.map((x) => (x * factor));
278-
}
279-
280-
layout()
281-
{
282-
this.layoutResults = [];
283-
const inputData = [...this.data];
284-
this.#squarishLayoutIterative(inputData);
285-
}
286-
287-
#squarishLayoutIterative(items)
288-
{
289-
const layoutState = new LayoutState(new Point(0, 0), structuredClone(this.areaSize));
290-
const remainingItems = [...items];
291-
let itemsInCurrentRow = [];
292-
293-
let { value: availableSpace, vertical: currentlyVertical } = TreeMapLayout.#getSmallerDimension(layoutState.remainingSize);
294-
295-
while (remainingItems.length > 1) {
296-
const rowWithChild = [...itemsInCurrentRow, remainingItems[0]]
297-
298-
if (itemsInCurrentRow.length === 0 || TreeMapLayout.#worstRatio(itemsInCurrentRow, availableSpace) >= TreeMapLayout.#worstRatio(rowWithChild, availableSpace)) {
299-
remainingItems.shift();
300-
itemsInCurrentRow = rowWithChild;
301-
continue;
302-
}
303-
304-
this.#layoutRow(itemsInCurrentRow, availableSpace, currentlyVertical, layoutState);
305-
({ value: availableSpace, vertical: currentlyVertical } = TreeMapLayout.#getSmallerDimension(layoutState.remainingSize));
306-
307-
itemsInCurrentRow = [];
308-
}
309-
310-
this.#layoutLastRow(itemsInCurrentRow, remainingItems, availableSpace, layoutState);
311-
}
312-
313-
static #worstRatio(rowValues, width)
314-
{
315-
const rowMax = rowValues.max();
316-
const rowMin = rowValues.min();
317-
const sumSquared = Math.pow(rowValues.sum(), 2);
318-
const widthSquared = Math.pow(width, 2);
319-
return Math.max((widthSquared * rowMax) / sumSquared, sumSquared / (widthSquared * rowMin));
320-
}
321-
322-
#layoutRow(rowValues, width, isVertical, layoutState)
323-
{
324-
const rowHeight = rowValues.sum() / width;
325-
326-
rowValues.forEach((rowItem) => {
327-
const rowWidth = rowItem / rowHeight;
328-
const curXPos = layoutState.currentPosition.x;
329-
const curYPos = layoutState.currentPosition.y;
330-
331-
let data;
332-
if (isVertical) {
333-
layoutState.currentPosition.y += rowWidth;
334-
data = {
335-
x: curXPos,
336-
y: curYPos,
337-
width: rowHeight,
338-
height: rowWidth,
339-
dataIndex: this.layoutResults.length,
340-
};
341-
} else {
342-
layoutState.currentPosition.x += rowWidth;
343-
data = {
344-
x: curXPos,
345-
y: curYPos,
346-
width: rowWidth,
347-
height: rowHeight,
348-
dataIndex: this.layoutResults.length,
349-
};
350-
}
351-
352-
this.layoutResults.push(data);
353-
});
354-
355-
if (isVertical) {
356-
layoutState.currentPosition.x += rowHeight;
357-
layoutState.currentPosition.y -= width;
358-
layoutState.remainingSize.width -= rowHeight;
359-
} else {
360-
layoutState.currentPosition.x -= width;
361-
layoutState.currentPosition.y += rowHeight;
362-
layoutState.remainingSize.height -= rowHeight;
363-
}
364-
}
365-
366-
#layoutLastRow(rowValues, remainingItems, width, layoutState)
367-
{
368-
const isVertical = TreeMapLayout.#getSmallerDimension(layoutState.remainingSize).vertical;
369-
if (rowValues.length)
370-
this.#layoutRow(rowValues, width, isVertical, layoutState);
371-
this.#layoutRow(remainingItems, width, isVertical, layoutState);
372-
}
373-
374-
static #getSmallerDimension(remainingSpace)
375-
{
376-
if (remainingSpace.height ** 2 > remainingSpace.width ** 2)
377-
return { value: remainingSpace.width, vertical: false };
378-
379-
return { value: remainingSpace.height, vertical: true };
380-
}
381-
}
382-
383258
class StoriesController {
384259
constructor(stage)
385260
{
@@ -410,23 +285,31 @@ class StoriesController {
410285

411286
this.items.length = complexity;
412287
}
413-
288+
414289
this._complexity = complexity;
290+
291+
const itemWidth = this.stageSize.width / 6;
292+
const itemHeight = this.stageSize.height / 3;
415293

416-
const numericValues = this.items.map((x) => x.value);
417-
418-
this.treeMap = new TreeMapLayout(this.stageSize, numericValues);
419-
this.treeMap.layout();
420-
421-
let i = 0;
422-
for (const data of this.treeMap.layoutResults) {
423-
const item = this.items[data.dataIndex];
294+
const xMax = this.stageSize.width - itemWidth;
295+
const yMax = this.stageSize.height - itemHeight;
296+
297+
for (let i = 0; i < this._complexity; ++i) {
298+
const item = this.items[i];
424299
const element = item.ensureElement();
425-
item.applyStyle(data);
300+
301+
const data = {
302+
// FIXME: Do some smarter layout that reduces overlap.
303+
x: Stage.randomInt(0, xMax),
304+
y: Stage.randomInt(0, yMax),
305+
width: itemWidth,
306+
height: itemHeight,
307+
};
426308

309+
item.applyStyle(data);
310+
427311
if (!element.parentElement)
428312
this.container.appendChild(element);
429-
++i;
430313
}
431314
}
432315

MotionMark/tests/dev/stories/stories.html

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@
6262
font-size: 10pt;
6363
overflow: clip;
6464
z-index: 0;
65+
opacity: 0.95;
6566
}
6667

6768
.box.rtl {

0 commit comments

Comments
 (0)