Add --trim-by-grid CLI option

This commit is contained in:
David N Campo 2019-03-22 10:54:20 -03:00 committed by David Capello
parent 8062c81018
commit f24eb75298
10 changed files with 73 additions and 7 deletions

View File

@ -480,6 +480,10 @@
<key command="SymmetryMode">
<param name="orientation" value="horizontal" />
</key>
<key command="AutocropSprite" />
<key command="AutocropSprite">
<param name="byGrid" value="true" />
</key>
</commands>
<!-- Keyboard shortcuts to select tools -->

View File

@ -59,6 +59,7 @@ AppOptions::AppOptions(int argc, const char* argv[])
, m_shapePadding(m_po.add("shape-padding").requiresValue("<value>").description("Add padding between frames"))
, m_innerPadding(m_po.add("inner-padding").requiresValue("<value>").description("Add padding inside each frame"))
, m_trim(m_po.add("trim").description("Trim all images before exporting"))
, m_trimByGrid(m_po.add("trim-by-grid").description("Trim all images by its correspondent grid boundaries before exporting"))
, m_crop(m_po.add("crop").requiresValue("x,y,width,height").description("Crop all the images to the given rectangle"))
, m_slice(m_po.add("slice").requiresValue("<name>").description("Crop the sprite to the given slice area"))
, m_filenameFormat(m_po.add("filename-format").requiresValue("<fmt>").description("Special format to generate filenames"))

View File

@ -73,6 +73,7 @@ public:
const Option& shapePadding() const { return m_shapePadding; }
const Option& innerPadding() const { return m_innerPadding; }
const Option& trim() const { return m_trim; }
const Option& trimByGrid() const { return m_trimByGrid; }
const Option& crop() const { return m_crop; }
const Option& slice() const { return m_slice; }
const Option& filenameFormat() const { return m_filenameFormat; }
@ -132,6 +133,7 @@ private:
Option& m_shapePadding;
Option& m_innerPadding;
Option& m_trim;
Option& m_trimByGrid;
Option& m_crop;
Option& m_slice;
Option& m_filenameFormat;

View File

@ -32,6 +32,7 @@ CliOpenFile::CliOpenFile()
listSlices = false;
ignoreEmpty = false;
trim = false;
trimByGrid = false;
oneFrame = false;
crop = gfx::Rect();
}

View File

@ -37,6 +37,7 @@ namespace app {
bool listSlices;
bool ignoreEmpty;
bool trim;
bool trimByGrid;
bool oneFrame;
gfx::Rect crop;

View File

@ -271,6 +271,14 @@ void CliProcessor::process(Context* ctx)
if (m_exporter)
m_exporter->setTrimCels(true);
}
// --trim-by-grid
else if (opt == &m_options.trimByGrid()) {
cof.trim = cof.trimByGrid = true;
if (m_exporter) {
m_exporter->setTrimCels(true);
m_exporter->setTrimByGrid(true);
}
}
// --crop x,y,width,height
else if (opt == &m_options.crop()) {
std::vector<std::string> parts;
@ -712,8 +720,13 @@ void CliProcessor::saveFile(Context* ctx, const CliOpenFile& cof)
// don't have sheet .json) Also, we should trim each frame
// individually (a process that can be done only in
// FileOp::operate()).
if (cof.trim)
ctx->executeCommand(trimCommand);
if (cof.trim) {
Params params;
if (cof.trimByGrid) {
params.set("byGrid", "true");
}
ctx->executeCommand(trimCommand, params);
}
CliOpenFile itemCof = cof;
FilenameInfo fnInfo;
@ -744,6 +757,7 @@ void CliProcessor::saveFile(Context* ctx, const CliOpenFile& cof)
// Call delegate
m_delegate->saveFile(ctx, itemCof);
// for trim or trimByGrid case
if (cof.trim) {
ctx->executeCommand(undoCommand);
clearUndo = true;

View File

@ -96,7 +96,10 @@ void PreviewCliDelegate::saveFile(Context* ctx, const CliOpenFile& cof)
}
if (cof.trim) {
std::cout << " - Trim\n";
if (cof.trimByGrid)
std::cout << " - Trim by Grid\n";
else
std::cout << " - Trim\n";
}
if (cof.ignoreEmpty) {

View File

@ -12,6 +12,7 @@
#include "app/commands/command.h"
#include "app/context_access.h"
#include "app/doc_api.h"
#include "app/i18n/strings.h"
#include "app/modules/gui.h"
#include "app/tx.h"
#include "app/ui/color_bar.h"
@ -87,8 +88,13 @@ public:
AutocropSpriteCommand();
protected:
void onLoadParams(const Params& params) override;
bool onEnabled(Context* context) override;
void onExecute(Context* context) override;
std::string onGetFriendlyName() const override;
private:
bool m_byGrid = false;
};
AutocropSpriteCommand::AutocropSpriteCommand()
@ -96,6 +102,16 @@ AutocropSpriteCommand::AutocropSpriteCommand()
{
}
void AutocropSpriteCommand::onLoadParams(const app::Params &params)
{
m_byGrid = false;
if (params.has_param("byGrid")) {
std::string isByGrid = params.get("byGrid");
if (isByGrid == "true")
m_byGrid = true;
}
}
bool AutocropSpriteCommand::onEnabled(Context* context)
{
return context->checkFlags(ContextFlags::ActiveDocumentIsWritable |
@ -108,8 +124,8 @@ void AutocropSpriteCommand::onExecute(Context* context)
Doc* document(writer.document());
Sprite* sprite(writer.sprite());
{
Tx tx(writer.context(), "Trim Sprite");
document->getApi(tx).trimSprite(sprite);
Tx tx(writer.context(), onGetFriendlyName());
document->getApi(tx).trimSprite(sprite, m_byGrid);
tx.commit();
}
@ -119,6 +135,14 @@ void AutocropSpriteCommand::onExecute(Context* context)
#endif
}
std::string AutocropSpriteCommand::onGetFriendlyName() const
{
if (m_byGrid)
return "Trim Sprite by Grid";
else
return "Trim Sprite";
}
Command* CommandFactory::createCropSpriteCommand()
{
return new CropSpriteCommand;

View File

@ -9,6 +9,7 @@
#endif
#include "app/doc_api.h"
#include "app/snap_to_grid.h"
#include "app/cmd/add_cel.h"
#include "app/cmd/add_frame.h"
@ -45,6 +46,7 @@
#include "app/context.h"
#include "app/doc.h"
#include "app/doc_undo.h"
#include "app/pref/preferences.h"
#include "app/transaction.h"
#include "doc/algorithm/flip_image.h"
#include "doc/algorithm/shrink_bounds.h"
@ -156,7 +158,7 @@ void DocApi::cropSprite(Sprite* sprite, const gfx::Rect& bounds)
}
}
void DocApi::trimSprite(Sprite* sprite)
void DocApi::trimSprite(Sprite* sprite, bool isByGrid)
{
gfx::Rect bounds;
@ -174,6 +176,20 @@ void DocApi::trimSprite(Sprite* sprite)
gfx::Rect frameBounds;
if (doc::algorithm::shrink_bounds(image, frameBounds, get_pixel(image, 0, 0)))
bounds = bounds.createUnion(frameBounds);
if (isByGrid) {
Doc* doc = m_document;
auto& docPref = Preferences::instance().document(doc);
gfx::Point posTopLeft =
snap_to_grid(docPref.grid.bounds(),
bounds.origin(),
PreferSnapTo::FloorGrid);
gfx::Point posBottomRight =
snap_to_grid(docPref.grid.bounds(),
bounds.point2(),
PreferSnapTo::CeilGrid);
bounds = gfx::Rect(posTopLeft, posBottomRight);
}
}
if (!bounds.isEmpty())

View File

@ -45,7 +45,7 @@ namespace app {
void setSpriteSize(Sprite* sprite, int w, int h);
void setSpriteTransparentColor(Sprite* sprite, color_t maskColor);
void cropSprite(Sprite* sprite, const gfx::Rect& bounds);
void trimSprite(Sprite* sprite);
void trimSprite(Sprite* sprite, bool isByGrid);
// Frames API
void addFrame(Sprite* sprite, frame_t newFrame);