text: import "./ColorPicker.css";
  
  import Hammer from "../module/hammer";
  import { onTouch } from "../hammerUtil";
  import {
    HSVToRGB,
    RGBToHSV,
    hexToRGB,
    isString,
    isValidHex,
    isValidRGB,
    isValidRGBA,
  } from "vis-util/esnext";
  
  const htmlColors = {
    black: "#000000",
    navy: "#000080",
    darkblue: "#00008B",
    mediumblue: "#0000CD",
    blue: "#0000FF",
    darkgreen: "#006400",
    green: "#008000",
    teal: "#008080",
    darkcyan: "#008B8B",
    deepskyblue: "#00BFFF",
    darkturquoise: "#00CED1",
    mediumspringgreen: "#00FA9A",
    lime: "#00FF00",
    springgreen: "#00FF7F",
    aqua: "#00FFFF",
    cyan: "#00FFFF",
    midnightblue: "#191970",
    dodgerblue: "#1E90FF",
    lightseagreen: "#20B2AA",
    forestgreen: "#228B22",
    seagreen: "#2E8B57",
    darkslategray: "#2F4F4F",
    limegreen: "#32CD32",
    mediumseagreen: "#3CB371",
    turquoise: "#40E0D0",
    royalblue: "#4169E1",
    steelblue: "#4682B4",
    darkslateblue: "#483D8B",
    mediumturquoise: "#48D1CC",
    indigo: "#4B0082",
    darkolivegreen: "#556B2F",
    cadetblue: "#5F9EA0",
    cornflowerblue: "#6495ED",
    mediumaquamarine: "#66CDAA",
    dimgray: "#696969",
    slateblue: "#6A5ACD",
    olivedrab: "#6B8E23",
    slategray: "#708090",
    lightslategray: "#778899",
    mediumslateblue: "#7B68EE",
    lawngreen: "#7CFC00",
    chartreuse: "#7FFF00",
    aquamarine: "#7FFFD4",
    maroon: "#800000",
    purple: "#800080",
    olive: "#808000",
    gray: "#808080",
    skyblue: "#87CEEB",
    lightskyblue: "#87CEFA",
    blueviolet: "#8A2BE2",
    darkred: "#8B0000",
    darkmagenta: "#8B008B",
    saddlebrown: "#8B4513",
    darkseagreen: "#8FBC8F",
    lightgreen: "#90EE90",
    mediumpurple: "#9370D8",
    darkviolet: "#9400D3",
    palegreen: "#98FB98",
    darkorchid: "#9932CC",
    yellowgreen: "#9ACD32",
    sienna: "#A0522D",
    brown: "#A52A2A",
    darkgray: "#A9A9A9",
    lightblue: "#ADD8E6",
    greenyellow: "#ADFF2F",
    paleturquoise: "#AFEEEE",
    lightsteelblue: "#B0C4DE",
    powderblue: "#B0E0E6",
    firebrick: "#B22222",
    darkgoldenrod: "#B8860B",
    mediumorchid: "#BA55D3",
    rosybrown: "#BC8F8F",
    darkkhaki: "#BDB76B",
    silver: "#C0C0C0",
    mediumvioletred: "#C71585",
    indianred: "#CD5C5C",
    peru: "#CD853F",
    chocolate: "#D2691E",
    tan: "#D2B48C",
    lightgrey: "#D3D3D3",
    palevioletred: "#D87093",
    thistle: "#D8BFD8",
    orchid: "#DA70D6",
    goldenrod: "#DAA520",
    crimson: "#DC143C",
    gainsboro: "#DCDCDC",
    plum: "#DDA0DD",
    burlywood: "#DEB887",
    lightcyan: "#E0FFFF",
    lavender: "#E6E6FA",
    darksalmon: "#E9967A",
    violet: "#EE82EE",
    palegoldenrod: "#EEE8AA",
    lightcoral: "#F08080",
    khaki: "#F0E68C",
    aliceblue: "#F0F8FF",
    honeydew: "#F0FFF0",
    azure: "#F0FFFF",
    sandybrown: "#F4A460",
    wheat: "#F5DEB3",
    beige: "#F5F5DC",
    whitesmoke: "#F5F5F5",
    mintcream: "#F5FFFA",
    ghostwhite: "#F8F8FF",
    salmon: "#FA8072",
    antiquewhite: "#FAEBD7",
    linen: "#FAF0E6",
    lightgoldenrodyellow: "#FAFAD2",
    oldlace: "#FDF5E6",
    red: "#FF0000",
    fuchsia: "#FF00FF",
    magenta: "#FF00FF",
    deeppink: "#FF1493",
    orangered: "#FF4500",
    tomato: "#FF6347",
    hotpink: "#FF69B4",
    coral: "#FF7F50",
    darkorange: "#FF8C00",
    lightsalmon: "#FFA07A",
    orange: "#FFA500",
    lightpink: "#FFB6C1",
    pink: "#FFC0CB",
    gold: "#FFD700",
    peachpuff: "#FFDAB9",
    navajowhite: "#FFDEAD",
    moccasin: "#FFE4B5",
    bisque: "#FFE4C4",
    mistyrose: "#FFE4E1",
    blanchedalmond: "#FFEBCD",
    papayawhip: "#FFEFD5",
    lavenderblush: "#FFF0F5",
    seashell: "#FFF5EE",
    cornsilk: "#FFF8DC",
    lemonchiffon: "#FFFACD",
    floralwhite: "#FFFAF0",
    snow: "#FFFAFA",
    yellow: "#FFFF00",
    lightyellow: "#FFFFE0",
    ivory: "#FFFFF0",
    white: "#FFFFFF",
  };
  
  /**
   * @param {number} [pixelRatio=1]
   */
  class ColorPicker {
    /**
     * @param {number} [pixelRatio=1]
     */
    constructor(pixelRatio = 1) {
      this.pixelRatio = pixelRatio;
      this.generated = false;
      this.centerCoordinates = { x: 289 / 2, y: 289 / 2 };
      this.r = 289 * 0.49;
      this.color = { r: 255, g: 255, b: 255, a: 1.0 };
      this.hueCircle = undefined;
      this.initialColor = { r: 255, g: 255, b: 255, a: 1.0 };
      this.previousColor = undefined;
      this.applied = false;
  
      // bound by
      this.updateCallback = () => {};
      this.closeCallback = () => {};
  
      // create all DOM elements
      this._create();
    }
  
    /**
     * this inserts the colorPicker into a div from the DOM
     *
     * @param {Element} container
     */
    insertTo(container) {
      if (this.hammer !== undefined) {
        this.hammer.destroy();
        this.hammer = undefined;
      }
      this.container = container;
      this.container.appendChild(this.frame);
      this._bindHammer();
  
      this._setSize();
    }
  
    /**
     * the callback is executed on apply and save. Bind it to the application
     *
     * @param {Function} callback
     */
    setUpdateCallback(callback) {
      if (typeof callback === "function") {
        this.updateCallback = callback;
      } else {
        throw new Error(
          "Function attempted to set as colorPicker update callback is not a function."
        );
      }
    }
  
    /**
     * the callback is executed on apply and save. Bind it to the application
     *
     * @param {Function} callback
     */
    setCloseCallback(callback) {
      if (typeof callback === "function") {
        this.closeCallback = callback;
      } else {
        throw new Error(
          "Function attempted to set as colorPicker closing callback is not a function."
        );
      }
    }
  
    /**
     *
     * @param {string} color
     * @returns {string}
     * @private
     */
    _isColorString(color) {
      if (typeof color === "string") {
        return htmlColors[color];
      }
    }
  
    /**
     * Set the color of the colorPicker
     * Supported formats:
     * 'red'                   --> HTML color string
     * '#ffffff'               --> hex string
     * 'rgb(255,255,255)'      --> rgb string
     * 'rgba(255,255,255,1.0)' --> rgba string
     * {r:255,g:255,b:255}     --> rgb object
     * {r:255,g:255,b:255,a:1.0} --> rgba object
     *
     * @param {string | object} color
     * @param {boolean} [setInitial=true]
     */
    setColor(color, setInitial = true) {
      if (color === "none") {
        return;
      }
  
      let rgba;
  
      // if a html color shorthand is used, convert to hex
      const htmlColor = this._isColorString(color);
      if (htmlColor !== undefined) {
        color = htmlColor;
      }
  
      // check format
      if (isString(color) === true) {
        if (isValidRGB(color) === true) {
          const rgbaArray = color
            .substr(4)
            .substr(0, color.length - 5)
            .split(",");
          rgba = { r: rgbaArray[0], g: rgbaArray[1], b: rgbaArray[2], a: 1.0 };
        } else if (isValidRGBA(color) === true) {
          const rgbaArray = color
            .substr(5)
            .substr(0, color.length - 6)
            .split(",");
          rgba = {
            r: rgbaArray[0],
            g: rgbaArray[1],
            b: rgbaArray[2],
            a: rgbaArray[3],
          };
        } else if (isValidHex(color) === true) {
          const rgbObj = hexToRGB(color);
          rgba = { r: rgbObj.r, g: rgbObj.g, b: rgbObj.b, a: 1.0 };
        }
      } else {
        if (color instanceof Object) {
          if (
            color.r !== undefined &&
            color.g !== undefined &&
            color.b !== undefined
          ) {
            const alpha = color.a !== undefined ? color.a : "1.0";
            rgba = { r: color.r, g: color.g, b: color.b, a: alpha };
          }
        }
      }
  
      // set color
      if (rgba === undefined) {
        throw new Error(
          "Unknown color passed to the colorPicker. Supported are strings: rgb, hex, rgba. Object: rgb ({r:r,g:g,b:b,[a:a]}). Supplied: " +
            JSON.stringify(color)
        );
      } else {
        this._setColor(rgba, setInitial);
      }
    }
  
    /**
     * this shows the color picker.
     * The hue circle is constructed once and stored.
     */
    show() {
      if (this.closeCallback !== undefined) {
        this.closeCallback();
        this.closeCallback = undefined;
      }
  
      this.applied = false;
      this.frame.style.display = "block";
      this._generateHueCircle();
    }
  
    // ------------------------------------------ PRIVATE ----------------------------- //
  
    /**
     * Hide the picker. Is called by the cancel button.
     * Optional boolean to store the previous color for easy access later on.
     *
     * @param {boolean} [storePrevious=true]
     * @private
     */
    _hide(storePrevious = true) {
      // store the previous color for next time;
      if (storePrevious === true) {
        this.previousColor = Object.assign({}, this.color);
      }
  
      if (this.applied === true) {
        this.updateCallback(this.initialColor);
      }
  
      this.frame.style.display = "none";
  
      // call the closing callback, restoring the onclick method.
      // this is in a setTimeout because it will trigger the show again before the click is done.
      setTimeout(() => {
        if (this.closeCallback !== undefined) {
          this.closeCallback();
          this.closeCallback = undefined;
        }
      }, 0);
    }
  
    /**
     * bound to the save button. Saves and hides.
     *
     * @private
     */
    _save() {
      this.updateCallback(this.color);
      this.applied = false;
      this._hide();
    }
  
    /**
     * Bound to apply button. Saves but does not close. Is undone by the cancel button.
     *
     * @private
     */
    _apply() {
      this.applied = true;
      this.updateCallback(this.color);
      this._updatePicker(this.color);
    }
  
    /**
     * load the color from the previous session.
     *
     * @private
     */
    _loadLast() {
      if (this.previousColor !== undefined) {
        this.setColor(this.previousColor, false);
      } else {
        alert("There is no last color to load...");
      }
    }
  
    /**
     * set the color, place the picker
     *
     * @param {object} rgba
     * @param {boolean} [setInitial=true]
     * @private
     */
    _setColor(rgba, setInitial = true) {
      // store the initial color
      if (setInitial === true) {
        this.initialColor = Object.assign({}, rgba);
      }
  
      this.color = rgba;
      const hsv = RGBToHSV(rgba.r, rgba.g, rgba.b);
  
      const angleConvert = 2 * Math.PI;
      const radius = this.r * hsv.s;
      const x =
        this.centerCoordinates.x + radius * Math.sin(angleConvert * hsv.h);
      const y =
        this.centerCoordinates.y + radius * Math.cos(angleConvert * hsv.h);
  
      this.colorPickerSelector.style.left =
        x - 0.5 * this.colorPickerSelector.clientWidth + "px";
      this.colorPickerSelector.style.top =
        y - 0.5 * this.colorPickerSelector.clientHeight + "px";
  
      this._updatePicker(rgba);
    }
  
    /**
     * bound to opacity control
     *
     * @param {number} value
     * @private
     */
    _setOpacity(value) {
      this.color.a = value / 100;
      this._updatePicker(this.color);
    }
  
    /**
     * bound to brightness control
     *
     * @param {number} value
     * @private
     */
    _setBrightness(value) {
      const hsv = RGBToHSV(this.color.r, this.color.g, this.color.b);
      hsv.v = value / 100;
      const rgba = HSVToRGB(hsv.h, hsv.s, hsv.v);
      rgba["a"] = this.color.a;
      this.color = rgba;
      this._updatePicker();
    }
  
    /**
     * update the color picker. A black circle overlays the hue circle to mimic the brightness decreasing.
     *
     * @param {object} rgba
     * @private
     */
    _updatePicker(rgba = this.color) {
      const hsv = RGBToHSV(rgba.r, rgba.g, rgba.b);
      const ctx = this.colorPickerCanvas.getContext("2d");
      if (this.pixelRation === undefined) {
        this.pixelRatio =
          (window.devicePixelRatio || 1) /
          (ctx.webkitBackingStorePixelRatio ||
            ctx.mozBackingStorePixelRatio ||
            ctx.msBackingStorePixelRatio ||
            ctx.oBackingStorePixelRatio ||
            ctx.backingStorePixelRatio ||
            1);
      }
      ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
  
      // clear the canvas
      const w = this.colorPickerCanvas.clientWidth;
      const h = this.colorPickerCanvas.clientHeight;
      ctx.clearRect(0, 0, w, h);
  
      ctx.putImageData(this.hueCircle, 0, 0);
      ctx.fillStyle = "rgba(0,0,0," + (1 - hsv.v) + ")";
      ctx.circle(this.centerCoordinates.x, this.centerCoordinates.y, this.r);
      ctx.fill();
  
      this.brightnessRange.value = 100 * hsv.v;
      this.opacityRange.value = 100 * rgba.a;
  
      this.initialColorDiv.style.backgroundColor =
        "rgba(" +
        this.initialColor.r +
        "," +
        this.initialColor.g +
        "," +
        this.initialColor.b +
        "," +
        this.initialColor.a +
        ")";
      this.newColorDiv.style.backgroundColor =
        "rgba(" +
        this.color.r +
        "," +
        this.color.g +
        "," +
        this.color.b +
        "," +
        this.color.a +
        ")";
    }
  
    /**
     * used by create to set the size of the canvas.
     *
     * @private
     */
    _setSize() {
      this.colorPickerCanvas.style.width = "100%";
      this.colorPickerCanvas.style.height = "100%";
  
      this.colorPickerCanvas.width = 289 * this.pixelRatio;
      this.colorPickerCanvas.height = 289 * this.pixelRatio;
    }
  
    /**
     * create all dom elements
     * TODO: cleanup, lots of similar dom elements
     *
     * @private
     */
    _create() {
      this.frame = document.createElement("div");
      this.frame.className = "vis-color-picker";
  
      this.colorPickerDiv = document.createElement("div");
      this.colorPickerSelector = document.createElement("div");
      this.colorPickerSelector.className = "vis-selector";
      this.colorPickerDiv.appendChild(this.colorPickerSelector);
  
      this.colorPickerCanvas = document.createElement("canvas");
      this.colorPickerDiv.appendChild(this.colorPickerCanvas);
  
      if (!this.colorPickerCanvas.getContext) {
        const noCanvas = document.createElement("DIV");
        noCanvas.style.color = "red";
        noCanvas.style.fontWeight = "bold";
        noCanvas.style.padding = "10px";
        noCanvas.innerHTML = "Error: your browser does not support HTML canvas";
        this.colorPickerCanvas.appendChild(noCanvas);
      } else {
        const ctx = this.colorPickerCanvas.getContext("2d");
        this.pixelRatio =
          (window.devicePixelRatio || 1) /
          (ctx.webkitBackingStorePixelRatio ||
            ctx.mozBackingStorePixelRatio ||
            ctx.msBackingStorePixelRatio ||
            ctx.oBackingStorePixelRatio ||
            ctx.backingStorePixelRatio ||
            1);
        this.colorPickerCanvas
          .getContext("2d")
          .setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
      }
  
      this.colorPickerDiv.className = "vis-color";
  
      this.opacityDiv = document.createElement("div");
      this.opacityDiv.className = "vis-opacity";
  
      this.brightnessDiv = document.createElement("div");
      this.brightnessDiv.className = "vis-brightness";
  
      this.arrowDiv = document.createElement("div");
      this.arrowDiv.className = "vis-arrow";
  
      this.opacityRange = document.createElement("input");
      try {
        this.opacityRange.type = "range"; // Not supported on IE9
        this.opacityRange.min = "0";
        this.opacityRange.max = "100";
      } catch (err) {
        // TODO: Add some error handling.
      }
      this.opacityRange.value = "100";
      this.opacityRange.className = "vis-range";
  
      this.brightnessRange = document.createElement("input");
      try {
        this.brightnessRange.type = "range"; // Not supported on IE9
        this.brightnessRange.min = "0";
        this.brightnessRange.max = "100";
      } catch (err) {
        // TODO: Add some error handling.
      }
      this.brightnessRange.value = "100";
      this.brightnessRange.className = "vis-range";
  
      this.opacityDiv.appendChild(this.opacityRange);
      this.brightnessDiv.appendChild(this.brightnessRange);
  
      const me = this;
      this.opacityRange.onchange = function () {
        me._setOpacity(this.value);
      };
      this.opacityRange.oninput = function () {
        me._setOpacity(this.value);
      };
      this.brightnessRange.onchange = function () {
        me._setBrightness(this.value);
      };
      this.brightnessRange.oninput = function () {
        me._setBrightness(this.value);
      };
  
      this.brightnessLabel = document.createElement("div");
      this.brightnessLabel.className = "vis-label vis-brightness";
      this.brightnessLabel.innerHTML = "brightness:";
  
      this.opacityLabel = document.createElement("div");
      this.opacityLabel.className = "vis-label vis-opacity";
      this.opacityLabel.innerHTML = "opacity:";
  
      this.newColorDiv = document.createElement("div");
      this.newColorDiv.className = "vis-new-color";
      this.newColorDiv.innerHTML = "new";
  
      this.initialColorDiv = document.createElement("div");
      this.initialColorDiv.className = "vis-initial-color";
      this.initialColorDiv.innerHTML = "initial";
  
      this.cancelButton = document.createElement("div");
      this.cancelButton.className = "vis-button vis-cancel";
      this.cancelButton.innerHTML = "cancel";
      this.cancelButton.onclick = this._hide.bind(this, false);
  
      this.applyButton = document.createElement("div");
      this.applyButton.className = "vis-button vis-apply";
      this.applyButton.innerHTML = "apply";
      this.applyButton.onclick = this._apply.bind(this);
  
      this.saveButton = document.createElement("div");
      this.saveButton.className = "vis-button vis-save";
      this.saveButton.innerHTML = "save";
      this.saveButton.onclick = this._save.bind(this);
  
      this.loadButton = document.createElement("div");
      this.loadButton.className = "vis-button vis-load";
      this.loadButton.innerHTML = "load last";
      this.loadButton.onclick = this._loadLast.bind(this);
  
      this.frame.appendChild(this.colorPickerDiv);
      this.frame.appendChild(this.arrowDiv);
      this.frame.appendChild(this.brightnessLabel);
      this.frame.appendChild(this.brightnessDiv);
      this.frame.appendChild(this.opacityLabel);
      this.frame.appendChild(this.opacityDiv);
      this.frame.appendChild(this.newColorDiv);
      this.frame.appendChild(this.initialColorDiv);
  
      this.frame.appendChild(this.cancelButton);
      this.frame.appendChild(this.applyButton);
      this.frame.appendChild(this.saveButton);
      this.frame.appendChild(this.loadButton);
    }
  
    /**
     * bind hammer to the color picker
     *
     * @private
     */
    _bindHammer() {
      this.drag = {};
      this.pinch = {};
      this.hammer = new Hammer(this.colorPickerCanvas);
      this.hammer.get("pinch").set({ enable: true });
  
      onTouch(this.hammer, (event) => {
        this._moveSelector(event);
      });
      this.hammer.on("tap", (event) => {
        this._moveSelector(event);
      });
      this.hammer.on("panstart", (event) => {
        this._moveSelector(event);
      });
      this.hammer.on("panmove", (event) => {
        this._moveSelector(event);
      });
      this.hammer.on("panend", (event) => {
        this._moveSelector(event);
      });
    }
  
    /**
     * generate the hue circle. This is relatively heavy (200ms) and is done only once on the first time it is shown.
     *
     * @private
     */
    _generateHueCircle() {
      if (this.generated === false) {
        const ctx = this.colorPickerCanvas.getContext("2d");
        if (this.pixelRation === undefined) {
          this.pixelRatio =
            (window.devicePixelRatio || 1) /
            (ctx.webkitBackingStorePixelRatio ||
              ctx.mozBackingStorePixelRatio ||
              ctx.msBackingStorePixelRatio ||
              ctx.oBackingStorePixelRatio ||
              ctx.backingStorePixelRatio ||
              1);
        }
        ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
  
        // clear the canvas
        const w = this.colorPickerCanvas.clientWidth;
        const h = this.colorPickerCanvas.clientHeight;
        ctx.clearRect(0, 0, w, h);
  
        // draw hue circle
        let x, y, hue, sat;
        this.centerCoordinates = { x: w * 0.5, y: h * 0.5 };
        this.r = 0.49 * w;
        const angleConvert = (2 * Math.PI) / 360;
        const hfac = 1 / 360;
        const sfac = 1 / this.r;
        let rgb;
        for (hue = 0; hue < 360; hue++) {
          for (sat = 0; sat < this.r; sat++) {
            x = this.centerCoordinates.x + sat * Math.sin(angleConvert * hue);
            y = this.centerCoordinates.y + sat * Math.cos(angleConvert * hue);
            rgb = HSVToRGB(hue * hfac, sat * sfac, 1);
            ctx.fillStyle = "rgb(" + rgb.r + "," + rgb.g + "," + rgb.b + ")";
            ctx.fillRect(x - 0.5, y - 0.5, 2, 2);
          }
        }
        ctx.strokeStyle = "rgba(0,0,0,1)";
        ctx.circle(this.centerCoordinates.x, this.centerCoordinates.y, this.r);
        ctx.stroke();
  
        this.hueCircle = ctx.getImageData(0, 0, w, h);
      }
      this.generated = true;
    }
  
    /**
     * move the selector. This is called by hammer functions.
     *
     * @param {Event}  event   The event
     * @private
     */
    _moveSelector(event) {
      const rect = this.colorPickerDiv.getBoundingClientRect();
      const left = event.center.x - rect.left;
      const top = event.center.y - rect.top;
  
      const centerY = 0.5 * this.colorPickerDiv.clientHeight;
      const centerX = 0.5 * this.colorPickerDiv.clientWidth;
  
      const x = left - centerX;
      const y = top - centerY;
  
      const angle = Math.atan2(x, y);
      const radius = 0.98 * Math.min(Math.sqrt(x * x + y * y), centerX);
  
      const newTop = Math.cos(angle) * radius + centerY;
      const newLeft = Math.sin(angle) * radius + centerX;
  
      this.colorPickerSelector.style.top =
        newTop - 0.5 * this.colorPickerSelector.clientHeight + "px";
      this.colorPickerSelector.style.left =
        newLeft - 0.5 * this.colorPickerSelector.clientWidth + "px";
  
      // set color
      let h = angle / (2 * Math.PI);
      h = h < 0 ? h + 1 : h;
      const s = radius / this.r;
      const hsv = RGBToHSV(this.color.r, this.color.g, this.color.b);
      hsv.h = h;
      hsv.s = s;
      const rgba = HSVToRGB(hsv.h, hsv.s, hsv.v);
      rgba["a"] = this.color.a;
      this.color = rgba;
  
      // update previews
      this.initialColorDiv.style.backgroundColor =
        "rgba(" +
        this.initialColor.r +
        "," +
        this.initialColor.g +
        "," +
        this.initialColor.b +
        "," +
        this.initialColor.a +
        ")";
      this.newColorDiv.style.backgroundColor =
        "rgba(" +
        this.color.r +
        "," +
        this.color.g +
        "," +
        this.color.b +
        "," +
        this.color.a +
        ")";
    }
  }
  
  export default ColorPicker;
  