Skip to content

Instantly share code, notes, and snippets.

@stipsan
Created November 22, 2019 12:32
Show Gist options
  • Save stipsan/c4506344746095146306ff08cbf48624 to your computer and use it in GitHub Desktop.
Save stipsan/c4506344746095146306ff08cbf48624 to your computer and use it in GitHub Desktop.
Masonry worklet example
// Plan on making a react/web component that reuses the layout logic from the worklet to lay out and
// reoder a css columns top down layout to a ltr flow
// From https://github.com/GoogleChromeLabs/houdini-samples
registerLayout(
'masonry',
class {
static get inputProperties() {
return ['--padding', '--columns'];
}
*intrinsicSizes() {
/* TODO implement :) */
}
async layout(children, edges, constraints, styleMap) {
const inlineSize = constraints.fixedInlineSize;
const padding = parseInt(styleMap.get('--padding'));
const columnValue = styleMap.get('--columns');
// We also accept 'auto', which will select the BEST number of columns.
let columns = parseInt(columnValue);
if (columnValue == 'auto' || !columns) {
columns = Math.ceil(inlineSize / 350); // MAGIC NUMBER o/.
}
// Layout all children with simply their column size.
const childInlineSize =
(inlineSize - (columns + 1) * padding) / columns;
/*
const childFragments = await children.map((child) => {
return child.layoutNextFragment({fixedInlineSize: childInlineSize});
});
*/
const childFragments = [];
for (let child of children) {
// (2) Perform layout upon the child.
const fragment = await child.layoutNextFragment({
fixedInlineSize: childInlineSize,
});
childFragments.push(fragment);
}
let autoBlockSize = 0;
const columnOffsets = Array(columns).fill(0);
for (let childFragment of childFragments) {
// Select the column with the least amount of stuff in it.
const min = columnOffsets.reduce(
(acc, val, idx) => {
if (!acc || val < acc.val) {
return { idx, val };
}
return acc;
},
{ val: +Infinity, idx: -1 }
);
childFragment.inlineOffset =
padding + (childInlineSize + padding) * min.idx;
childFragment.blockOffset = padding + min.val;
columnOffsets[min.idx] =
childFragment.blockOffset + childFragment.blockSize;
autoBlockSize = Math.max(
autoBlockSize,
columnOffsets[min.idx] + padding
);
}
return { autoBlockSize, childFragments };
}
}
);
/**
* Copyright 2018 Google Inc. All Rights Reserved.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment