@wordpress/components
Version:
UI components for WordPress.
284 lines (247 loc) • 8.3 kB
JavaScript
"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = void 0;
var _element = require("@wordpress/element");
var _classnames = _interopRequireDefault(require("classnames"));
var _lodash = require("lodash");
var _alpha = _interopRequireDefault(require("./alpha"));
var _hue = _interopRequireDefault(require("./hue"));
var _inputs = _interopRequireDefault(require("./inputs"));
var _saturation = _interopRequireDefault(require("./saturation"));
var _utils = require("./utils");
/**
* Parts of this source were derived and modified from react-color,
* released under the MIT license.
*
* https://github.com/casesandberg/react-color/
*
* Copyright (c) 2015 Case Sandberg
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
/**
* External dependencies
*/
/**
* WordPress dependencies
*/
/**
* Internal dependencies
*/
const toLowerCase = value => String(value).toLowerCase();
const isValueEmpty = data => {
if (data.source === 'hex' && data.hex === undefined) {
return true;
}
if (data.source === 'hsl' && (data.h === undefined || data.s === undefined || data.l === undefined)) {
return true;
}
/**
* Check that if source is `rgb`:
* `r`, `g` or `b` properties are not undefined
* OR (||) `h`, `s`, `v` or `a` properties are not undefined
* OR (||) `h`, `s`, `l` or `a` properties are not undefined
*
* before it was checking with NOT(!) statement witch for `0` (bool|int) values returns `true`
* this is a typecasting issue only visible for hex values that derive from #000000
*/
return data.source === 'rgb' && (data.r === undefined || data.g === undefined || data.b === undefined) && (data.h === undefined || data.s === undefined || data.v === undefined || data.a === undefined) && (data.h === undefined || data.s === undefined || data.l === undefined || data.a === undefined);
};
const isValidColor = colors => colors.hex ? (0, _utils.isValidHex)(colors.hex) : (0, _utils.simpleCheckForValidColor)(colors);
/**
* Function that creates the new color object
* from old data and the new value.
*
* @param {Object} oldColors The old color object.
* @param {string} oldColors.hex
* @param {Object} oldColors.rgb
* @param {number} oldColors.rgb.r
* @param {number} oldColors.rgb.g
* @param {number} oldColors.rgb.b
* @param {number} oldColors.rgb.a
* @param {Object} oldColors.hsl
* @param {number} oldColors.hsl.h
* @param {number} oldColors.hsl.s
* @param {number} oldColors.hsl.l
* @param {number} oldColors.hsl.a
* @param {string} oldColors.draftHex Same format as oldColors.hex
* @param {Object} oldColors.draftRgb Same format as oldColors.rgb
* @param {Object} oldColors.draftHsl Same format as oldColors.hsl
* @param {Object} data Data containing the new value to update.
* @param {Object} data.source One of `hex`, `rgb`, `hsl`.
* @param {string|number} data.value Value to update.
* @param {string} data.valueKey Depends on `data.source` values:
* - when source = `rgb`, valuKey can be `r`, `g`, `b`, or `a`.
* - when source = `hsl`, valuKey can be `h`, `s`, `l`, or `a`.
* @return {Object} A new color object for a specific source. For example:
* { source: 'rgb', r: 1, g: 2, b:3, a:0 }
*/
const dataToColors = (oldColors, {
source,
valueKey,
value
}) => {
if (source === 'hex') {
return {
source,
[source]: value
};
}
return {
source,
...{ ...oldColors[source],
...{
[valueKey]: value
}
}
};
};
class ColorPicker extends _element.Component {
constructor({
color = '0071a1'
}) {
super(...arguments);
const colors = (0, _utils.colorToState)(color);
this.state = { ...colors,
draftHex: toLowerCase(colors.hex),
draftRgb: colors.rgb,
draftHsl: colors.hsl
};
this.commitValues = this.commitValues.bind(this);
this.setDraftValues = this.setDraftValues.bind(this);
this.resetDraftValues = this.resetDraftValues.bind(this);
this.handleInputChange = this.handleInputChange.bind(this);
}
commitValues(data) {
const {
oldHue,
onChangeComplete = _lodash.noop
} = this.props;
if (isValidColor(data)) {
const colors = (0, _utils.colorToState)(data, data.h || oldHue);
this.setState({ ...colors,
draftHex: toLowerCase(colors.hex),
draftHsl: colors.hsl,
draftRgb: colors.rgb
}, (0, _lodash.debounce)((0, _lodash.partial)(onChangeComplete, colors), 100));
}
}
resetDraftValues() {
this.setState({
draftHex: this.state.hex,
draftHsl: this.state.hsl,
draftRgb: this.state.rgb
});
}
setDraftValues(data) {
switch (data.source) {
case 'hex':
this.setState({
draftHex: toLowerCase(data.hex)
});
break;
case 'rgb':
this.setState({
draftRgb: data
});
break;
case 'hsl':
this.setState({
draftHsl: data
});
break;
}
}
handleInputChange(data) {
switch (data.state) {
case 'reset':
this.resetDraftValues();
break;
case 'commit':
const colors = dataToColors(this.state, data);
if (!isValueEmpty(colors)) {
this.commitValues(colors);
}
break;
case 'draft':
this.setDraftValues(dataToColors(this.state, data));
break;
}
}
render() {
const {
className,
disableAlpha
} = this.props;
const {
color,
hsl,
hsv,
rgb,
draftHex,
draftHsl,
draftRgb
} = this.state;
const classes = (0, _classnames.default)(className, {
'components-color-picker': true,
'is-alpha-disabled': disableAlpha,
'is-alpha-enabled': !disableAlpha
});
return (0, _element.createElement)("div", {
className: classes
}, (0, _element.createElement)("div", {
className: "components-color-picker__saturation"
}, (0, _element.createElement)(_saturation.default, {
hsl: hsl,
hsv: hsv,
onChange: this.commitValues
})), (0, _element.createElement)("div", {
className: "components-color-picker__body"
}, (0, _element.createElement)("div", {
className: "components-color-picker__controls"
}, (0, _element.createElement)("div", {
className: "components-color-picker__swatch"
}, (0, _element.createElement)("div", {
className: "components-color-picker__active",
style: {
backgroundColor: color && color.toRgbString()
}
})), (0, _element.createElement)("div", {
className: "components-color-picker__toggles"
}, (0, _element.createElement)(_hue.default, {
hsl: hsl,
onChange: this.commitValues
}), disableAlpha ? null : (0, _element.createElement)(_alpha.default, {
rgb: rgb,
hsl: hsl,
onChange: this.commitValues
}))), (0, _element.createElement)(_inputs.default, {
rgb: draftRgb,
hsl: draftHsl,
hex: draftHex,
onChange: this.handleInputChange,
disableAlpha: disableAlpha
})));
}
}
exports.default = ColorPicker;
//# sourceMappingURL=index.js.map