[change] defer Image loading

x4 faster render benchmark
This commit is contained in:
Nicolas Gallagher
2017-02-18 00:03:06 -08:00
parent e1fc253277
commit eb59875bed
2 changed files with 37 additions and 10 deletions
+16 -10
View File
@@ -1,9 +1,10 @@
/* global window */ /* global window */
import applyNativeMethods from '../../modules/applyNativeMethods'; import applyNativeMethods from '../../modules/applyNativeMethods';
import createDOMElement from '../../modules/createDOMElement';
import ImageResizeMode from './ImageResizeMode'; import ImageResizeMode from './ImageResizeMode';
import ImageLoader from '../../modules/ImageLoader'; import ImageLoader from '../../modules/ImageLoader';
import ImageStylePropTypes from './ImageStylePropTypes'; import ImageStylePropTypes from './ImageStylePropTypes';
import requestAnimationFrame from 'fbjs/lib/requestAnimationFrame'; import requestIdleCallback, { cancelIdleCallback } from '../../modules/requestIdleCallback';
import StyleSheet from '../../apis/StyleSheet'; import StyleSheet from '../../apis/StyleSheet';
import StyleSheetPropType from '../../propTypes/StyleSheetPropType'; import StyleSheetPropType from '../../propTypes/StyleSheetPropType';
import View from '../View'; import View from '../View';
@@ -153,13 +154,20 @@ class Image extends Component {
} }
_createImageLoader() { _createImageLoader() {
this._destroyImageLoader(); this._loadRequest = requestIdleCallback(() => {
const uri = resolveAssetSource(this.props.source); this._destroyImageLoader();
this._imageRequestId = ImageLoader.load(uri, this._onLoad, this._onError); const uri = resolveAssetSource(this.props.source);
this._onLoadStart(); this._imageRequestId = ImageLoader.load(uri, this._onLoad, this._onError);
this._onLoadStart();
});
} }
_destroyImageLoader() { _destroyImageLoader() {
if (this._loadRequest) {
cancelIdleCallback(this._loadRequest);
this._loadRequest = null;
}
if (this._imageRequestId) { if (this._imageRequestId) {
ImageLoader.abort(this._imageRequestId); ImageLoader.abort(this._imageRequestId);
this._imageRequestId = null; this._imageRequestId = null;
@@ -204,11 +212,9 @@ class Image extends Component {
const shouldDisplaySource = this._imageState === STATUS_LOADED || this._imageState === STATUS_LOADING; const shouldDisplaySource = this._imageState === STATUS_LOADED || this._imageState === STATUS_LOADING;
// only triggers a re-render when the image is loading (to support PJEG), loaded, or failed // only triggers a re-render when the image is loading (to support PJEG), loaded, or failed
if (shouldDisplaySource !== this.state.shouldDisplaySource) { if (shouldDisplaySource !== this.state.shouldDisplaySource) {
requestAnimationFrame(() => { if (this._isMounted) {
if (this._isMounted) { this.setState(() => ({ shouldDisplaySource }));
this.setState({ shouldDisplaySource }); }
}
});
} }
} }
} }
+21
View File
@@ -0,0 +1,21 @@
const _requestIdleCallback = function (cb) {
return setTimeout(() => {
const start = Date.now();
cb({
didTimeout: false,
timeRemaining() {
return Math.max(0, 50 - (Date.now() - start));
}
});
}, 1);
};
const _cancelIdleCallback = function (id) {
clearTimeout(id);
};
const requestIdleCallback = window.requestIdleCallback || _requestIdleCallback;
const cancelIdleCallback = window.cancelIdleCallback || _cancelIdleCallback;
export default requestIdleCallback;
export { cancelIdleCallback };