mirror of
https://github.com/janishutz/color-thief.git
synced 2025-11-25 05:44:24 +00:00
start migrating to TS, update eslint config
This commit is contained in:
19
.eslintrc.js
19
.eslintrc.js
@@ -1,19 +0,0 @@
|
|||||||
module.exports = {
|
|
||||||
"env": {
|
|
||||||
"browser": true,
|
|
||||||
"commonjs": true,
|
|
||||||
"es6": true,
|
|
||||||
"node": true
|
|
||||||
},
|
|
||||||
"extends": "eslint:recommended",
|
|
||||||
"globals": {
|
|
||||||
"Atomics": "readonly",
|
|
||||||
"SharedArrayBuffer": "readonly"
|
|
||||||
},
|
|
||||||
"parserOptions": {
|
|
||||||
"ecmaVersion": 2018
|
|
||||||
},
|
|
||||||
"rules": {
|
|
||||||
"one-var": ["warn", { "initialized": "never" }]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
75
eslint.config.mjs
Normal file
75
eslint.config.mjs
Normal file
@@ -0,0 +1,75 @@
|
|||||||
|
import stylisticTS from '@stylistic/eslint-plugin';
|
||||||
|
|
||||||
|
export default [
|
||||||
|
{
|
||||||
|
plugins: {
|
||||||
|
'@stylistic/ts': stylisticTS,
|
||||||
|
},
|
||||||
|
languageOptions: {
|
||||||
|
ecmaVersion: 6,
|
||||||
|
sourceType: 'module',
|
||||||
|
},
|
||||||
|
rules: {
|
||||||
|
// Error prevention
|
||||||
|
'prefer-const': 'error',
|
||||||
|
'no-async-promise-executor': 'error',
|
||||||
|
'no-cond-assign': 'error',
|
||||||
|
'no-const-assign': 'error',
|
||||||
|
'no-constant-condition': 'error',
|
||||||
|
'no-debugger': 'error',
|
||||||
|
'no-dupe-else-if': 'error',
|
||||||
|
'no-dupe-keys': 'warn',
|
||||||
|
'no-dupe-class-members': 'error',
|
||||||
|
'no-dupe-args': 'error',
|
||||||
|
'no-duplicate-case': 'error',
|
||||||
|
'no-duplicate-imports': 'error',
|
||||||
|
'no-empty-pattern': 'error',
|
||||||
|
'no-fallthrough': 'error',
|
||||||
|
'no-invalid-regexp': 'warn',
|
||||||
|
'no-loss-of-precision': 'warn',
|
||||||
|
'no-import-assign': 'error',
|
||||||
|
'no-irregular-whitespace': 'error',
|
||||||
|
'no-self-assign': 'error',
|
||||||
|
'no-undef': 'warn',
|
||||||
|
'no-unreachable': 'error',
|
||||||
|
'no-unsafe-finally': 'error',
|
||||||
|
'no-unsafe-negation': 'error',
|
||||||
|
'no-unused-private-class-members': 'warn',
|
||||||
|
'no-unused-vars': 'error',
|
||||||
|
'no-use-before-define': 'error',
|
||||||
|
|
||||||
|
// Style
|
||||||
|
'arrow-body-style': [ 'error', 'always' ],
|
||||||
|
'camelcase': 'warn',
|
||||||
|
'curly': [ 'error', 'all' ],
|
||||||
|
'eqeqeq': [ 'error', 'always' ],
|
||||||
|
'func-style': [ 'error', 'expression' ],
|
||||||
|
'no-array-constructor': 'error',
|
||||||
|
'no-else-return': 'error',
|
||||||
|
'no-empty': 'warn',
|
||||||
|
'no-empty-static-block': 'warn',
|
||||||
|
'no-eval': 'error',
|
||||||
|
'no-implicit-coercion': 'error',
|
||||||
|
'no-invalid-this': 'warn',
|
||||||
|
'no-multi-assign': 'warn',
|
||||||
|
'no-new': 'error',
|
||||||
|
'no-redeclare': 'error',
|
||||||
|
'no-script-url': 'error',
|
||||||
|
'no-shadow': 'error',
|
||||||
|
'no-shadow-restricted-names': 'error',
|
||||||
|
'no-underscore-dangle': 'warn',
|
||||||
|
'no-unused-expressions': 'warn',
|
||||||
|
'no-useless-constructor': 'warn',
|
||||||
|
'no-var': 'warn',
|
||||||
|
'prefer-arrow-callback': 'error',
|
||||||
|
'prefer-exponentiation-operator': 'warn',
|
||||||
|
'prefer-numeric-literals': 'error',
|
||||||
|
'require-await': 'warn',
|
||||||
|
|
||||||
|
// Formatting
|
||||||
|
// https://eslint.style/rules/js/array-bracket-newline
|
||||||
|
// TODO: Finish up
|
||||||
|
'@stylistic/ts/indent': [ 'error', 4 ]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
8791
package-lock.json
generated
8791
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
18
package.json
18
package.json
@@ -34,22 +34,16 @@
|
|||||||
"test": "mocha && cypress run --config video=false",
|
"test": "mocha && cypress run --config video=false",
|
||||||
"test:browser": "./node_modules/.bin/cypress run --headed --browser chrome",
|
"test:browser": "./node_modules/.bin/cypress run --headed --browser chrome",
|
||||||
"test:node": "mocha",
|
"test:node": "mocha",
|
||||||
"cypress": "./node_modules/.bin/cypress open"
|
"cypress": "./node_modules/.bin/cypress open",
|
||||||
|
"lint": "eslint ./src && prettier ./src"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@node-minify/core": "^4.0.5",
|
"@stylistic/eslint-plugin": "^2.3.0",
|
||||||
"@node-minify/uglify-es": "^4.0.5",
|
"cypress": "^13.12.0",
|
||||||
"chai": "^4.2.0",
|
"eslint": "^8.40.0"
|
||||||
"chai-as-promised": "^7.1.1",
|
|
||||||
"cypress": "^12.6.0",
|
|
||||||
"eslint": "^5.16.0",
|
|
||||||
"http-server": "^0.11.1",
|
|
||||||
"microbundle": "^0.15.0",
|
|
||||||
"mocha": "^6.2.0",
|
|
||||||
"mustache": "^3.0.1"
|
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@lokesh.dhakar/quantize": "^1.3.0",
|
"@lokesh.dhakar/quantize": "^1.3.0",
|
||||||
"get-pixels": "^3.3.2"
|
"ndarray-pixels": "^4.1.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
// TODO: Update using this pr https://github.com/lokesh/color-thief/pull/254
|
||||||
const getPixels = require('get-pixels');
|
const getPixels = require('get-pixels');
|
||||||
const quantize = require('@lokesh.dhakar/quantize');
|
const quantize = require('@lokesh.dhakar/quantize');
|
||||||
|
|
||||||
@@ -27,73 +28,81 @@ function validateOptions(options) {
|
|||||||
|
|
||||||
if (typeof colorCount === 'undefined' || !Number.isInteger(colorCount)) {
|
if (typeof colorCount === 'undefined' || !Number.isInteger(colorCount)) {
|
||||||
colorCount = 10;
|
colorCount = 10;
|
||||||
} else if (colorCount === 1 ) {
|
} else if (colorCount === 1) {
|
||||||
throw new Error('colorCount should be between 2 and 20. To get one color, call getColor() instead of getPalette()');
|
throw new Error(
|
||||||
|
'colorCount should be between 2 and 20. To get one color, call getColor() instead of getPalette()',
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
colorCount = Math.max(colorCount, 2);
|
colorCount = Math.max(colorCount, 2);
|
||||||
colorCount = Math.min(colorCount, 20);
|
colorCount = Math.min(colorCount, 20);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (typeof quality === 'undefined' || !Number.isInteger(quality) || quality < 1) {
|
if (
|
||||||
|
typeof quality === 'undefined' ||
|
||||||
|
!Number.isInteger(quality) ||
|
||||||
|
quality < 1
|
||||||
|
) {
|
||||||
quality = 10;
|
quality = 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
colorCount,
|
colorCount,
|
||||||
quality
|
quality,
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function loadImg(img) {
|
function loadImg(img) {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
getPixels(img, function(err, data) {
|
getPixels(img, function (err, data) {
|
||||||
if(err) {
|
if (err) {
|
||||||
reject(err)
|
reject(err);
|
||||||
} else {
|
} else {
|
||||||
resolve(data);
|
resolve(data);
|
||||||
}
|
}
|
||||||
})
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function getColor(img, quality) {
|
function getColor(img, quality) {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
getPalette(img, 5, quality)
|
getPalette(img, 5, quality)
|
||||||
.then(palette => {
|
.then((palette) => {
|
||||||
resolve(palette[0]);
|
resolve(palette[0]);
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch((err) => {
|
||||||
reject(err);
|
reject(err);
|
||||||
})
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function getPalette(img, colorCount = 10, quality = 10) {
|
function getPalette(img, colorCount = 10, quality = 10) {
|
||||||
const options = validateOptions({
|
const options = validateOptions({
|
||||||
colorCount,
|
colorCount,
|
||||||
quality
|
quality,
|
||||||
});
|
});
|
||||||
|
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
loadImg(img)
|
loadImg(img)
|
||||||
.then(imgData => {
|
.then((imgData) => {
|
||||||
const pixelCount = imgData.shape[0] * imgData.shape[1];
|
const pixelCount = imgData.shape[0] * imgData.shape[1];
|
||||||
const pixelArray = createPixelArray(imgData.data, pixelCount, options.quality);
|
const pixelArray = createPixelArray(
|
||||||
|
imgData.data,
|
||||||
|
pixelCount,
|
||||||
|
options.quality,
|
||||||
|
);
|
||||||
|
|
||||||
const cmap = quantize(pixelArray, options.colorCount);
|
const cmap = quantize(pixelArray, options.colorCount);
|
||||||
const palette = cmap? cmap.palette() : null;
|
const palette = cmap ? cmap.palette() : null;
|
||||||
|
|
||||||
resolve(palette);
|
resolve(palette);
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch((err) => {
|
||||||
reject(err);
|
reject(err);
|
||||||
})
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
getColor,
|
getColor,
|
||||||
getPalette
|
getPalette,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
0
src/color-thief-node.ts
Normal file
0
src/color-thief-node.ts
Normal file
@@ -20,7 +20,6 @@ import core from './core.js';
|
|||||||
* @license
|
* @license
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
CanvasImage Class
|
CanvasImage Class
|
||||||
Class that wraps the html image element and canvas.
|
Class that wraps the html image element and canvas.
|
||||||
@@ -55,13 +54,12 @@ var ColorThief = function () {};
|
|||||||
* most dominant color.
|
* most dominant color.
|
||||||
*
|
*
|
||||||
* */
|
* */
|
||||||
ColorThief.prototype.getColor = function(sourceImage, quality = 10) {
|
ColorThief.prototype.getColor = function (sourceImage, quality = 10) {
|
||||||
const palette = this.getPalette(sourceImage, 5, quality);
|
const palette = this.getPalette(sourceImage, 5, quality);
|
||||||
const dominantColor = palette[0];
|
const dominantColor = palette[0];
|
||||||
return dominantColor;
|
return dominantColor;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* getPalette(sourceImage[, colorCount, quality])
|
* getPalette(sourceImage[, colorCount, quality])
|
||||||
* returns array[ {r: num, g: num, b: num}, {r: num, g: num, b: num}, ...]
|
* returns array[ {r: num, g: num, b: num}, {r: num, g: num, b: num}, ...]
|
||||||
@@ -77,10 +75,10 @@ ColorThief.prototype.getColor = function(sourceImage, quality = 10) {
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
ColorThief.prototype.getPalette = function(sourceImage, colorCount, quality) {
|
ColorThief.prototype.getPalette = function (sourceImage, colorCount, quality) {
|
||||||
const options = core.validateOptions({
|
const options = core.validateOptions({
|
||||||
colorCount,
|
colorCount,
|
||||||
quality
|
quality,
|
||||||
});
|
});
|
||||||
|
|
||||||
// Create custom CanvasImage object
|
// Create custom CanvasImage object
|
||||||
@@ -88,53 +86,56 @@ ColorThief.prototype.getPalette = function(sourceImage, colorCount, quality) {
|
|||||||
const imageData = image.getImageData();
|
const imageData = image.getImageData();
|
||||||
const pixelCount = image.width * image.height;
|
const pixelCount = image.width * image.height;
|
||||||
|
|
||||||
const pixelArray = core.createPixelArray(imageData.data, pixelCount, options.quality);
|
const pixelArray = core.createPixelArray(
|
||||||
|
imageData.data,
|
||||||
|
pixelCount,
|
||||||
|
options.quality,
|
||||||
|
);
|
||||||
|
|
||||||
// Send array to quantize function which clusters values
|
// Send array to quantize function which clusters values
|
||||||
// using median cut algorithm
|
// using median cut algorithm
|
||||||
const cmap = quantize(pixelArray, options.colorCount);
|
const cmap = quantize(pixelArray, options.colorCount);
|
||||||
const palette = cmap? cmap.palette() : null;
|
const palette = cmap ? cmap.palette() : null;
|
||||||
|
|
||||||
return palette;
|
return palette;
|
||||||
};
|
};
|
||||||
|
|
||||||
ColorThief.prototype.getColorFromUrl = function(imageUrl, callback, quality) {
|
ColorThief.prototype.getColorFromUrl = function (imageUrl, callback, quality) {
|
||||||
const sourceImage = document.createElement("img");
|
const sourceImage = document.createElement('img');
|
||||||
|
|
||||||
sourceImage.addEventListener('load' , () => {
|
sourceImage.addEventListener('load', () => {
|
||||||
const palette = this.getPalette(sourceImage, 5, quality);
|
const palette = this.getPalette(sourceImage, 5, quality);
|
||||||
const dominantColor = palette[0];
|
const dominantColor = palette[0];
|
||||||
callback(dominantColor, imageUrl);
|
callback(dominantColor, imageUrl);
|
||||||
});
|
});
|
||||||
sourceImage.src = imageUrl
|
sourceImage.src = imageUrl;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
ColorThief.prototype.getImageData = function (imageUrl, callback) {
|
||||||
ColorThief.prototype.getImageData = function(imageUrl, callback) {
|
|
||||||
let xhr = new XMLHttpRequest();
|
let xhr = new XMLHttpRequest();
|
||||||
xhr.open('GET', imageUrl, true);
|
xhr.open('GET', imageUrl, true);
|
||||||
xhr.responseType = 'arraybuffer';
|
xhr.responseType = 'arraybuffer';
|
||||||
xhr.onload = function() {
|
xhr.onload = function () {
|
||||||
if (this.status == 200) {
|
if (this.status == 200) {
|
||||||
let uInt8Array = new Uint8Array(this.response);
|
let uInt8Array = new Uint8Array(this.response);
|
||||||
i = uInt8Array.length;
|
i = uInt8Array.length;
|
||||||
let binaryString = new Array(i);
|
let binaryString = new Array(i);
|
||||||
for (let i = 0; i < uInt8Array.length; i++){
|
for (let i = 0; i < uInt8Array.length; i++) {
|
||||||
binaryString[i] = String.fromCharCode(uInt8Array[i]);
|
binaryString[i] = String.fromCharCode(uInt8Array[i]);
|
||||||
}
|
}
|
||||||
let data = binaryString.join('');
|
let data = binaryString.join('');
|
||||||
let base64 = window.btoa(data);
|
let base64 = window.btoa(data);
|
||||||
callback ('data:image/png;base64,' + base64);
|
callback('data:image/png;base64,' + base64);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
};
|
||||||
xhr.send();
|
xhr.send();
|
||||||
};
|
};
|
||||||
|
|
||||||
ColorThief.prototype.getColorAsync = function(imageUrl, callback, quality) {
|
ColorThief.prototype.getColorAsync = function (imageUrl, callback, quality) {
|
||||||
const thief = this;
|
const thief = this;
|
||||||
this.getImageData(imageUrl, function(imageData){
|
this.getImageData(imageUrl, function (imageData) {
|
||||||
const sourceImage = document.createElement("img");
|
const sourceImage = document.createElement('img');
|
||||||
sourceImage.addEventListener('load' , function(){
|
sourceImage.addEventListener('load', function () {
|
||||||
const palette = thief.getPalette(sourceImage, 5, quality);
|
const palette = thief.getPalette(sourceImage, 5, quality);
|
||||||
const dominantColor = palette[0];
|
const dominantColor = palette[0];
|
||||||
callback(dominantColor, this);
|
callback(dominantColor, this);
|
||||||
@@ -143,5 +144,4 @@ ColorThief.prototype.getColorAsync = function(imageUrl, callback, quality) {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
export default ColorThief;
|
export default ColorThief;
|
||||||
|
|||||||
180
src/color-thief.ts
Normal file
180
src/color-thief.ts
Normal file
@@ -0,0 +1,180 @@
|
|||||||
|
import quantize from '../node_modules/@lokesh.dhakar/quantize/dist/index.mjs';
|
||||||
|
import core from './core.js';
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Color Thief v2.4.0
|
||||||
|
* by Lokesh Dhakar - http://www.lokeshdhakar.com
|
||||||
|
*
|
||||||
|
* Thanks
|
||||||
|
* ------
|
||||||
|
* Nick Rabinowitz - For creating quantize.js.
|
||||||
|
* John Schulz - For clean up and optimization. @JFSIII
|
||||||
|
* Nathan Spady - For adding drag and drop support to the demo page.
|
||||||
|
*
|
||||||
|
* License
|
||||||
|
* -------
|
||||||
|
* Copyright Lokesh Dhakar
|
||||||
|
* Released under the MIT license
|
||||||
|
* https://raw.githubusercontent.com/lokesh/color-thief/master/LICENSE
|
||||||
|
*
|
||||||
|
* @license
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
CanvasImage Class
|
||||||
|
Class that wraps the html image element and canvas.
|
||||||
|
It also simplifies some of the canvas context manipulation
|
||||||
|
with a set of helper functions.
|
||||||
|
*/
|
||||||
|
|
||||||
|
const CanvasImage = function (image: HTMLImageElement) {
|
||||||
|
this.canvas = document.createElement('canvas');
|
||||||
|
this.context = this.canvas.getContext('2d');
|
||||||
|
this.width = this.canvas.width = image.naturalWidth;
|
||||||
|
this.height = this.canvas.height = image.naturalHeight;
|
||||||
|
this.context.drawImage(image, 0, 0, this.width, this.height);
|
||||||
|
};
|
||||||
|
|
||||||
|
CanvasImage.prototype.getImageData = function () {
|
||||||
|
return this.context.getImageData(0, 0, this.width, this.height);
|
||||||
|
};
|
||||||
|
|
||||||
|
interface ColorThiefResult {
|
||||||
|
r: number;
|
||||||
|
g: number;
|
||||||
|
b: number;
|
||||||
|
}
|
||||||
|
|
||||||
|
class ColorThief {
|
||||||
|
/**
|
||||||
|
* Use the median cut algorithm provided by quantize.js to cluster similar
|
||||||
|
* colors and return the base color from the largest cluster.
|
||||||
|
* @param {HTMLImageElement} sourceImage:HTMLImageElement
|
||||||
|
* @param {number} quality Quality is an optional argument. It needs to be an integer. 1 is the highest quality settings.
|
||||||
|
* 10 is the default. There is a trade-off between quality and speed. The bigger the number, the
|
||||||
|
* faster a color will be returned but the greater the likelihood that it will not be the visually
|
||||||
|
* most dominant color.
|
||||||
|
* @returns {ColorThiefResult} returns {r: num, g: num, b: num}
|
||||||
|
*/
|
||||||
|
getColor(
|
||||||
|
sourceImage: HTMLImageElement,
|
||||||
|
quality: number = 10,
|
||||||
|
): ColorThiefResult {
|
||||||
|
const palette = this.getPalette(sourceImage, 5, quality);
|
||||||
|
return palette[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Use the median cut algorithm provided by quantize.js to cluster similar colors.
|
||||||
|
* @param {HTMLImageElement} sourceImage The image you want to have processed, as an HTMLImageElement
|
||||||
|
* @param {number?} colorCount colorCount determines the size of the palette; the number of colors returned. If not set, it
|
||||||
|
* defaults to 10.
|
||||||
|
* @param {number?} quality quality is an optional argument. It needs to be an integer. 1 is the highest quality settings.
|
||||||
|
* 10 is the default. There is a trade-off between quality and speed. The bigger the number, the
|
||||||
|
* faster the palette generation but the greater the likelihood that colors will be missed.
|
||||||
|
* @returns {ColorThiefResult[]} returns array[ {r: num, g: num, b: num}, {r: num, g: num, b: num}, ...]
|
||||||
|
*/
|
||||||
|
getPalette(
|
||||||
|
sourceImage: HTMLImageElement,
|
||||||
|
colorCount?: number,
|
||||||
|
quality: number = 10,
|
||||||
|
): ColorThiefResult[] {
|
||||||
|
const options = core.validateOptions({
|
||||||
|
colorCount,
|
||||||
|
quality,
|
||||||
|
});
|
||||||
|
|
||||||
|
// Create custom CanvasImage object
|
||||||
|
const image = new CanvasImage(sourceImage);
|
||||||
|
const imageData = image.getImageData();
|
||||||
|
const pixelCount = image.width * image.height;
|
||||||
|
|
||||||
|
const pixelArray = core.createPixelArray(
|
||||||
|
imageData.data,
|
||||||
|
pixelCount,
|
||||||
|
options.quality,
|
||||||
|
);
|
||||||
|
|
||||||
|
// Send array to quantize function which clusters values
|
||||||
|
// using median cut algorithm
|
||||||
|
const cmap = quantize(pixelArray, options.colorCount);
|
||||||
|
const palette = cmap ? cmap.palette() : null;
|
||||||
|
|
||||||
|
return palette;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Description
|
||||||
|
* @param {any} imageUrl
|
||||||
|
* @param {any} callback
|
||||||
|
* @param {any} quality
|
||||||
|
* @returns {any}
|
||||||
|
*/
|
||||||
|
getColorFromUrl(imageUrl, callback, quality) {
|
||||||
|
const sourceImage = document.createElement('img');
|
||||||
|
|
||||||
|
sourceImage.addEventListener('load', () => {
|
||||||
|
const palette = this.getPalette(sourceImage, 5, quality);
|
||||||
|
const dominantColor = palette[0];
|
||||||
|
callback(dominantColor, imageUrl);
|
||||||
|
});
|
||||||
|
sourceImage.src = imageUrl;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Description
|
||||||
|
* @param {string} imageUrl
|
||||||
|
* @param {string} callback
|
||||||
|
* @returns {void}
|
||||||
|
*/
|
||||||
|
getImageData(imageUrl: string, callback) {
|
||||||
|
let xhr = new XMLHttpRequest();
|
||||||
|
xhr.open('GET', imageUrl, true);
|
||||||
|
xhr.responseType = 'arraybuffer';
|
||||||
|
|
||||||
|
fetch(imageUrl).then((res) => {
|
||||||
|
if (res.status === 200) {
|
||||||
|
res.arrayBuffer().then((response) => {
|
||||||
|
const uInt8Array = new Uint8Array(response);
|
||||||
|
let binaryString = new Array(uInt8Array.length);
|
||||||
|
for (let i = 0; i < uInt8Array.length; i++) {
|
||||||
|
binaryString[i] = String.fromCharCode(uInt8Array[i]);
|
||||||
|
}
|
||||||
|
let data = binaryString.join('');
|
||||||
|
let base64 = window.btoa(data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
xhr.onload = function () {
|
||||||
|
if (this.status == 200) {
|
||||||
|
let uInt8Array = new Uint8Array(this.response);
|
||||||
|
|
||||||
|
callback('data:image/png;base64,' + base64);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
xhr.send();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Description
|
||||||
|
* @param {any} imageUrl
|
||||||
|
* @param {any} callback
|
||||||
|
* @param {any} quality
|
||||||
|
* @returns {any}
|
||||||
|
*/
|
||||||
|
getColorAsync = function (imageUrl, callback, quality) {
|
||||||
|
const thief = this;
|
||||||
|
this.getImageData(imageUrl, function (imageData) {
|
||||||
|
const sourceImage = document.createElement('img');
|
||||||
|
sourceImage.addEventListener('load', function () {
|
||||||
|
const palette = thief.getPalette(sourceImage, 5, quality);
|
||||||
|
const dominantColor = palette[0];
|
||||||
|
callback(dominantColor, this);
|
||||||
|
});
|
||||||
|
sourceImage.src = imageData;
|
||||||
|
});
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export default ColorThief;
|
||||||
18
src/core.js
18
src/core.js
@@ -24,24 +24,30 @@ function validateOptions(options) {
|
|||||||
|
|
||||||
if (typeof colorCount === 'undefined' || !Number.isInteger(colorCount)) {
|
if (typeof colorCount === 'undefined' || !Number.isInteger(colorCount)) {
|
||||||
colorCount = 10;
|
colorCount = 10;
|
||||||
} else if (colorCount === 1 ) {
|
} else if (colorCount === 1) {
|
||||||
throw new Error('colorCount should be between 2 and 20. To get one color, call getColor() instead of getPalette()');
|
throw new Error(
|
||||||
|
'colorCount should be between 2 and 20. To get one color, call getColor() instead of getPalette()',
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
colorCount = Math.max(colorCount, 2);
|
colorCount = Math.max(colorCount, 2);
|
||||||
colorCount = Math.min(colorCount, 20);
|
colorCount = Math.min(colorCount, 20);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (typeof quality === 'undefined' || !Number.isInteger(quality) || quality < 1) {
|
if (
|
||||||
|
typeof quality === 'undefined' ||
|
||||||
|
!Number.isInteger(quality) ||
|
||||||
|
quality < 1
|
||||||
|
) {
|
||||||
quality = 10;
|
quality = 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
colorCount,
|
colorCount,
|
||||||
quality
|
quality,
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
createPixelArray,
|
createPixelArray,
|
||||||
validateOptions
|
validateOptions,
|
||||||
};
|
};
|
||||||
|
|||||||
0
src/core.ts
Normal file
0
src/core.ts
Normal file
Reference in New Issue
Block a user