mirror of
https://github.com/aseprite/aseprite.git
synced 2025-03-29 19:20:09 +00:00
Show indicator with old/new colors in ColorPopup (fix #1696)
This commit is contained in:
parent
e6da079e54
commit
5a91325750
@ -518,6 +518,7 @@
|
||||
<border part="editor_selected" state="focus" />
|
||||
</style>
|
||||
<style id="top_shade_view" extends="editor_view" />
|
||||
<style id="normal_shade_view" extends="view" />
|
||||
<style id="menu_shade_view" extends="view">
|
||||
<background color="menuitem_hot_face" state="mouse" />
|
||||
</style>
|
||||
|
@ -1,5 +1,5 @@
|
||||
// Aseprite
|
||||
// Copyright (C) 2001-2017 David Capello
|
||||
// Copyright (C) 2001-2018 David Capello
|
||||
//
|
||||
// This program is distributed under the terms of
|
||||
// the End-User License Agreement for Aseprite.
|
||||
@ -173,6 +173,11 @@ Color Color::fromString(const std::string& str)
|
||||
return color;
|
||||
}
|
||||
|
||||
Color Color::toRgb() const
|
||||
{
|
||||
return Color::fromRgb(getRed(), getGreen(), getBlue(), getAlpha());
|
||||
}
|
||||
|
||||
std::string Color::toString() const
|
||||
{
|
||||
std::stringstream result;
|
||||
|
@ -1,5 +1,5 @@
|
||||
// Aseprite
|
||||
// Copyright (C) 2001-2017 David Capello
|
||||
// Copyright (C) 2001-2018 David Capello
|
||||
//
|
||||
// This program is distributed under the terms of
|
||||
// the End-User License Agreement for Aseprite.
|
||||
@ -52,6 +52,7 @@ namespace app {
|
||||
static Color fromImageGetPixel(Image* image, int x, int y);
|
||||
static Color fromString(const std::string& str);
|
||||
|
||||
Color toRgb() const;
|
||||
std::string toString() const;
|
||||
std::string toHumanReadableString(PixelFormat format, HumanReadableString type) const;
|
||||
|
||||
|
@ -187,8 +187,10 @@ ColorPopup::ColorPopup(const ColorButtonOptions& options)
|
||||
new PaletteView(false, PaletteView::SelectOneColor, this, 7*guiscale()):
|
||||
nullptr)
|
||||
, m_simpleColors(nullptr)
|
||||
, m_oldAndNew(Shade(2), ColorShades::ClickEntries)
|
||||
, m_maskLabel("Transparent Color Selected")
|
||||
, m_canPin(options.canPinSelector)
|
||||
, m_insideChange(false)
|
||||
, m_disableHexUpdate(false)
|
||||
{
|
||||
if (options.showSimpleColors) {
|
||||
@ -226,6 +228,7 @@ ColorPopup::ColorPopup(const ColorButtonOptions& options)
|
||||
m_topBox.addChild(&m_colorType);
|
||||
m_topBox.addChild(new Separator("", VERTICAL));
|
||||
m_topBox.addChild(&m_hexColorEntry);
|
||||
m_topBox.addChild(&m_oldAndNew);
|
||||
|
||||
// TODO fix this hack for close button in popup window
|
||||
// Move close button (decorative widget) inside the m_topBox
|
||||
@ -261,6 +264,7 @@ ColorPopup::ColorPopup(const ColorButtonOptions& options)
|
||||
|
||||
m_sliders.ColorChange.connect(&ColorPopup::onColorSlidersChange, this);
|
||||
m_hexColorEntry.ColorChange.connect(&ColorPopup::onColorHexEntryChange, this);
|
||||
m_oldAndNew.Click.connect(&ColorPopup::onSelectOldColor, this);
|
||||
|
||||
// Set RGB just for the sizeHint(), and then deselect the color type
|
||||
// (the first setColor() call will setup it correctly.)
|
||||
@ -311,6 +315,14 @@ void ColorPopup::setColor(const app::Color& color,
|
||||
|
||||
if (options == ChangeType)
|
||||
selectColorType(m_color.getType());
|
||||
|
||||
// Set the new color
|
||||
Shade shade = m_oldAndNew.getShade();
|
||||
shade.resize(2);
|
||||
shade[1] = (color.getType() == app::Color::IndexType ? color.toRgb(): color);
|
||||
if (!m_insideChange)
|
||||
shade[0] = shade[1];
|
||||
m_oldAndNew.setShade(shade);
|
||||
}
|
||||
|
||||
app::Color ColorPopup::getColor() const
|
||||
@ -370,17 +382,26 @@ void ColorPopup::onMakeFixed()
|
||||
|
||||
void ColorPopup::onPaletteViewIndexChange(int index, ui::MouseButtons buttons)
|
||||
{
|
||||
base::ScopedValue<bool> restore(m_insideChange, true,
|
||||
m_insideChange);
|
||||
|
||||
setColorWithSignal(app::Color::fromIndex(index), ChangeType);
|
||||
}
|
||||
|
||||
void ColorPopup::onColorSlidersChange(ColorSlidersChangeEvent& ev)
|
||||
{
|
||||
base::ScopedValue<bool> restore(m_insideChange, true,
|
||||
m_insideChange);
|
||||
|
||||
setColorWithSignal(ev.color(), DontChangeType);
|
||||
findBestfitIndex(ev.color());
|
||||
}
|
||||
|
||||
void ColorPopup::onColorHexEntryChange(const app::Color& color)
|
||||
{
|
||||
base::ScopedValue<bool> restore(m_insideChange, true,
|
||||
m_insideChange);
|
||||
|
||||
// Disable updating the hex entry so we don't override what the user
|
||||
// is writting in the text field.
|
||||
m_disableHexUpdate = true;
|
||||
@ -396,6 +417,16 @@ void ColorPopup::onColorHexEntryChange(const app::Color& color)
|
||||
m_disableHexUpdate = false;
|
||||
}
|
||||
|
||||
void ColorPopup::onSelectOldColor()
|
||||
{
|
||||
Shade shade = m_oldAndNew.getShade();
|
||||
int hot = m_oldAndNew.getHotEntry();
|
||||
if (hot >= 0 &&
|
||||
hot < int(shade.size())) {
|
||||
setColorWithSignal(shade[hot], DontChangeType);
|
||||
}
|
||||
}
|
||||
|
||||
void ColorPopup::onSimpleColorClick()
|
||||
{
|
||||
m_colorType.deselectItems();
|
||||
@ -425,6 +456,9 @@ void ColorPopup::onSimpleColorClick()
|
||||
|
||||
void ColorPopup::onColorTypeClick()
|
||||
{
|
||||
base::ScopedValue<bool> restore(m_insideChange, true,
|
||||
m_insideChange);
|
||||
|
||||
if (m_simpleColors)
|
||||
m_simpleColors->deselect();
|
||||
|
||||
@ -466,6 +500,9 @@ void ColorPopup::onColorTypeClick()
|
||||
|
||||
void ColorPopup::onPaletteChange()
|
||||
{
|
||||
base::ScopedValue<bool> restore(m_insideChange, inEditMode(),
|
||||
m_insideChange);
|
||||
|
||||
setColor(getColor(), DontChangeType);
|
||||
invalidate();
|
||||
|
||||
@ -495,8 +532,14 @@ void ColorPopup::findBestfitIndex(const app::Color& color)
|
||||
void ColorPopup::setColorWithSignal(const app::Color& color,
|
||||
const SetColorOptions options)
|
||||
{
|
||||
Shade shade = m_oldAndNew.getShade();
|
||||
|
||||
setColor(color, options);
|
||||
|
||||
shade.resize(2);
|
||||
shade[1] = color;
|
||||
m_oldAndNew.setShade(shade);
|
||||
|
||||
// Fire ColorChange signal
|
||||
ColorChange(color);
|
||||
}
|
||||
|
@ -9,8 +9,10 @@
|
||||
#pragma once
|
||||
|
||||
#include "app/color.h"
|
||||
#include "app/shade.h"
|
||||
#include "app/ui/button_set.h"
|
||||
#include "app/ui/color_button_options.h"
|
||||
#include "app/ui/color_shades.h"
|
||||
#include "app/ui/color_sliders.h"
|
||||
#include "app/ui/hex_color_entry.h"
|
||||
#include "app/ui/palette_view.h"
|
||||
@ -50,6 +52,7 @@ namespace app {
|
||||
void onMakeFixed() override;
|
||||
void onColorSlidersChange(ColorSlidersChangeEvent& ev);
|
||||
void onColorHexEntryChange(const app::Color& color);
|
||||
void onSelectOldColor();
|
||||
void onSimpleColorClick();
|
||||
void onColorTypeClick();
|
||||
void onPaletteChange();
|
||||
@ -83,10 +86,12 @@ namespace app {
|
||||
SimpleColors* m_simpleColors;
|
||||
CustomButtonSet m_colorType;
|
||||
HexColorEntry m_hexColorEntry;
|
||||
ColorShades m_oldAndNew;
|
||||
ColorSliders m_sliders;
|
||||
ui::Label m_maskLabel;
|
||||
obs::scoped_connection m_onPaletteChangeConn;
|
||||
bool m_canPin;
|
||||
bool m_insideChange;
|
||||
|
||||
// This variable is used to avoid updating the m_hexColorEntry text
|
||||
// when the color change is generated from a
|
||||
|
@ -81,7 +81,7 @@ int ColorShades::size() const
|
||||
for (const auto& color : m_shade) {
|
||||
if ((color.getIndex() >= 0 &&
|
||||
color.getIndex() < get_current_palette()->size()) ||
|
||||
(m_click == Select)) {
|
||||
(m_click == ClickWholeShade)) {
|
||||
++colors;
|
||||
}
|
||||
}
|
||||
@ -94,9 +94,11 @@ Shade ColorShades::getShade() const
|
||||
for (const auto& color : m_shade) {
|
||||
if ((color.getIndex() >= 0 &&
|
||||
color.getIndex() < get_current_palette()->size()) ||
|
||||
(m_click == Select)) {
|
||||
(m_click == ClickWholeShade)) {
|
||||
colors.push_back(color);
|
||||
}
|
||||
else if (m_click == ClickEntries)
|
||||
colors.push_back(color);
|
||||
}
|
||||
return colors;
|
||||
}
|
||||
@ -123,7 +125,18 @@ void ColorShades::updateShadeFromColorBarPicks()
|
||||
void ColorShades::onInitTheme(ui::InitThemeEvent& ev)
|
||||
{
|
||||
Widget::onInitTheme(ev);
|
||||
setStyle(skin::SkinTheme::instance()->styles.menuShadeView());
|
||||
|
||||
auto theme = skin::SkinTheme::instance();
|
||||
|
||||
switch (m_click) {
|
||||
case ClickEntries:
|
||||
case DragAndDropEntries:
|
||||
setStyle(theme->styles.normalShadeView());
|
||||
break;
|
||||
case ClickWholeShade:
|
||||
setStyle(theme->styles.menuShadeView());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
bool ColorShades::onProcessMessage(ui::Message* msg)
|
||||
@ -131,7 +144,8 @@ bool ColorShades::onProcessMessage(ui::Message* msg)
|
||||
switch (msg->type()) {
|
||||
|
||||
case ui::kOpenMessage:
|
||||
if (m_click == DragAndDrop) {
|
||||
if (m_click == DragAndDropEntries) {
|
||||
// TODO This connection should be in the ContextBar
|
||||
m_conn = ColorBar::instance()->ChangeSelection.connect(
|
||||
base::Bind<void>(&ColorShades::onChangeColorBarSelection, this));
|
||||
}
|
||||
@ -142,27 +156,42 @@ bool ColorShades::onProcessMessage(ui::Message* msg)
|
||||
ui::set_mouse_cursor(ui::kMoveCursor);
|
||||
return true;
|
||||
}
|
||||
else if (m_click == ClickEntries &&
|
||||
m_hotIndex >= 0 &&
|
||||
m_hotIndex < int(m_shade.size())) {
|
||||
ui::set_mouse_cursor(ui::kHandCursor);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
|
||||
case ui::kMouseEnterMessage:
|
||||
case ui::kMouseLeaveMessage:
|
||||
if (!hasCapture())
|
||||
m_hotIndex = -1;
|
||||
|
||||
invalidate();
|
||||
break;
|
||||
|
||||
case ui::kMouseDownMessage: {
|
||||
if (m_click == DragAndDrop) {
|
||||
if (m_hotIndex >= 0 &&
|
||||
m_hotIndex < int(m_shade.size())) {
|
||||
m_dragIndex = m_hotIndex;
|
||||
m_dropBefore = false;
|
||||
captureMouse();
|
||||
case ui::kMouseDownMessage:
|
||||
if (m_hotIndex >= 0 &&
|
||||
m_hotIndex < int(m_shade.size())) {
|
||||
switch (m_click) {
|
||||
case ClickEntries:
|
||||
Click();
|
||||
m_hotIndex = -1;
|
||||
invalidate();
|
||||
break;
|
||||
case DragAndDropEntries:
|
||||
m_dragIndex = m_hotIndex;
|
||||
m_dropBefore = false;
|
||||
captureMouse();
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case ui::kMouseUpMessage: {
|
||||
if (m_click == Select) {
|
||||
if (m_click == ClickWholeShade) {
|
||||
setSelected(true);
|
||||
Click();
|
||||
closeWindow();
|
||||
@ -226,7 +255,7 @@ void ColorShades::onSizeHint(ui::SizeHintEvent& ev)
|
||||
if (size < 2)
|
||||
ev.setSizeHint(gfx::Size((16+m_boxSize)*ui::guiscale()+textWidth(), 18*ui::guiscale()));
|
||||
else {
|
||||
if (m_click == Select && size > 16)
|
||||
if (m_click == ClickWholeShade && size > 16)
|
||||
size = 16;
|
||||
ev.setSizeHint(gfx::Size(6+m_boxSize*size, 18)*ui::guiscale());
|
||||
}
|
||||
@ -280,7 +309,8 @@ void ColorShades::onPaint(ui::PaintEvent& ev)
|
||||
hotBounds = box;
|
||||
}
|
||||
|
||||
if (!hotBounds.isEmpty() && m_click == DragAndDrop) {
|
||||
if (!hotBounds.isEmpty() &&
|
||||
isHotEntryVisible()) {
|
||||
hotBounds.enlarge(3*ui::guiscale());
|
||||
|
||||
ui::PaintWidgetPartInfo info;
|
||||
|
@ -20,7 +20,11 @@ namespace app {
|
||||
|
||||
class ColorShades : public ui::Widget {
|
||||
public:
|
||||
enum ClickType { DragAndDrop, Select };
|
||||
enum ClickType {
|
||||
ClickEntries,
|
||||
DragAndDropEntries,
|
||||
ClickWholeShade
|
||||
};
|
||||
|
||||
ColorShades(const Shade& colors, ClickType click);
|
||||
|
||||
@ -33,6 +37,8 @@ namespace app {
|
||||
|
||||
void updateShadeFromColorBarPicks();
|
||||
|
||||
int getHotEntry() const { return m_hotIndex; }
|
||||
|
||||
obs::signal<void()> Click;
|
||||
|
||||
private:
|
||||
@ -41,6 +47,9 @@ namespace app {
|
||||
void onSizeHint(ui::SizeHintEvent& ev) override;
|
||||
void onPaint(ui::PaintEvent& ev) override;
|
||||
void onChangeColorBarSelection();
|
||||
bool isHotEntryVisible() const {
|
||||
return m_click != ClickWholeShade;
|
||||
}
|
||||
|
||||
ClickType m_click;
|
||||
Shade m_shade;
|
||||
|
@ -462,7 +462,7 @@ class ContextBar::InkShadesField : public HBox {
|
||||
public:
|
||||
InkShadesField()
|
||||
: m_button(SkinTheme::instance()->parts.iconArrowDown())
|
||||
, m_shade(Shade(), ColorShades::DragAndDrop)
|
||||
, m_shade(Shade(), ColorShades::DragAndDropEntries)
|
||||
, m_loaded(false) {
|
||||
addChild(&m_button);
|
||||
addChild(&m_shade);
|
||||
@ -530,7 +530,7 @@ private:
|
||||
|
||||
int i = 0;
|
||||
for (const Shade& shade : m_shades) {
|
||||
auto shadeWidget = new ColorShades(shade, ColorShades::Select);
|
||||
auto shadeWidget = new ColorShades(shade, ColorShades::ClickWholeShade);
|
||||
shadeWidget->setExpansive(true);
|
||||
shadeWidget->Click.connect(
|
||||
[&]{
|
||||
|
Loading…
x
Reference in New Issue
Block a user