Flickr's justified-layout in a React hook. Calculate justified layouts to create beautiful image galleries or whatever you want.
npm i use-justified-layoutimport useJustifiedLayout from 'use-justified-layout'
import images from './images'
const Gallery = () => {
const [layout] = useJustifiedLayout({
layoutInput: images
})
return (
<div style={{position: "relative", height={layout.containerHeight}}>
{layout.boxes.map(({width, height, top, left}, index) => (
<img
width={width}
height={height}
style={{ top, left, position: "absolute" }}
src={images[index].url}
/>
))}
</div>
)
}useJustifiedLayout returns and array of two elements: [layout, layoutIsReady]
-
layoutIsReady: abooleanthat indicates whether or not thelayoutcalculation is ready. Useful in cases where you want to show a loader to the user. -
layout: theLayoutGeometryobject returned by the originaljustified-layoutlibrary. The type is defined as follow:type LayoutGeometry = { containerHeight: number; widowCount: number; boxes: Box[]; };
-
containerHeightis theheightof the complete layout, it is necessary since you need to useposition: absoluteto display the items. This attribute will help you avoid things to overlap in yourDOM. -
widowCountis the number of items at the end of a layout that doesn't make a full row. For example, the next layout will have awidowCountvalue of2. -
boxesare the calculated attributes for every item in your layout. Aboxhas the following shape:type Box = { aspectRatio: number; top: number; width: number; height: number; left: number; };
-
The hooks accepts a object with the following shape:
interface IUseJustifiedLayout {
layoutInput: LayoutInput;
configuration?: LayoutConfiguration;
dependencies?: ReadonlyArray<unknown>;
}-
layoutInput: information about the items, necessary to calculate the layout.type AspectRatio = number; type SizeObject = { width: number; height: number; }; type LayoutInput = AspectRatio[] | SizeObject[];
As you can see, you have to options when passing
layoutInput:-
Aspect ratios:
[1.33, 1, 0.65] -
Size objects:
[{ width: 400, height: 300 }, { width: 300, height: 300 }, { width: 250, height: 400 }]
-
-
dependencies: this is an array with the same function as the dependencies array that you pass to anuseEffecthook. When a value of this array changes, the layout gets recalculated. By default, the layout will recalculate if thelayoutInputchanges. -
configuration: you can use the following attributes to customize thelayoutoutput. This table comes from thejustified-layoutlibrary documentation (with a slight modifications), you can see the original here.Name Type Default Description containerWidth number1060 The width that boxes will be contained within irrelevant of padding. containerPadding numberContainerPadding10 boxSpacing numberBoxSpacing10 targetRowHeight number0.25 How far row heights can stray from targetRowHeight.0would force rows to be thetargetRowHeightexactly and would likely make it impossible to justify. The value must be between0and1maxNumRows numbernone Will stop adding rows at this number regardless of how many items still need to be laid out. forceAspectRatio booleannumberfalse showWidows booleantrue By default we'll return items at the end of a justified layout even if they don't make a full row. If falsethey'll be omitted from the output.fullWidthBreakoutRowCadence booleannumberfalse
Please visit the justified-layout documentation to get more ideas on how to play with the configurations.
WIP :)

