apeman-react-upload
Version:
apeman react package for file upload components.
268 lines (230 loc) • 21.2 kB
JavaScript
/**
* apeman react package for file upload components.
* @class ApUpload
*/
'use strict';
Object.defineProperty(exports, "__esModule", {
value: true
});
var _react = require('react');
var _react2 = _interopRequireDefault(_react);
var _classnames = require('classnames');
var _classnames2 = _interopRequireDefault(_classnames);
var _async = require('async');
var _async2 = _interopRequireDefault(_async);
var _path = require('path');
var _path2 = _interopRequireDefault(_path);
var _uuid = require('uuid');
var _uuid2 = _interopRequireDefault(_uuid);
var _apemanReactImage = require('apeman-react-image');
var _apemanReactSpinner = require('apeman-react-spinner');
var _apemanReactButton = require('apeman-react-button');
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
/** @lends ApUpload */
var ApUpload = _react2.default.createClass({
displayName: 'ApUpload',
// --------------------
// Specs
// --------------------
propTypes: {
/** Name of input */
name: _react.PropTypes.string,
/** DOM id of input */
id: _react.PropTypes.string,
/** Allow multiple upload */
multiple: _react.PropTypes.bool,
/** Handler for change event */
onChange: _react.PropTypes.func,
/** Handler for load event */
onLoad: _react.PropTypes.func,
/** Handler for error event */
onError: _react.PropTypes.func,
/** Image width */
width: _react.PropTypes.number,
/** Image height */
height: _react.PropTypes.number,
/** Guide text */
text: _react.PropTypes.string,
/** Accept file type */
accept: _react.PropTypes.string,
/** Guide icon */
icon: _react.PropTypes.string,
/** Icon for close images */
closeIcon: _react.PropTypes.string,
/** Spinner theme */
spinner: _react.PropTypes.string,
/** Value of input */
value: _react.PropTypes.oneOfType([_react.PropTypes.string, _react.PropTypes.array])
},
mixins: [],
statics: {
readFile: function readFile(file, callback) {
var reader = new window.FileReader();
reader.onerror = function onerror(err) {
callback(err);
};
reader.onload = function onload(ev) {
callback(null, ev.target.result);
};
reader.readAsDataURL(file);
},
isImageUrl: function isImageUrl(url) {
var imageExtensions = ['.jpg', '.jpeg', '.svg', '.gif', '.png'];
return (/^data:image/.test(url) || !! ~imageExtensions.indexOf(_path2.default.extname(url))
);
}
},
getInitialState: function getInitialState() {
var s = this;
var props = s.props;
var hasValue = props.value && props.value.length > 0;
return {
spinning: false,
error: null,
urls: hasValue ? [].concat(props.value) : null
};
},
getDefaultProps: function getDefaultProps() {
return {
name: null,
id: 'ap-upload-' + _uuid2.default.v4(),
multiple: false,
width: 180,
height: 180,
accept: null,
text: 'Upload file',
icon: 'fa fa-cloud-upload',
closeIcon: 'fa fa-close',
spinnerIcon: _apemanReactSpinner.ApSpinner.DEFAULT_THEME,
onChange: null,
onLoad: null,
onError: null
};
},
render: function render() {
var s = this;
var state = s.state;
var props = s.props;
var width = props.width;
var height = props.height;
return _react2.default.createElement(
'div',
{ className: (0, _classnames2.default)('ap-upload', props.className),
style: Object.assign({}, props.style) },
_react2.default.createElement('input', { type: 'file',
className: 'ap-upload-input',
multiple: props.multiple,
name: props.name,
id: props.id,
accept: props.accept,
onChange: s.handleChange,
style: { width: width, height: height }
}),
_react2.default.createElement(
'label',
{ className: 'ap-upload-label', htmlFor: props.id },
_react2.default.createElement('span', { className: 'ap-upload-aligner' }),
_react2.default.createElement(
'span',
{ className: 'ap-upload-label-inner' },
_react2.default.createElement('i', { className: (0, _classnames2.default)('ap-upload-icon', props.icon) }),
_react2.default.createElement(
'span',
{ className: 'ap-upload-text' },
props.text
),
props.children
)
),
s._renderPreviewImage(state.urls, width, height),
s._renderRemoveButton(!!(state.urls && state.urls.length > 0), props.closeIcon),
s._renderSpinner(state.spinning, props.spinner)
);
},
// --------------------
// Lifecycle
// --------------------
// ------------------
// Custom
// ------------------
handleChange: function handleChange(e) {
var s = this;
var props = s.props;
var target = e.target;
var files = Array.prototype.slice.call(target.files, 0);
var onChange = props.onChange;
var onError = props.onError;
var onLoad = props.onLoad;
s.setState({ spinning: true });
if (onChange) {
onChange(e);
}
_async2.default.concat(files, ApUpload.readFile, function (err, urls) {
e.urls = urls;
e.target = target;
s.setState({
spinning: false,
error: err,
urls: urls
});
if (err) {
if (onError) {
onError(err);
}
} else {
if (onLoad) {
onLoad(e);
}
}
});
},
handleRemove: function handleRemove() {
var s = this;
var props = s.props;
var onLoad = props.onLoad;
s.setState({
error: null,
urls: null
});
if (onLoad) {
onLoad([]);
}
},
// ------------------
// Private
// ------------------
_renderSpinner: function _renderSpinner(spinning, theme) {
var s = this;
return _react2.default.createElement(_apemanReactSpinner.ApSpinner, { enabled: spinning, theme: theme });
},
_renderRemoveButton: function _renderRemoveButton(removable, icon) {
var s = this;
if (!removable) {
return null;
}
return _react2.default.createElement(
_apemanReactButton.ApButton,
{ onTap: s.handleRemove, className: 'ap-upload-remove-button' },
_react2.default.createElement('i', { className: (0, _classnames2.default)('ap-upload-remove-icon', icon) })
);
},
_renderPreviewImage: function _renderPreviewImage(urls, width, height) {
if (!urls) {
return null;
}
var s = this;
return urls.filter(function (url) {
return ApUpload.isImageUrl(url);
}).map(function (url, i) {
return _react2.default.createElement(_apemanReactImage.ApImage, { key: url,
src: url,
height: height,
width: width,
className: (0, _classnames2.default)('ap-upload-preview-image'),
style: { left: i * 10 + '%', top: i * 10 + '%' },
scale: 'fit' });
});
}
});
exports.default = ApUpload;
//# sourceMappingURL=data:application/json;base64,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ZVJvb3QiOiIvVXNlcnMvb2t1bmlzaGluaXNoaS9Qcm9qZWN0cy9hcGVtYW4tcHJvamVjdHMvYXBlbWFuLXJlYWN0LXVwbG9hZC9saWIiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIGFwZW1hbiByZWFjdCBwYWNrYWdlIGZvciBmaWxlIHVwbG9hZCBjb21wb25lbnRzLlxuICogQGNsYXNzIEFwVXBsb2FkXG4gKi9cblxuJ3VzZSBzdHJpY3QnXG5cbmltcG9ydCBSZWFjdCwge1Byb3BUeXBlcyBhcyB0eXBlc30gZnJvbSAncmVhY3QnXG5pbXBvcnQgY2xhc3NuYW1lcyBmcm9tICdjbGFzc25hbWVzJ1xuaW1wb3J0IGFzeW5jIGZyb20gJ2FzeW5jJ1xuaW1wb3J0IHBhdGggZnJvbSAncGF0aCdcbmltcG9ydCB1dWlkIGZyb20gJ3V1aWQnXG5pbXBvcnQge0FwSW1hZ2V9IGZyb20gJ2FwZW1hbi1yZWFjdC1pbWFnZSdcbmltcG9ydCB7QXBTcGlubmVyfSBmcm9tICdhcGVtYW4tcmVhY3Qtc3Bpbm5lcidcbmltcG9ydCB7QXBCdXR0b259IGZyb20gJ2FwZW1hbi1yZWFjdC1idXR0b24nXG5cbi8qKiBAbGVuZHMgQXBVcGxvYWQgKi9cbmNvbnN0IEFwVXBsb2FkID0gUmVhY3QuY3JlYXRlQ2xhc3Moe1xuXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gIC8vIFNwZWNzXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgcHJvcFR5cGVzOiB7XG4gICAgLyoqIE5hbWUgb2YgaW5wdXQgKi9cbiAgICBuYW1lOiB0eXBlcy5zdHJpbmcsXG4gICAgLyoqIERPTSBpZCBvZiBpbnB1dCAqL1xuICAgIGlkOiB0eXBlcy5zdHJpbmcsXG4gICAgLyoqIEFsbG93IG11bHRpcGxlIHVwbG9hZCAqL1xuICAgIG11bHRpcGxlOiB0eXBlcy5ib29sLFxuICAgIC8qKiBIYW5kbGVyIGZvciBjaGFuZ2UgZXZlbnQgKi9cbiAgICBvbkNoYW5nZTogdHlwZXMuZnVuYyxcbiAgICAvKiogSGFuZGxlciBmb3IgbG9hZCBldmVudCAqL1xuICAgIG9uTG9hZDogdHlwZXMuZnVuYyxcbiAgICAvKiogSGFuZGxlciBmb3IgZXJyb3IgZXZlbnQgKi9cbiAgICBvbkVycm9yOiB0eXBlcy5mdW5jLFxuICAgIC8qKiBJbWFnZSB3aWR0aCAqL1xuICAgIHdpZHRoOiB0eXBlcy5udW1iZXIsXG4gICAgLyoqIEltYWdlIGhlaWdodCAqL1xuICAgIGhlaWdodDogdHlwZXMubnVtYmVyLFxuICAgIC8qKiBHdWlkZSB0ZXh0ICovXG4gICAgdGV4dDogdHlwZXMuc3RyaW5nLFxuICAgIC8qKiBBY2NlcHQgZmlsZSB0eXBlICovXG4gICAgYWNjZXB0OiB0eXBlcy5zdHJpbmcsXG4gICAgLyoqIEd1aWRlIGljb24gKi9cbiAgICBpY29uOiB0eXBlcy5zdHJpbmcsXG4gICAgLyoqIEljb24gZm9yIGNsb3NlIGltYWdlcyAqL1xuICAgIGNsb3NlSWNvbjogdHlwZXMuc3RyaW5nLFxuICAgIC8qKiBTcGlubmVyIHRoZW1lICovXG4gICAgc3Bpbm5lcjogdHlwZXMuc3RyaW5nLFxuICAgIC8qKiBWYWx1ZSBvZiBpbnB1dCAqL1xuICAgIHZhbHVlOiB0eXBlcy5vbmVPZlR5cGUoW1xuICAgICAgdHlwZXMuc3RyaW5nLFxuICAgICAgdHlwZXMuYXJyYXlcbiAgICBdKVxuICB9LFxuXG4gIG1peGluczogW10sXG5cbiAgc3RhdGljczoge1xuICAgIHJlYWRGaWxlIChmaWxlLCBjYWxsYmFjaykge1xuICAgICAgbGV0IHJlYWRlciA9IG5ldyB3aW5kb3cuRmlsZVJlYWRlcigpXG4gICAgICByZWFkZXIub25lcnJvciA9IGZ1bmN0aW9uIG9uZXJyb3IgKGVycikge1xuICAgICAgICBjYWxsYmFjayhlcnIpXG4gICAgICB9XG4gICAgICByZWFkZXIub25sb2FkID0gZnVuY3Rpb24gb25sb2FkIChldikge1xuICAgICAgICBjYWxsYmFjayhudWxsLCBldi50YXJnZXQucmVzdWx0KVxuICAgICAgfVxuICAgICAgcmVhZGVyLnJlYWRBc0RhdGFVUkwoZmlsZSlcbiAgICB9LFxuICAgIGlzSW1hZ2VVcmwgKHVybCkge1xuICAgICAgY29uc3QgaW1hZ2VFeHRlbnNpb25zID0gW1xuICAgICAgICAnLmpwZycsXG4gICAgICAgICcuanBlZycsXG4gICAgICAgICcuc3ZnJyxcbiAgICAgICAgJy5naWYnLFxuICAgICAgICAnLnBuZydcbiAgICAgIF1cbiAgICAgIHJldHVybiAvXmRhdGE6aW1hZ2UvLnRlc3QodXJsKSB8fCAhIX5pbWFnZUV4dGVuc2lvbnMuaW5kZXhPZihwYXRoLmV4dG5hbWUodXJsKSlcbiAgICB9XG4gIH0sXG5cbiAgZ2V0SW5pdGlhbFN0YXRlICgpIHtcbiAgICBjb25zdCBzID0gdGhpc1xuICAgIGxldCB7IHByb3BzIH0gPSBzXG4gICAgbGV0IGhhc1ZhbHVlID0gcHJvcHMudmFsdWUgJiYgcHJvcHMudmFsdWUubGVuZ3RoID4gMFxuICAgIHJldHVybiB7XG4gICAgICBzcGlubmluZzogZmFsc2UsXG4gICAgICBlcnJvcjogbnVsbCxcbiAgICAgIHVybHM6IGhhc1ZhbHVlID8gW10uY29uY2F0KHByb3BzLnZhbHVlKSA6IG51bGxcbiAgICB9XG4gIH0sXG5cbiAgZ2V0RGVmYXVsdFByb3BzICgpIHtcbiAgICByZXR1cm4ge1xuICAgICAgbmFtZTogbnVsbCxcbiAgICAgIGlkOiBgYXAtdXBsb2FkLSR7dXVpZC52NCgpfWAsXG4gICAgICBtdWx0aXBsZTogZmFsc2UsXG4gICAgICB3aWR0aDogMTgwLFxuICAgICAgaGVpZ2h0OiAxODAsXG4gICAgICBhY2NlcHQ6IG51bGwsXG4gICAgICB0ZXh0OiAnVXBsb2FkIGZpbGUnLFxuICAgICAgaWNvbjogJ2ZhIGZhLWNsb3VkLXVwbG9hZCcsXG4gICAgICBjbG9zZUljb246ICdmYSBmYS1jbG9zZScsXG4gICAgICBzcGlubmVySWNvbjogQXBTcGlubmVyLkRFRkFVTFRfVEhFTUUsXG4gICAgICBvbkNoYW5nZTogbnVsbCxcbiAgICAgIG9uTG9hZDogbnVsbCxcbiAgICAgIG9uRXJyb3I6IG51bGxcbiAgICB9XG4gIH0sXG5cbiAgcmVuZGVyICgpIHtcbiAgICBjb25zdCBzID0gdGhpc1xuICAgIGxldCB7IHN0YXRlLCBwcm9wcyB9ID0gc1xuICAgIGxldCB7IHdpZHRoLCBoZWlnaHQgfSA9IHByb3BzXG4gICAgcmV0dXJuIChcbiAgICAgIDxkaXYgY2xhc3NOYW1lPXtjbGFzc25hbWVzKCdhcC11cGxvYWQnLCBwcm9wcy5jbGFzc05hbWUpfVxuICAgICAgICAgICBzdHlsZT17T2JqZWN0LmFzc2lnbih7fSwgcHJvcHMuc3R5bGUpfT5cbiAgICAgICAgPGlucHV0IHR5cGU9J2ZpbGUnXG4gICAgICAgICAgICAgICBjbGFzc05hbWU9J2FwLXVwbG9hZC1pbnB1dCdcbiAgICAgICAgICAgICAgIG11bHRpcGxlPXsgcHJvcHMubXVsdGlwbGUgfVxuICAgICAgICAgICAgICAgbmFtZT17IHByb3BzLm5hbWUgfVxuICAgICAgICAgICAgICAgaWQ9eyBwcm9wcy5pZCB9XG4gICAgICAgICAgICAgICBhY2NlcHQ9eyBwcm9wcy5hY2NlcHQgfVxuICAgICAgICAgICAgICAgb25DaGFuZ2U9e3MuaGFuZGxlQ2hhbmdlfVxuICAgICAgICAgICAgICAgc3R5bGU9e3t3aWR0aCwgaGVpZ2h0fX1cbiAgICAgICAgLz5cbiAgICAgICAgPGxhYmVsIGNsYXNzTmFtZT0nYXAtdXBsb2FkLWxhYmVsJyBodG1sRm9yPXsgcHJvcHMuaWQgfT5cbiAgICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3NOYW1lPSdhcC11cGxvYWQtYWxpZ25lcic+XG4gICAgICAgICAgICAgICAgICAgIDwvc3Bhbj5cbiAgICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3NOYW1lPSdhcC11cGxvYWQtbGFiZWwtaW5uZXInPlxuICAgICAgICAgICAgICAgICAgICAgICAgPGkgY2xhc3NOYW1lPXsgY2xhc3NuYW1lcygnYXAtdXBsb2FkLWljb24nLCBwcm9wcy5pY29uKSB9Lz5cbiAgICAgICAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzTmFtZT0nYXAtdXBsb2FkLXRleHQnPntwcm9wcy50ZXh0fTwvc3Bhbj5cbiAgICAgICAgICAgICAgICAgICAgICB7IHByb3BzLmNoaWxkcmVuIH1cbiAgICAgICAgICAgICAgICAgICAgPC9zcGFuPlxuICAgICAgICA8L2xhYmVsPlxuICAgICAgICB7IHMuX3JlbmRlclByZXZpZXdJbWFnZShzdGF0ZS51cmxzLCB3aWR0aCwgaGVpZ2h0KSB9XG4gICAgICAgIHsgcy5fcmVuZGVyUmVtb3ZlQnV0dG9uKCEhKHN0YXRlLnVybHMgJiYgc3RhdGUudXJscy5sZW5ndGggPiAwKSwgcHJvcHMuY2xvc2VJY29uKSB9XG4gICAgICAgIHsgcy5fcmVuZGVyU3Bpbm5lcihzdGF0ZS5zcGlubmluZywgcHJvcHMuc3Bpbm5lcikgfVxuICAgICAgPC9kaXY+XG4gICAgKVxuICB9LFxuXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gIC8vIExpZmVjeWNsZVxuICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIC8vIC0tLS0tLS0tLS0tLS0tLS0tLVxuICAvLyBDdXN0b21cbiAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgaGFuZGxlQ2hhbmdlIChlKSB7XG4gICAgY29uc3QgcyA9IHRoaXNcbiAgICBsZXQgeyBwcm9wcyB9ID0gc1xuICAgIGxldCB7IHRhcmdldCB9ID0gZVxuICAgIGxldCBmaWxlcyA9IEFycmF5LnByb3RvdHlwZS5zbGljZS5jYWxsKHRhcmdldC5maWxlcywgMClcblxuICAgIGxldCB7IG9uQ2hhbmdlLCBvbkVycm9yLCBvbkxvYWQgfSA9IHByb3BzXG5cbiAgICBzLnNldFN0YXRlKHsgc3Bpbm5pbmc6IHRydWUgfSlcbiAgICBpZiAob25DaGFuZ2UpIHtcbiAgICAgIG9uQ2hhbmdlKGUpXG4gICAgfVxuICAgIGFzeW5jLmNvbmNhdChmaWxlcywgQXBVcGxvYWQucmVhZEZpbGUsIChlcnIsIHVybHMpID0+IHtcbiAgICAgIGUudXJscyA9IHVybHNcbiAgICAgIGUudGFyZ2V0ID0gdGFyZ2V0XG4gICAgICBzLnNldFN0YXRlKHtcbiAgICAgICAgc3Bpbm5pbmc6IGZhbHNlLFxuICAgICAgICBlcnJvcjogZXJyLFxuICAgICAgICB1cmxzOiB1cmxzXG4gICAgICB9KVxuICAgICAgaWYgKGVycikge1xuICAgICAgICBpZiAob25FcnJvcikge1xuICAgICAgICAgIG9uRXJyb3IoZXJyKVxuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpZiAob25Mb2FkKSB7XG4gICAgICAgICAgb25Mb2FkKGUpXG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9KVxuICB9LFxuXG4gIGhhbmRsZVJlbW92ZSAoKSB7XG4gICAgY29uc3QgcyA9IHRoaXNcbiAgICBsZXQgeyBwcm9wcyB9ID0gc1xuICAgIGxldCB7IG9uTG9hZCB9ID0gcHJvcHNcbiAgICBzLnNldFN0YXRlKHtcbiAgICAgIGVycm9yOiBudWxsLFxuICAgICAgdXJsczogbnVsbFxuICAgIH0pXG4gICAgaWYgKG9uTG9hZCkge1xuICAgICAgb25Mb2FkKFtdKVxuICAgIH1cbiAgfSxcblxuICAvLyAtLS0tLS0tLS0tLS0tLS0tLS1cbiAgLy8gUHJpdmF0ZVxuICAvLyAtLS0tLS0tLS0tLS0tLS0tLS1cblxuICBfcmVuZGVyU3Bpbm5lciAoc3Bpbm5pbmcsIHRoZW1lKSB7XG4gICAgY29uc3QgcyA9IHRoaXNcbiAgICByZXR1cm4gKFxuICAgICAgPEFwU3Bpbm5lciBlbmFibGVkPXtzcGlubmluZ30gdGhlbWU9e3RoZW1lfT5cbiAgICAgIDwvQXBTcGlubmVyPlxuICAgIClcbiAgfSxcblxuICBfcmVuZGVyUmVtb3ZlQnV0dG9uIChyZW1vdmFibGUsIGljb24pIHtcbiAgICBjb25zdCBzID0gdGhpc1xuICAgIGlmICghcmVtb3ZhYmxlKSB7XG4gICAgICByZXR1cm4gbnVsbFxuICAgIH1cbiAgICByZXR1cm4gKFxuICAgICAgPEFwQnV0dG9uIG9uVGFwPXsgcy5oYW5kbGVSZW1vdmUgfSBjbGFzc05hbWU9J2FwLXVwbG9hZC1yZW1vdmUtYnV0dG9uJz5cbiAgICAgICAgPGkgY2xhc3NOYW1lPXsgY2xhc3NuYW1lcygnYXAtdXBsb2FkLXJlbW92ZS1pY29uJywgaWNvbikgfS8+XG4gICAgICA8L0FwQnV0dG9uPlxuICAgIClcbiAgfSxcblxuICBfcmVuZGVyUHJldmlld0ltYWdlICh1cmxzLCB3aWR0aCwgaGVpZ2h0KSB7XG4gICAgaWYgKCF1cmxzKSB7XG4gICAgICByZXR1cm4gbnVsbFxuICAgIH1cbiAgICBjb25zdCBzID0gdGhpc1xuICAgIHJldHVybiB1cmxzXG4gICAgICAuZmlsdGVyKCh1cmwpID0+IEFwVXBsb2FkLmlzSW1hZ2VVcmwodXJsKSlcbiAgICAgIC5tYXAoKHVybCwgaSkgPT4gKFxuICAgICAgICA8QXBJbWFnZSBrZXk9eyB1cmwgfVxuICAgICAgICAgICAgICAgICBzcmM9eyB1cmwgfVxuICAgICAgICAgICAgICAgICBoZWlnaHQ9eyBoZWlnaHQgfVxuICAgICAgICAgICAgICAgICB3aWR0aD17IHdpZHRoIH1cbiAgICAgICAgICAgICAgICAgY2xhc3NOYW1lPXsgY2xhc3NuYW1lcygnYXAtdXBsb2FkLXByZXZpZXctaW1hZ2UnKSB9XG4gICAgICAgICAgICAgICAgIHN0eWxlPXsgeyBsZWZ0OiBgJHtpICogMTB9JWAsIHRvcDogYCR7aSAqIDEwfSVgIH0gfVxuICAgICAgICAgICAgICAgICBzY2FsZT0nZml0Jz5cbiAgICAgICAgPC9BcEltYWdlPlxuICAgICAgKSlcbiAgfVxufSlcblxuZXhwb3J0IGRlZmF1bHQgQXBVcGxvYWRcbiJdfQ==