jam-cloud/jam-ui/node_modules/react-jss/lib/createHoc.js

330 lines
12 KiB
JavaScript

'use strict';
Object.defineProperty(exports, "__esModule", {
value: true
});
var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; };
var _react = require('react');
var _react2 = _interopRequireDefault(_react);
var _propTypes = require('prop-types');
var _propTypes2 = _interopRequireDefault(_propTypes);
var _theming = require('theming');
var _theming2 = _interopRequireDefault(_theming);
var _jss = require('./jss');
var _jss2 = _interopRequireDefault(_jss);
var _compose = require('./compose');
var _compose2 = _interopRequireDefault(_compose);
var _getDisplayName = require('./getDisplayName');
var _getDisplayName2 = _interopRequireDefault(_getDisplayName);
var _ns = require('./ns');
var ns = _interopRequireWildcard(_ns);
var _contextTypes = require('./contextTypes');
var _contextTypes2 = _interopRequireDefault(_contextTypes);
function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj['default'] = obj; return newObj; } }
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { 'default': obj }; }
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
function _objectWithoutProperties(obj, keys) { var target = {}; for (var i in obj) { if (keys.indexOf(i) >= 0) continue; if (!Object.prototype.hasOwnProperty.call(obj, i)) continue; target[i] = obj[i]; } return target; }
var env = process.env.NODE_ENV;
// Like a Symbol
var dynamicStylesNs = Math.random();
/*
* # Use cases
*
* - Unthemed component accepts styles object
* - Themed component accepts styles creator function which takes theme as a single argument
* - Multiple instances will re-use the same static sheet via sheets manager
* - Sheet manager identifies static sheets by theme as a key
* - For unthemed components theme is an empty object
* - The very first instance will add static sheet to sheets manager
* - Every further instances will get that static sheet from sheet manager
* - Every mount of every instance will call method `sheetsManager.manage`,
* thus incrementing reference counter.
* - Every unmount of every instance will call method `sheetsManager.unmanage`,
* thus decrementing reference counter.
* - `sheetsManager.unmanage` under the hood will detach static sheet once reference
* counter is zero.
* - Dynamic styles are not shared between instances
*
*/
var getStyles = function getStyles(stylesOrCreator, theme) {
if (typeof stylesOrCreator !== 'function') {
return stylesOrCreator;
}
return stylesOrCreator(theme);
};
// Returns an object with array property as a key and true as a value.
var toMap = function toMap(arr) {
return arr.reduce(function (map, prop) {
map[prop] = true;
return map;
}, {});
};
var defaultInjectProps = {
sheet: false,
classes: true,
theme: true
};
var managersCounter = 0;
/**
* Wrap a Component into a JSS Container Component.
*
* @param {Object|Function} stylesOrCreator
* @param {Component} InnerComponent
* @param {Object} [options]
* @return {Component}
*/
exports['default'] = function (stylesOrCreator, InnerComponent) {
var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
var isThemingEnabled = typeof stylesOrCreator === 'function';
var _options$theming = options.theming,
theming = _options$theming === undefined ? _theming2['default'] : _options$theming,
inject = options.inject,
optionsJss = options.jss,
sheetOptions = _objectWithoutProperties(options, ['theming', 'inject', 'jss']);
var injectMap = inject ? toMap(inject) : defaultInjectProps;
var themeListener = theming.themeListener;
var displayName = (0, _getDisplayName2['default'])(InnerComponent);
var defaultClassNamePrefix = env === 'production' ? undefined : displayName + '-';
var noTheme = {};
var managerId = managersCounter++;
var manager = new _jss.SheetsManager();
var defaultProps = _extends({}, InnerComponent.defaultProps);
delete defaultProps.classes;
var Jss = function (_Component) {
_inherits(Jss, _Component);
function Jss(props, context) {
_classCallCheck(this, Jss);
var _this = _possibleConstructorReturn(this, (Jss.__proto__ || Object.getPrototypeOf(Jss)).call(this, props, context));
_initialiseProps.call(_this);
var theme = isThemingEnabled ? themeListener.initial(context) : noTheme;
_this.state = _this.createState({ theme: theme }, props);
return _this;
}
_createClass(Jss, [{
key: 'componentWillMount',
value: function componentWillMount() {
this.manage(this.state);
}
}, {
key: 'componentDidMount',
value: function componentDidMount() {
if (isThemingEnabled) {
this.unsubscribeId = themeListener.subscribe(this.context, this.setTheme);
}
}
}, {
key: 'componentWillReceiveProps',
value: function componentWillReceiveProps(nextProps, nextContext) {
this.context = nextContext;
var dynamicSheet = this.state.dynamicSheet;
if (dynamicSheet) dynamicSheet.update(nextProps);
}
}, {
key: 'componentWillUpdate',
value: function componentWillUpdate(nextProps, nextState) {
if (isThemingEnabled && this.state.theme !== nextState.theme) {
var newState = this.createState(nextState, nextProps);
this.manage(newState);
this.manager.unmanage(this.state.theme);
this.setState(newState);
}
}
}, {
key: 'componentDidUpdate',
value: function componentDidUpdate(prevProps, prevState) {
// We remove previous dynamicSheet only after new one was created to avoid FOUC.
if (prevState.dynamicSheet !== this.state.dynamicSheet) {
this.jss.removeStyleSheet(prevState.dynamicSheet);
}
}
}, {
key: 'componentWillUnmount',
value: function componentWillUnmount() {
if (this.unsubscribeId) {
themeListener.unsubscribe(this.context, this.unsubscribeId);
}
this.manager.unmanage(this.state.theme);
if (this.state.dynamicSheet) {
this.state.dynamicSheet.detach();
}
}
}, {
key: 'createState',
value: function createState(_ref, _ref2) {
var theme = _ref.theme,
dynamicSheet = _ref.dynamicSheet;
var userClasses = _ref2.classes;
var contextSheetOptions = this.context[ns.sheetOptions];
if (contextSheetOptions && contextSheetOptions.disableStylesGeneration) {
return { theme: theme, dynamicSheet: dynamicSheet, classes: {} };
}
var classNamePrefix = defaultClassNamePrefix;
var staticSheet = this.manager.get(theme);
if (contextSheetOptions && contextSheetOptions.classNamePrefix) {
classNamePrefix = contextSheetOptions.classNamePrefix + classNamePrefix;
}
if (!staticSheet) {
var styles = getStyles(stylesOrCreator, theme);
staticSheet = this.jss.createStyleSheet(styles, _extends({}, sheetOptions, contextSheetOptions, {
meta: displayName + ', ' + (isThemingEnabled ? 'Themed' : 'Unthemed') + ', Static',
classNamePrefix: classNamePrefix
}));
this.manager.add(theme, staticSheet);
staticSheet[dynamicStylesNs] = (0, _jss.getDynamicStyles)(styles);
}
var dynamicStyles = staticSheet[dynamicStylesNs];
if (dynamicStyles) {
dynamicSheet = this.jss.createStyleSheet(dynamicStyles, _extends({}, sheetOptions, contextSheetOptions, {
meta: displayName + ', ' + (isThemingEnabled ? 'Themed' : 'Unthemed') + ', Dynamic',
classNamePrefix: classNamePrefix,
link: true
}));
}
var defaultClasses = InnerComponent.defaultProps ? InnerComponent.defaultProps.classes : {};
var jssClasses = dynamicSheet ? (0, _compose2['default'])(staticSheet.classes, dynamicSheet.classes) : staticSheet.classes;
var classes = _extends({}, defaultClasses, jssClasses, userClasses);
return { theme: theme, dynamicSheet: dynamicSheet, classes: classes };
}
}, {
key: 'manage',
value: function manage(_ref3) {
var theme = _ref3.theme,
dynamicSheet = _ref3.dynamicSheet;
var contextSheetOptions = this.context[ns.sheetOptions];
if (contextSheetOptions && contextSheetOptions.disableStylesGeneration) {
return;
}
var registry = this.context[ns.sheetsRegistry];
var staticSheet = this.manager.manage(theme);
if (registry) registry.add(staticSheet);
if (dynamicSheet) {
dynamicSheet.update(this.props).attach();
if (registry) registry.add(dynamicSheet);
}
}
}, {
key: 'render',
value: function render() {
var _state = this.state,
theme = _state.theme,
dynamicSheet = _state.dynamicSheet,
classes = _state.classes;
var _props = this.props,
innerRef = _props.innerRef,
props = _objectWithoutProperties(_props, ['innerRef']);
var sheet = dynamicSheet || this.manager.get(theme);
if (injectMap.sheet && !props.sheet) props.sheet = sheet;
if (isThemingEnabled && injectMap.theme && !props.theme) props.theme = theme;
// We have merged classes already.
if (injectMap.classes) props.classes = classes;
return _react2['default'].createElement(InnerComponent, _extends({ ref: innerRef }, props));
}
}, {
key: 'jss',
get: function get() {
return this.context[ns.jss] || optionsJss || _jss2['default'];
}
}, {
key: 'manager',
get: function get() {
var managers = this.context[ns.managers];
// If `managers` map is present in the context, we use it in order to
// let JssProvider reset them when new response has to render server-side.
if (managers) {
if (!managers[managerId]) {
managers[managerId] = new _jss.SheetsManager();
}
return managers[managerId];
}
return manager;
}
}]);
return Jss;
}(_react.Component);
Jss.displayName = 'Jss(' + displayName + ')';
Jss.InnerComponent = InnerComponent;
Jss.contextTypes = _extends({}, _contextTypes2['default'], isThemingEnabled && themeListener.contextTypes);
Jss.propTypes = {
innerRef: _propTypes2['default'].func
};
Jss.defaultProps = defaultProps;
var _initialiseProps = function _initialiseProps() {
var _this2 = this;
this.setTheme = function (theme) {
return _this2.setState({ theme: theme });
};
};
return Jss;
};