Skip to content
This repository has been archived by the owner on Jan 19, 2023. It is now read-only.

Commit

Permalink
feat: Custom error message prop for when images fail to load
Browse files Browse the repository at this point in the history
fix: fixes #82
  • Loading branch information
wuweiweiwu committed Jan 19, 2018
1 parent e4c4622 commit 419998d
Show file tree
Hide file tree
Showing 5 changed files with 99 additions and 2 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,7 @@ onCloseRequest | func | | yes | Close window event. S
onMovePrevRequest | func | empty function | | Move to previous image event. Should change the parent state such that `props.prevSrc` becomes `props.mainSrc`, `props.mainSrc` becomes `props.nextSrc`, etc.
onMoveNextRequest | func | empty function | | Move to next image event. Should change the parent state such that `props.nextSrc` becomes `props.mainSrc`, `props.mainSrc` becomes `props.prevSrc`, etc.
onImageLoadError | func | empty function | | Called when an image fails to load.<div>`(imageSrc: string, srcType: string, errorEvent: object): void`</div>
imageLoadErrorMessage | node | `"This image failed to load"` || What is rendered in place of an image if it fails to load. Centered in the lightbox viewport.
onAfterOpen | func | empty function | | Called after the modal has rendered.
discourageDownloads | bool | `false` | | When `true`, enables download discouragement (preventing [right-click -> Save Image As...])
animationDisabled | bool | `false` | | When `true`, image sliding animations are disabled
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ exports[`Snapshot Testing Lightbox renders properly" 1`] = `
enableZoom={true}
imageCaption={null}
imageCrossOrigin={null}
imageLoadErrorMessage="This image failed to load"
imagePadding={10}
imageTitle={null}
keyRepeatKeyupBonus={40}
Expand Down
27 changes: 27 additions & 0 deletions src/__tests__/react-image-lightbox.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -156,3 +156,30 @@ describe('Snapshot Testing', () => {
expect(wrapper).toMatchSnapshot();
});
});

describe('Error Testing', () => {
it('Should render the default error message', () => {
const wrapper = mount(<Lightbox {...commonProps} />);
wrapper.setState({
loadErrorStatus: { mainSrc: true },
});
wrapper.update();
expect(wrapper.find('div.errorContainer')).toHaveText(
'This image failed to load'
);
});
it('Should render the specified error message', () => {
const wrapper = mount(<Lightbox {...commonProps} />);
const imageLoadErrorMessage = <p>Specified Error Message</p>;
wrapper.setState({
loadErrorStatus: { mainSrc: true },
});
wrapper.setProps({
imageLoadErrorMessage,
});
wrapper.update();
expect(wrapper.find('div.errorContainer')).toContainReact(
imageLoadErrorMessage
);
});
});
48 changes: 46 additions & 2 deletions src/react-image-lightbox.js
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,9 @@ class ReactImageLightbox extends Component {

// Vertical offset from center
offsetY: 0,

// image load error for srcType
loadErrorStatus: {},
};

this.closeIfClickInner = this.closeIfClickInner.bind(this);
Expand Down Expand Up @@ -1142,6 +1145,12 @@ class ReactImageLightbox extends Component {

inMemoryImage.onerror = errorEvent => {
this.props.onImageLoadError(imageSrc, srcType, errorEvent);

// failed to load so set the state loadErrorStatus
this.setState(prevState => ({
loadErrorStatus: { ...prevState.loadErrorStatus, [srcType]: true },
}));

done(errorEvent);
};

Expand Down Expand Up @@ -1180,6 +1189,13 @@ class ReactImageLightbox extends Component {
this.getSrcTypes().forEach(srcType => {
const type = srcType.name;

// there is no error when we try to load it initially
if (props[type] && this.state.loadErrorStatus[type]) {
this.setState(prevState => ({
loadErrorStatus: { ...prevState.loadErrorStatus, [type]: false },
}));
}

// Load unloaded images
if (props[type] && !this.isImageLoaded(props[type])) {
this.loadImage(
Expand Down Expand Up @@ -1273,7 +1289,13 @@ class ReactImageLightbox extends Component {
imageCrossOrigin,
reactModalProps,
} = this.props;
const { zoomLevel, offsetX, offsetY, isClosing } = this.state;
const {
zoomLevel,
offsetX,
offsetY,
isClosing,
loadErrorStatus,
} = this.state;

const boxSize = this.getLightboxRect();
let transitionStyle = {};
Expand Down Expand Up @@ -1313,7 +1335,26 @@ class ReactImageLightbox extends Component {
imageStyle.cursor = 'move';
}

if (bestImageInfo === null) {
// support IE 9 and 11
const hasTrueValue = object =>
Object.keys(object).some(key => object[key]);

// when error on one of the loads then push custom error stuff
if (bestImageInfo === null && hasTrueValue(loadErrorStatus)) {
images.push(
<div
className={`${imageClass} ${styles.image} ril-errored`}
style={imageStyle}
key={this.props[srcType] + keyEndings[srcType]}
>
<div className={styles.errorContainer}>
{this.props.imageLoadErrorMessage}
</div>
</div>
);

return;
} else if (bestImageInfo === null) {
const loadingIcon =
ieVersion < 10 ? (
<div className={styles.loadingContainer__icon}>
Expand Down Expand Up @@ -1759,6 +1800,8 @@ ReactImageLightbox.propTypes = {
zoomInLabel: PropTypes.string,
zoomOutLabel: PropTypes.string,
closeLabel: PropTypes.string,

imageLoadErrorMessage: PropTypes.node,
};

ReactImageLightbox.defaultProps = {
Expand Down Expand Up @@ -1792,6 +1835,7 @@ ReactImageLightbox.defaultProps = {
wrapperClassName: '',
zoomInLabel: 'Zoom in',
zoomOutLabel: 'Zoom out',
imageLoadErrorMessage: 'This image failed to load',
};

export default ReactImageLightbox;
24 changes: 24 additions & 0 deletions src/style.scss
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,30 @@ $maxCaptionHeight: 150px;
right: 0;
bottom: 0;
left: 0;
.imagePrev & {
display: none;
}
.imageNext & {
display: none;
}
}

.errorContainer {
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
display: flex;
align-items: center;
justify-content: center;
color: #fff;
.imagePrev & {
display: none;
}
.imageNext & {
display: none;
}
}

.loadingContainer__icon {
Expand Down

0 comments on commit 419998d

Please sign in to comment.