1// Aseprite
2// Copyright (C) 2020-2021 Igara Studio S.A.
3// Copyright (C) 2001-2018 David Capello
4//
5// This program is distributed under the terms of
6// the End-User License Agreement for Aseprite.
7
8#ifdef HAVE_CONFIG_H
9#include "config.h"
10#endif
11
12#include "app/app.h"
13#include "app/commands/command.h"
14#include "app/context_access.h"
15#include "app/doc_api.h"
16#include "app/i18n/strings.h"
17#include "app/modules/gui.h"
18#include "app/tx.h"
19#include "app/ui/status_bar.h"
20#include "doc/layer.h"
21#include "doc/sprite.h"
22#include "fmt/format.h"
23#include "ui/alert.h"
24#include "ui/widget.h"
25
26namespace app {
27
28class RemoveLayerCommand : public Command {
29public:
30 RemoveLayerCommand();
31
32protected:
33 bool onEnabled(Context* context) override;
34 void onExecute(Context* context) override;
35};
36
37RemoveLayerCommand::RemoveLayerCommand()
38 : Command(CommandId::RemoveLayer(), CmdRecordableFlag)
39{
40}
41
42bool RemoveLayerCommand::onEnabled(Context* context)
43{
44 return context->checkFlags(ContextFlags::ActiveDocumentIsWritable |
45 ContextFlags::HasActiveSprite |
46 ContextFlags::HasActiveLayer);
47}
48
49void RemoveLayerCommand::onExecute(Context* context)
50{
51 std::string layerName;
52 ContextWriter writer(context);
53 Doc* document(writer.document());
54 Sprite* sprite(writer.sprite());
55 {
56 Tx tx(writer.context(), "Remove Layer");
57 DocApi api = document->getApi(tx);
58
59 const Site* site = writer.site();
60 if (site->inTimeline() &&
61 !site->selectedLayers().empty()) {
62 SelectedLayers selLayers = site->selectedLayers();
63 selLayers.removeChildrenIfParentIsSelected();
64
65 layer_t deletedTopLevelLayers = 0;
66 for (Layer* layer : selLayers) {
67 if (layer->parent() == sprite->root())
68 ++deletedTopLevelLayers;
69 }
70
71 if (deletedTopLevelLayers == sprite->root()->layersCount()) {
72 ui::Alert::show(Strings::alerts_cannot_delete_all_layers());
73 return;
74 }
75
76 for (Layer* layer : selLayers) {
77 api.removeLayer(layer);
78 }
79 }
80 else {
81 if (sprite->root()->layersCount() == 1) {
82 ui::Alert::show(Strings::alerts_cannot_delete_all_layers());
83 return;
84 }
85
86 Layer* layer = writer.layer();
87 layerName = layer->name();
88 api.removeLayer(layer);
89 }
90
91 tx.commit();
92 }
93
94#ifdef ENABLE_UI
95 if (context->isUIAvailable()) {
96 update_screen_for_document(document);
97
98 StatusBar::instance()->invalidate();
99 if (!layerName.empty())
100 StatusBar::instance()->showTip(
101 1000, fmt::format(Strings::remove_layer_x_removed(), layerName));
102 else
103 StatusBar::instance()->showTip(1000,
104 Strings::remove_layer_layers_removed());
105 }
106#endif
107}
108
109Command* CommandFactory::createRemoveLayerCommand()
110{
111 return new RemoveLayerCommand;
112}
113
114} // namespace app
115