/* * Copyright 2017 Laszlo Balazs-Csiki * * This file is part of Pixelitor. Pixelitor is free software: you * can redistribute it and/or modify it under the terms of the GNU * General Public License, version 3 as published by the Free * Software Foundation. * * Pixelitor is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Pixelitor. If not, see <http://www.gnu.org/licenses/>. */ package pixelitor.layers; import pixelitor.menus.NamedAction; import pixelitor.utils.Messages; import javax.swing.*; import java.awt.event.ActionEvent; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import static pixelitor.Composition.ImageChangeActions.FULL; public class LayerMaskActions { private LayerMaskActions() { } public static void addPopupMenu(JLabel label, Layer layer) { label.addMouseListener(new PopupMouseListener(layer)); } private static class PopupMouseListener extends MouseAdapter { private final JPopupMenu menu; public PopupMouseListener(Layer layer) { menu = new JPopupMenu(); JMenu showMenu = new JMenu("Show/Edit"); menu.add(showMenu); MaskViewMode.NORMAL.addToMenu(showMenu, layer); MaskViewMode.SHOW_MASK.addToMenu(showMenu, layer); MaskViewMode.EDIT_MASK.addToMenu(showMenu, layer); MaskViewMode.RUBYLITH.addToMenu(showMenu, layer); menu.addSeparator(); menu.add(new JMenuItem(new DeleteMaskAction(layer))); // masks can be applied only to image layers if (layer instanceof ImageLayer) { menu.add(new JMenuItem(new ApplyMaskAction(layer))); } menu.add(new JMenuItem(new EnableDisableMaskAction(layer))); // masks can be linked only to content layers if (layer instanceof ContentLayer) { menu.add(new JMenuItem(new LinkUnlinkMaskAction(layer))); } } @Override public void mousePressed(MouseEvent e) { if (e.isPopupTrigger()) { popup(e); } else if (SwingUtilities.isLeftMouseButton(e)) { LayerButton.selectLayerIfIconClicked(e); } } @Override public void mouseReleased(MouseEvent e) { if (e.isPopupTrigger()) { popup(e); } } private void popup(MouseEvent e) { menu.show(e.getComponent(), e.getX(), e.getY()); } } private static class DeleteMaskAction extends AbstractAction { private final Layer layer; public DeleteMaskAction(Layer layer) { super("Delete"); this.layer = layer; } @Override public void actionPerformed(ActionEvent e) { layer.deleteMask(true); } } private static class ApplyMaskAction extends AbstractAction { private final Layer layer; public ApplyMaskAction(Layer layer) { super("Apply"); this.layer = layer; } @Override public void actionPerformed(ActionEvent e) { if (!(layer instanceof ImageLayer)) { // actually we should never get here because the popup menu // is enabled only for image layers Messages.showNotImageLayerError(); return; } ((ImageLayer) layer).applyLayerMask(true); layer.getComp().imageChanged(FULL); } } static class EnableDisableMaskAction extends NamedAction implements LayerChangeListener { private final Layer layer; public EnableDisableMaskAction(Layer layer) { super(calcName(layer)); this.layer = layer; layer.addLayerChangeObserver(this); } @Override public void actionPerformed(ActionEvent e) { layer.setMaskEnabled(!layer.isMaskEnabled(), true); refreshName(); } private void refreshName() { setName(calcName(layer)); } private static String calcName(Layer layer) { return layer.isMaskEnabled() ? "Disable" : "Enable"; } @Override public void layerStateChanged() { refreshName(); } } static class LinkUnlinkMaskAction extends NamedAction implements LayerChangeListener { private final Layer layer; public LinkUnlinkMaskAction(Layer layer) { super(calcName(layer)); this.layer = layer; layer.getMask().addLayerChangeObserver(this); } @Override public void actionPerformed(ActionEvent e) { LayerMask mask = layer.getMask(); mask.setLinked(!mask.isLinked(), true); refreshName(); } private void refreshName() { setName(calcName(layer)); } private static String calcName(Layer layer) { return layer.getMask().isLinked() ? "Unlink" : "Link"; } @Override public void layerStateChanged() { refreshName(); } } }