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

Improve fixed layout #4

Merged
merged 3 commits into from
Apr 3, 2019
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
63 changes: 2 additions & 61 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,6 @@ A simple, fast and flexibility image gallery.

<img src="https://github.com/kurpachsv/react-gallery/raw/master/preview-masonry.png" alt="Preview masonry" />

<img src="https://github.com/kurpachsv/react-gallery/raw/master/preview-fixed.png" alt="Preview fixed" />


See [storybook](https://kurpachsv.github.io/react-gallery) for live demonstration.

Expand Down Expand Up @@ -64,71 +62,14 @@ className | string | '' | optional; container class name
columnClassName | string | '' | optional; item class name
rowClassName | string | '' | optional; row class name (for default layout)
enableFixed | bool | false | optional; turn on/off fixed layout mode
fixedSize | number | 200 | optional; size in px of image container
fixedBottom | number | 50 | optional; size in px of bottom margin
fixedGutter | number | 10 | optional size in px of space between images (only for fixed layout mode)
enableDetailView | bool | false | optional; turn on/off detail view mode for fixed or masonry layout
detailsViewRenderer | function | default implementation | optional; component/function for render of detail view

## Renderers

For better flexibility, you can override default image renderer, here is a default implementation:

```javascript
import {Image} from '@kurpachsv/react-gallery';
```

```javascript
const defaultRenderer = imageProps => {
return (
<Fragment>
<Image
{...imageProps}
/>
<div
style={{
backgroundColor: 'rgb(187, 189, 191)',
paddingTop: `${imageProps.placeholderHeight}%`,
}}
/>
</Fragment>
);
};
```

Also you can override default details renderer, here is a default implementation:

```javascript
const DETAILS_IMAGE_HEIGHT = 300;

const defaultDetailsViewRenderer = ({visible, selectedImage, gutter, isGutterUnitsInPercent}) => {
const gutterWithUnits = isGutterUnitsInPercent ? `${gutter}%` : `${gutter}px`;
return (
<div
className={visible ? style.container : style['container--disable']}
style={{
height: visible ? DETAILS_IMAGE_HEIGHT : 0,
visibility: visible ? 'visible' : 'hidden',
marginBottom: visible ? gutterWithUnits : 0,
}}
>

<div className={style['image-wrapper']}>
{visible && (
<Image
style={{
height: DETAILS_IMAGE_HEIGHT,
width: selectedImage.width / selectedImage.height * DETAILS_IMAGE_HEIGHT,
}}
src={selectedImage.src}
/>
)}
</div>
</div>
);
};
```

For better flexibility, you can override default image renderer, [here](https://github.com/kurpachsv/react-gallery/blob/master/src/Renderer.js#L7) is a default implementation:
Also you can override default details renderer, [here](https://github.com/kurpachsv/react-gallery/blob/master/src/Renderer.js#L26) is a default implementation.

## License

Expand Down
173 changes: 68 additions & 105 deletions dist/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -259,9 +259,7 @@ var COLUMNS_MAX_COUNT = 5;
var COLUMN_MAX_WIDTH = 200;
var COLUMN_MAX_HEIGHT = 200;
var GUTTER_IN_PERCENT = 0.5;
var DEFAULT_FIXED_SIZE = 200;
var DEFAULT_FIXED_BOTTOM = 50;
var DEFAULT_FIXED_GUTTER = 10;

var Engine =
/*#__PURE__*/
Expand Down Expand Up @@ -417,19 +415,9 @@ function () {
return itemAfterResize.width;
}
}, {
key: "resizeColumnByFixedSize",
value: function resizeColumnByFixedSize(item, row, fixedSize, fixedBottom) {
item = Engine.resizeByHeight(item, item.height - (fixedBottom - (fixedSize - item.height)));

if (item.height > fixedSize) {
item = Engine.resizeByHeight(item, fixedSize);
}

if (item.width > fixedSize) {
item = Engine.resizeByWidth(item, fixedSize);
}

return item;
key: "calculateFixedWidthInPercent",
value: function calculateFixedWidthInPercent(item, row) {
return 100 / row.length - this.getGutterInPercent();
}
}, {
key: "buildRows",
Expand Down Expand Up @@ -525,15 +513,13 @@ var DETAILS_IMAGE_HEIGHT = 300;
var defaultDetailsViewRenderer = function defaultDetailsViewRenderer(_ref) {
var visible = _ref.visible,
selectedImage = _ref.selectedImage,
gutter = _ref.gutter,
isGutterUnitsInPercent = _ref.isGutterUnitsInPercent;
var gutterWithUnits = isGutterUnitsInPercent ? "".concat(gutter, "%") : "".concat(gutter, "px");
gutterInPercent = _ref.gutterInPercent;
return React__default.createElement("div", {
className: visible ? style.container : style['container--disable'],
style: {
height: visible ? DETAILS_IMAGE_HEIGHT : 0,
visibility: visible ? 'visible' : 'hidden',
marginBottom: visible ? gutterWithUnits : 0
marginBottom: visible ? "".concat(gutterInPercent, "%") : 0
}
}, React__default.createElement("div", {
className: style['image-wrapper']
Expand All @@ -549,11 +535,10 @@ var defaultDetailsViewRenderer = function defaultDetailsViewRenderer(_ref) {
defaultDetailsViewRenderer.propTypes = {
visible: PropTypes.bool.isRequired,
selectedImage: PropTypes.object.isRequired,
gutter: PropTypes.number,
isGutterUnitsInPercent: PropTypes.bool.isRequired
gutterInPercent: PropTypes.number
};
defaultDetailsViewRenderer.defaultProps = {
gutter: 0
gutterInPercent: 0
};

var hasDocument = (typeof document === "undefined" ? "undefined" : _typeof(document)) === 'object' && document !== null;
Expand Down Expand Up @@ -718,9 +703,7 @@ function (_Component) {
columnClassName = _this$props.columnClassName,
rowClassName = _this$props.rowClassName,
enableFixed = _this$props.enableFixed,
fixedSize = _this$props.fixedSize,
fixedBottom = _this$props.fixedBottom,
fixedGutter = _this$props.fixedGutter,
enableDetailView = _this$props.enableDetailView;
this.engine.setImages(images).setMaxColumnsCount(columnsMaxCount).setColumnMaxWidth(columnMaxWidth).setColumnMaxHeight(columnMaxHeight).setGutterInPercent(gutterInPercent);
this.setState({
Expand All @@ -737,9 +720,7 @@ function (_Component) {
columnClassName: columnClassName,
rowClassName: rowClassName,
enableFixed: enableFixed,
fixedSize: fixedSize,
fixedBottom: fixedBottom,
fixedGutter: fixedGutter,
enableDetailView: enableDetailView
});
}
Expand All @@ -762,9 +743,7 @@ function (_Component) {
columnClassName: nextProps.columnClassName,
rowClassName: nextProps.rowClassName,
enableFixed: nextProps.enableFixed,
fixedSize: nextProps.fixedSize,
fixedBottom: nextProps.fixedBottom,
fixedGutter: nextProps.fixedGutter,
enableDetailView: nextProps.enableDetailView
});
}
Expand Down Expand Up @@ -890,8 +869,7 @@ function (_Component) {
visible: rowIndex === selectedImageRow,
selectedImage: selectedImage,
rowHeight: selectedRowHeight,
gutter: _this3.engine.getGutterInPercent(),
isGutterUnitsInPercent: true,
gutterInPercent: _this3.engine.getGutterInPercent(),
selectedImageId: selectedImageId,
selectedImageProps: selectedImageProps
}))))
Expand All @@ -910,89 +888,78 @@ function (_Component) {
imageRenderer = _ref4.imageRenderer,
disableObserver = _ref4.disableObserver,
disableActualImage = _ref4.disableActualImage,
fixedGutter = _ref4.fixedGutter,
columnsMaxCount = _ref4.columnsMaxCount,
fixedSize = _ref4.fixedSize,
fixedBottom = _ref4.fixedBottom,
enableDetailView = _ref4.enableDetailView,
detailsViewRenderer = _ref4.detailsViewRenderer;
detailsViewRenderer = _ref4.detailsViewRenderer,
fixedBottom = _ref4.fixedBottom;
var _this$state3 = this.state,
selectedImageRow = _this$state3.selectedImageRow,
selectedImage = _this$state3.selectedImage,
selectedRowHeight = _this$state3.selectedRowHeight,
selectedImageId = _this$state3.selectedImageId,
selectedImageProps = _this$state3.selectedImageProps;
return React__default.createElement("div", {
className: "".concat(style$1.container, " ").concat(className),
style: {
width: columnsMaxCount * fixedSize + columnsMaxCount * fixedGutter - fixedGutter
}
className: "".concat(style$1.container, " ").concat(className)
}, rows.map(function (el, rowIndex) {
var row = el.row;
return React__default.createElement(React__default.Fragment, {
return (
/* eslint-disable-next-line react/no-array-index-key */
key: "row-".concat(rowIndex)
}, React__default.createElement("div", {
className: rowClassName
}, row.map(function (column, columnIndex) {
var columnAfterResize = _this4.engine.resizeColumnByFixedSize(column, row, fixedSize, fixedBottom);

var placeholderHeight = 100 * columnAfterResize.height / columnAfterResize.width;
return React__default.createElement(React__default.Fragment, {
key: "column-".concat(column.src, "-").concat(rowIndex, "-").concat(columnIndex)
}, React__default.createElement("div", {
/* eslint-disable-next-line react/no-array-index-key */
key: "column-".concat(column.src, "-").concat(rowIndex, "-").concat(columnIndex),
className: "".concat(style$1['item--fixed'], " ").concat(columnClassName),
style: {
width: fixedSize,
height: fixedSize,
margin: row.length === columnIndex + 1 ? "0 0 ".concat(fixedGutter, "px 0") : "0 ".concat(fixedGutter, "px ").concat(fixedGutter, "px 0")
}
React__default.createElement(React__default.Fragment, {
key: "row-".concat(rowIndex)
}, React__default.createElement("div", {
style: {
width: columnAfterResize.width,
height: columnAfterResize.height,
margin: 'auto',
// eslint-disable-next-line
marginTop: "".concat(fixedSize - columnAfterResize.height - fixedBottom, "px")
}
}, React__default.createElement(ViewMonitor, {
disableObserver: disableObserver
}, function (isViewable) {
return imageRenderer(_objectSpread({}, columnAfterResize, {
placeholderHeight: placeholderHeight,
visible: !disableActualImage && isViewable,
onClick: function onClick() {
return _this4.handleSelectImage({
selectedImageRow: rowIndex,
selectedImage: columnAfterResize,
selectedRowHeight: columnAfterResize.height,
// eslint-disable-next-line
selectedImageId: "column-".concat(column.src, "-").concat(rowIndex, "-").concat(columnIndex),
selectedImageProps: {
placeholderHeight: placeholderHeight,
newWidthInPercent: fixedSize,
newWidth: columnAfterResize.width,
newHeight: columnAfterResize.height
}
});
},
specifyImageSizes: true,
newWidth: columnAfterResize.width,
newHeight: columnAfterResize.height,
fixedSize: fixedSize
}));
}))));
})), React__default.createElement("div", null, enableDetailView && detailsViewRenderer(_objectSpread({}, row, {
visible: rowIndex === selectedImageRow,
selectedImage: selectedImage,
rowHeight: selectedRowHeight,
gutter: fixedGutter,
isGutterUnitsInPercent: false,
selectedImageId: selectedImageId,
selectedImageProps: selectedImageProps
}))));
className: rowClassName
}, row.map(function (column, columnIndex) {
var newWidth = _this4.engine.calculateWidth(column, row, el.isIncomplete);

var newHeight = _this4.engine.calculateHeight(column, row, el.isIncomplete);

var newWidthInPercent = _this4.engine.calculateFixedWidthInPercent(column, row);

var placeholderHeight = 100 * newHeight / newWidth;
return React__default.createElement("div", {
/* eslint-disable-next-line react/no-array-index-key */
key: "column-".concat(column.src, "-").concat(rowIndex, "-").concat(columnIndex),
className: "".concat(style$1['item--fixed'], " ").concat(columnClassName),
style: {
width: el.isIncomplete ? "".concat(newWidth, "px") : "".concat(newWidthInPercent, "%"),
margin: row.length === columnIndex + 1 ? "0 0 ".concat(_this4.engine.getGutterInPercent(), "% 0") : "0 ".concat(_this4.engine.getGutterInPercent(), "% ").concat(_this4.engine.getGutterInPercent(), "% 0")
}
}, React__default.createElement("div", {
style: {
// eslint-disable-next-line
marginBottom: "".concat(fixedBottom, "px")
}
}, React__default.createElement(ViewMonitor, {
disableObserver: disableObserver
}, function (isViewable) {
return imageRenderer(_objectSpread({}, column, {
placeholderHeight: placeholderHeight,
visible: !disableActualImage && isViewable,
onClick: function onClick() {
return _this4.handleSelectImage({
selectedImageRow: rowIndex,
selectedImage: column,
selectedRowHeight: newHeight,
// eslint-disable-next-line
selectedImageId: "column-".concat(column.src, "-").concat(rowIndex, "-").concat(columnIndex),
selectedImageProps: {
placeholderHeight: placeholderHeight,
newWidthInPercent: newWidthInPercent,
newWidth: newWidth,
newHeight: newHeight
}
});
}
}));
})));
})), React__default.createElement("div", null, enableDetailView && detailsViewRenderer(_objectSpread({}, row, {
visible: rowIndex === selectedImageRow,
selectedImage: selectedImage,
rowHeight: selectedRowHeight,
gutterInPercent: _this4.engine.getGutterInPercent(),
selectedImageId: selectedImageId,
selectedImageProps: selectedImageProps
}))))
);
}));
}
}, {
Expand Down Expand Up @@ -1044,9 +1011,7 @@ _defineProperty(Gallery, "propTypes", {
disableObserver: PropTypes.bool,
disableActualImage: PropTypes.bool,
enableFixed: PropTypes.bool,
fixedSize: PropTypes.number,
fixedBottom: PropTypes.number,
fixedGutter: PropTypes.number,
enableDetailView: PropTypes.bool,
detailsViewRenderer: PropTypes.func
});
Expand All @@ -1064,9 +1029,7 @@ _defineProperty(Gallery, "defaultProps", {
disableObserver: false,
disableActualImage: false,
enableFixed: false,
fixedSize: DEFAULT_FIXED_SIZE,
fixedBottom: DEFAULT_FIXED_BOTTOM,
fixedGutter: DEFAULT_FIXED_GUTTER,
enableDetailView: false,
detailsViewRenderer: defaultDetailsViewRenderer
});
Expand Down
2 changes: 1 addition & 1 deletion package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@kurpachsv/react-gallery",
"version": "0.2.16",
"version": "0.2.17",
"description": "A simple, fast and flexibility image gallery.",
"main": "dist/index.js",
"scripts": {
Expand Down
Loading