Mutualize HTML generation for drawing tools and transform

This commit is contained in:
jdescottes
2014-11-21 01:15:55 +01:00
parent c8dae1cb79
commit 0f49c884f2
30 changed files with 334 additions and 231 deletions

View File

@@ -0,0 +1,145 @@
(function () {
var ns = $.namespace('pskl.widgets');
var DEFAULT_COLOR = '#000000';
ns.ColorsList = function (container) {
this.selectedIndex = -1;
this.palette = new pskl.model.Palette('tmp', 'tmp', []);
this.container = container;
this.colorsList = this.container.querySelector('.colors-list');
this.colorPreviewEl = this.container.querySelector('.color-preview');
$(container).sortable({
placeholder: 'colors-list-drop-proxy',
update: this.onColorDrop_.bind(this),
items: '.create-palette-color'
});
this.colorsList.addEventListener('click', this.onColorContainerClick_.bind(this));
var colorPickerContainer = container.querySelector('.color-picker-container');
this.hslRgbColorPicker = new pskl.widgets.HslRgbColorPicker(colorPickerContainer, this.onColorUpdated_.bind(this));
this.hslRgbColorPicker.init();
};
ns.ColorsList.prototype.setColors = function (colors) {
if (colors.length === 0) {
colors.push(DEFAULT_COLOR);
}
this.palette.setColors(colors);
this.selectColor_(0);
this.refresh_();
};
ns.ColorsList.prototype.getColors = function () {
return this.palette.getColors();
};
ns.ColorsList.prototype.destroy = function () {
this.hslRgbColorPicker.destroy();
this.container = null;
this.colorsList = null;
this.colorPreviewEl = null;
};
/**
* Lightweight refresh only changing the color of one element of the palette color list
*/
ns.ColorsList.prototype.refreshColorElement_ = function (index) {
var color = this.palette.get(this.selectedIndex);
var element = document.querySelector('[data-palette-index="'+index+'"]');
if (element) {
element.style.background = color;
element.classList.toggle('light-color', this.isLight_(color));
}
};
ns.ColorsList.prototype.onColorContainerClick_ = function (evt) {
var target = evt.target;
if (target.classList.contains('create-palette-color')) {
this.onPaletteColorClick_(evt, target);
} else if (target.classList.contains('create-palette-new-color')) {
this.onNewColorClick_(evt, target);
} else if (target.classList.contains('create-palette-remove-color')) {
this.onRemoveColorClick_(evt, target);
}
this.refresh_();
};
ns.ColorsList.prototype.onColorUpdated_ = function (color) {
var rgbColor = color.toRgbString();
this.colorPreviewEl.style.background = rgbColor;
if (this.palette) {
this.palette.set(this.selectedIndex, rgbColor);
this.refreshColorElement_(this.selectedIndex);
}
};
ns.ColorsList.prototype.onPaletteColorClick_ = function (evt, target) {
var index = parseInt(target.dataset.paletteIndex,10);
this.selectColor_(index);
};
ns.ColorsList.prototype.onRemoveColorClick_ = function (evt, target) {
var colorElement = target.parentNode;
var index = parseInt(colorElement.dataset.paletteIndex,10);
this.removeColor_(index);
};
ns.ColorsList.prototype.onNewColorClick_ = function (evt, target) {
var newColor = this.palette.get(this.selectedIndex) || '#000000';
this.palette.add(newColor);
this.selectColor_(this.palette.size()-1);
};
ns.ColorsList.prototype.refresh_ = function () {
var html = "";
var tpl = pskl.utils.Template.get('create-palette-color-template');
var colors = this.palette.getColors();
colors.forEach(function (color, index) {
var isSelected = (index === this.selectedIndex);
html += pskl.utils.Template.replace(tpl, {
'color':color, index:index,
':selected':isSelected,
':light-color':this.isLight_(color)
});
}.bind(this));
html += '<li class="create-palette-new-color">+</li>';
this.colorsList.innerHTML = html;
};
ns.ColorsList.prototype.selectColor_ = function (index) {
this.selectedIndex = index;
this.hslRgbColorPicker.setColor(this.palette.get(index));
};
ns.ColorsList.prototype.removeColor_ = function (index) {
this.palette.removeAt(index);
this.refresh_();
};
ns.ColorsList.prototype.isLight_ = function (color) {
var rgb = window.tinycolor(color).toRgb();
return rgb.r+rgb.b+rgb.g > 128*3;
};
ns.ColorsList.prototype.onColorDrop_ = function (evt, drop) {
var colorElement = drop.item.get(0);
var oldIndex = parseInt(colorElement.dataset.paletteIndex, 10);
var newIndex = $('.create-palette-color').index(drop.item);
this.palette.move(oldIndex, newIndex);
this.selectedIndex = newIndex;
this.refresh_();
};
})();

View File

@@ -0,0 +1,194 @@
(function () {
var ns = $.namespace('pskl.widgets');
ns.HslRgbColorPicker = function (container, colorUpdatedCallback) {
this.container = container;
this.colorUpdatedCallback = colorUpdatedCallback;
this.lastInputTimestamp_ = 0;
};
ns.HslRgbColorPicker.prototype.init = function () {
var isChromeOrFirefox = pskl.utils.UserAgent.isChrome || pskl.utils.UserAgent.isFirefox;
var changeEvent = isChromeOrFirefox ? 'input' : 'change';
this.container.addEventListener(changeEvent, this.onPickerChange_.bind(this));
this.container.addEventListener('keydown', this.onKeydown_.bind(this));
this.spectrumEl = this.container.querySelector('.color-picker-spectrum');
$(this.spectrumEl).spectrum({
flat: true,
showInput: true,
showButtons: false,
move : this.setColor.bind(this),
change : this.setColor.bind(this),
preferredFormat: 'hex'
});
this.setColor("#000000");
};
ns.HslRgbColorPicker.prototype.destroy = function () {
this.container = null;
this.spectrumEl = null;
};
ns.HslRgbColorPicker.prototype.onPickerChange_ = function (evt) {
var target = evt.target;
var model = target.dataset.model;
var dimension = target.dataset.dimension;
var value = parseInt(target.value, 10);
if (dimension === 'v' || dimension === 's') {
value = value/100;
}
var color;
if (model === 'rgb') {
color = this.tinyColor.toRgb();
} else if (model === 'hsv') {
color = this.hsvColor;
}
if (isNaN(value)) {
value = color[dimension];
} else {
color[dimension] = value;
}
this.setColor(color);
};
ns.HslRgbColorPicker.prototype.onKeydown_ = function (evt) {
var target = evt.target;
if (target.getAttribute('type').toLowerCase() === 'text') {
var value = parseInt(target.value, 10);
var dimension = target.dataset.dimension;
var key = pskl.service.keyboard.KeycodeTranslator.toChar(evt.keyCode);
if (key === 'up') {
value = value + 1;
} else if (key === 'down') {
value = value - 1;
}
value = this.normalizeDimension_(value, dimension);
target.value = value;
this.onPickerChange_(evt);
}
};
ns.HslRgbColorPicker.prototype.setColor = function (inputColor) {
if (!this.unplugged) {
this.unplugged = true;
this.hsvColor = this.toHsvColor_(inputColor);
this.tinyColor = this.toTinyColor_(inputColor);
this.updateInputs();
$(".color-picker-spectrum").spectrum("set", this.tinyColor);
this.colorUpdatedCallback(this.tinyColor);
this.unplugged = false;
}
};
ns.HslRgbColorPicker.prototype.updateInputs = function () {
var inputs = this.container.querySelectorAll('input');
var rgb = this.tinyColor.toRgb();
for (var i = 0 ; i < inputs.length ; i++) {
var input = inputs[i];
var dimension = input.dataset.dimension;
var model = input.dataset.model;
if (model === 'rgb') {
input.value = rgb[dimension];
} else if (model === 'hsv') {
var value = this.hsvColor[dimension];
if (dimension === 'v' || dimension === 's') {
value = 100 * value;
}
input.value = Math.round(value);
}
if (input.getAttribute('type') === 'range') {
this.updateSliderBackground(input);
}
}
};
ns.HslRgbColorPicker.prototype.updateSliderBackground = function (slider) {
var dimension = slider.dataset.dimension;
var model = slider.dataset.model;
var start, end;
var isHueSlider = dimension === 'h';
if (!isHueSlider) {
var colors = this.getSliderBackgroundColors_(model, dimension);
slider.style.backgroundImage = "linear-gradient(to right, " + colors.start + " 0, " + colors.end + " 100%)";
}
};
ns.HslRgbColorPicker.prototype.getSliderBackgroundColors_ = function (model, dimension) {
var start, end;
if (model === 'hsv') {
start = JSON.parse(JSON.stringify(this.hsvColor));
start[dimension] = 0;
end = JSON.parse(JSON.stringify(this.hsvColor));
end[dimension] = 1;
} else {
start = this.tinyColor.toRgb();
start[dimension] = 0;
end = this.tinyColor.toRgb();
end[dimension] = 255;
}
return {
start : window.tinycolor(start).toRgbString(),
end : window.tinycolor(end).toRgbString()
};
};
ns.HslRgbColorPicker.prototype.toTinyColor_ = function (color) {
if (typeof color == "object" && color.hasOwnProperty("_tc_id")) {
return color;
} else {
return window.tinycolor(JSON.parse(JSON.stringify(color)));
}
};
ns.HslRgbColorPicker.prototype.toHsvColor_ = function (color) {
var isHsvColor = ['h','s','v'].every(color.hasOwnProperty.bind(color));
if (isHsvColor) {
return {
h : Math.max(0, Math.min(359, color.h)),
s : Math.max(0, Math.min(1, color.s)),
v : Math.max(0, Math.min(1, color.v))
};
} else {
return this.toTinyColor_(color).toHsv();
}
};
ns.HslRgbColorPicker.prototype.normalizeDimension_ = function (value, dimension) {
var ranges = {
'h' : [0, 359],
's' : [0, 100],
'v' : [0, 100],
'r' : [0, 255],
'g' : [0, 255],
'b' : [0, 255]
};
var range = ranges[dimension];
return Math.max(range[0], Math.min(range[1], value));
} ;
})();