Skip to content

Commit d40808b

Browse files
committed
Update box draw to support cropping.
1 parent 7fc162e commit d40808b

3 files changed

Lines changed: 191 additions & 78 deletions

File tree

SerialPrograms/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -705,4 +705,4 @@ if (QT_MAJOR GREATER_EQUAL 6)
705705
endif()
706706

707707
# Add command-line executable (GUI-free) from subdirectory
708-
include(Source/CommandLine/CommandLineExecutable.cmake)
708+
include(Source/CommandLine/CommandLineExecutable.cmake)

SerialPrograms/Source/NintendoSwitch/DevPrograms/BoxDraw.cpp

Lines changed: 155 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -10,15 +10,99 @@
1010
#include "Common/Cpp/Strings/StringTools.h"
1111
#include "BoxDraw.h"
1212

13-
// #include <iostream>
14-
// using std::cout;
15-
// using std::endl;
13+
//#include <iostream>
14+
//using std::cout;
15+
//using std::endl;
1616

1717
namespace PokemonAutomation{
1818
namespace NintendoSwitch{
1919

2020

2121

22+
BoxDrawGroup::~BoxDrawGroup(){
23+
BOX_COORDINATES.remove_listener(*this);
24+
HEIGHT.remove_listener(*this);
25+
WIDTH.remove_listener(*this);
26+
Y.remove_listener(*this);
27+
X.remove_listener(*this);
28+
}
29+
BoxDrawGroup::BoxDrawGroup(
30+
std::string label,
31+
LockMode lock_while_program_is_running,
32+
EnableMode enable_mode,
33+
bool show_restore_defaults_button,
34+
ImageFloatBox box
35+
)
36+
: GroupOption(
37+
std::move(label),
38+
lock_while_program_is_running,
39+
enable_mode,
40+
show_restore_defaults_button
41+
)
42+
, X("<b>X Coordinate:</b>", LockMode::UNLOCK_WHILE_RUNNING, box.x, 0.0, 1.0)
43+
, Y("<b>Y Coordinate:</b>", LockMode::UNLOCK_WHILE_RUNNING, box.y, 0.0, 1.0)
44+
, WIDTH("<b>Width:</b>", LockMode::UNLOCK_WHILE_RUNNING, box.width, 0.0, 1.0)
45+
, HEIGHT("<b>Height:</b>", LockMode::UNLOCK_WHILE_RUNNING, box.height, 0.0, 1.0)
46+
, BOX_COORDINATES(
47+
false,
48+
"ImageFloatBox coordinates",
49+
LockMode::UNLOCK_WHILE_RUNNING,
50+
make_full_str(),
51+
"0.3, 0.3, 0.4, 0.4"
52+
)
53+
{
54+
PA_ADD_OPTION(X);
55+
PA_ADD_OPTION(Y);
56+
PA_ADD_OPTION(WIDTH);
57+
PA_ADD_OPTION(HEIGHT);
58+
PA_ADD_OPTION(BOX_COORDINATES);
59+
60+
BoxDrawGroup::on_config_value_changed(&X);
61+
X.add_listener(*this);
62+
Y.add_listener(*this);
63+
WIDTH.add_listener(*this);
64+
HEIGHT.add_listener(*this);
65+
BOX_COORDINATES.add_listener(*this);
66+
}
67+
68+
void BoxDrawGroup::on_config_value_changed(void* object){
69+
if (object == &X || object == &Y || object == &WIDTH || object == &HEIGHT){
70+
BOX_COORDINATES.set(make_full_str());
71+
report_value_changed(this);
72+
}else if(object == &BOX_COORDINATES){
73+
std::string box_coord_string = BOX_COORDINATES;
74+
std::vector<std::string> all_coords = StringTools::split(box_coord_string, ", ");
75+
76+
std::string x_string = all_coords[0];
77+
std::string y_string = all_coords[1];
78+
std::string width_string = all_coords[2];
79+
std::string height_string = all_coords[3];
80+
81+
double x_coord = std::stod(x_string);
82+
double y_coord = std::stod(y_string);
83+
double width_coord = std::stod(width_string);
84+
double height_coord = std::stod(height_string);
85+
86+
// cout << box_coord_string << endl;
87+
// cout << std::to_string(x_coord) << endl;
88+
// cout << std::to_string(y_coord) << endl;
89+
// cout << std::to_string(width_coord) << endl;
90+
// cout << std::to_string(height_coord) << endl;
91+
92+
X.set(x_coord);
93+
Y.set(y_coord);
94+
WIDTH.set(width_coord);
95+
HEIGHT.set(height_coord);
96+
}else{
97+
report_value_changed(object);
98+
}
99+
}
100+
101+
102+
103+
104+
105+
22106
BoxDraw_Descriptor::BoxDraw_Descriptor()
23107
: SingleSwitchProgramDescriptor(
24108
"NintendoSwitch:BoxDraw",
@@ -32,17 +116,22 @@ BoxDraw_Descriptor::BoxDraw_Descriptor()
32116
{}
33117

34118
BoxDraw::BoxDraw()
35-
: X("<b>X Coordinate:</b>", LockMode::UNLOCK_WHILE_RUNNING, 0.3, 0.0, 1.0)
36-
, Y("<b>Y Coordinate:</b>", LockMode::UNLOCK_WHILE_RUNNING, 0.3, 0.0, 1.0)
37-
, WIDTH("<b>Width:</b>", LockMode::UNLOCK_WHILE_RUNNING, 0.4, 0.0, 1.0)
38-
, HEIGHT("<b>Height:</b>", LockMode::UNLOCK_WHILE_RUNNING, 0.4, 0.0, 1.0)
39-
, BOX_COORDINATES(false, "ImageFloatBox coordinates", LockMode::UNLOCK_WHILE_RUNNING, "0.3, 0.3, 0.4, 0.4", "0.3, 0.3, 0.4, 0.4")
119+
: INFERENCE_BOX(
120+
"Inference Box",
121+
LockMode::UNLOCK_WHILE_RUNNING,
122+
GroupOption::EnableMode::ALWAYS_ENABLED,
123+
false
124+
)
125+
, CONTENT_BOX(
126+
"Content Box",
127+
LockMode::UNLOCK_WHILE_RUNNING,
128+
GroupOption::EnableMode::DEFAULT_DISABLED,
129+
true,
130+
{0.1, 0.1, .8, .8}
131+
)
40132
{
41-
PA_ADD_OPTION(X);
42-
PA_ADD_OPTION(Y);
43-
PA_ADD_OPTION(WIDTH);
44-
PA_ADD_OPTION(HEIGHT);
45-
PA_ADD_OPTION(BOX_COORDINATES);
133+
PA_ADD_OPTION(INFERENCE_BOX);
134+
PA_ADD_OPTION(CONTENT_BOX);
46135
}
47136

48137
class BoxDraw::DrawnBox : public ConfigOption::Listener, public VideoOverlay::MouseListener{
@@ -58,11 +147,8 @@ class BoxDraw::DrawnBox : public ConfigOption::Listener, public VideoOverlay::Mo
58147
// DrawnBox listens to changes in the config option (X, Y, WIDTH, HEIGHT)
59148
// and mouse events on the video overlay layer.
60149
try{
61-
m_parent.X.add_listener(*this);
62-
m_parent.Y.add_listener(*this);
63-
m_parent.WIDTH.add_listener(*this);
64-
m_parent.HEIGHT.add_listener(*this);
65-
m_parent.BOX_COORDINATES.add_listener(*this);
150+
m_parent.INFERENCE_BOX.add_listener(*this);
151+
m_parent.CONTENT_BOX.add_listener(*this);
66152
overlay.add_mouse_listener(*this);
67153
}catch (...){
68154
detach();
@@ -73,17 +159,28 @@ class BoxDraw::DrawnBox : public ConfigOption::Listener, public VideoOverlay::Mo
73159
{
74160
std::lock_guard<Mutex> lg(m_lock);
75161
m_overlay_set.clear();
76-
m_overlay_set.add(COLOR_RED, {m_parent.X, m_parent.Y, m_parent.WIDTH, m_parent.HEIGHT});
77-
}
78-
79-
if (object == &m_parent.X || object == &m_parent.Y || object == &m_parent.WIDTH || object == &m_parent.HEIGHT){
80-
m_parent.update_box_coordinates();
81-
}
82-
else if(object == &m_parent.BOX_COORDINATES){
83-
m_parent.update_individual_coordinates();
162+
double ix = m_parent.INFERENCE_BOX.X;
163+
double iy = m_parent.INFERENCE_BOX.Y;
164+
double iw = m_parent.INFERENCE_BOX.WIDTH;
165+
double ih = m_parent.INFERENCE_BOX.HEIGHT;
166+
if (m_parent.CONTENT_BOX.enabled()){
167+
double cx = m_parent.CONTENT_BOX.X;
168+
double cy = m_parent.CONTENT_BOX.Y;
169+
double cw = m_parent.CONTENT_BOX.WIDTH;
170+
double ch = m_parent.CONTENT_BOX.HEIGHT;
171+
m_overlay_set.add(COLOR_GREEN, {cx, cy, cw, ch});
172+
ix *= cw;
173+
iy *= ch;
174+
iw *= cw;
175+
ih *= ch;
176+
ix += cx;
177+
iy += cy;
178+
}
179+
m_overlay_set.add(COLOR_RED, {ix, iy, iw, ih});
84180
}
85-
86-
181+
// if (object != &m_parent.INFERENCE_BOX){
182+
// m_parent.INFERENCE_BOX.on_config_value_changed(object);
183+
// }
87184
}
88185
virtual void on_mouse_press(double x, double y) override{
89186
// m_parent.WIDTH.set(0);
@@ -107,28 +204,48 @@ class BoxDraw::DrawnBox : public ConfigOption::Listener, public VideoOverlay::Mo
107204
double yl = m_mouse_start->second;
108205
double yh = y;
109206

207+
if (m_parent.CONTENT_BOX.enabled()){
208+
double cx = m_parent.CONTENT_BOX.X;
209+
double cy = m_parent.CONTENT_BOX.Y;
210+
double cw = m_parent.CONTENT_BOX.WIDTH;
211+
double ch = m_parent.CONTENT_BOX.HEIGHT;
212+
213+
xl = (xl - cx) / cw;
214+
xl = std::max(xl, 0.);
215+
xl = std::min(xl, 1.);
216+
217+
yl = (yl - cy) / ch;
218+
yl = std::max(yl, 0.);
219+
yl = std::min(yl, 1.);
220+
221+
xh = (xh - cx) / cw;
222+
xh = std::max(xh, 0.);
223+
xh = std::min(xh, 1.);
224+
225+
yh = (yh - cy) / ch;
226+
yh = std::max(yh, 0.);
227+
yh = std::min(yh, 1.);
228+
}
229+
110230
if (xl > xh){
111231
std::swap(xl, xh);
112232
}
113233
if (yl > yh){
114234
std::swap(yl, yh);
115235
}
116236

117-
m_parent.X.set(xl);
118-
m_parent.Y.set(yl);
119-
m_parent.WIDTH.set(xh - xl);
120-
m_parent.HEIGHT.set(yh - yl);
237+
m_parent.INFERENCE_BOX.X.set(xl);
238+
m_parent.INFERENCE_BOX.Y.set(yl);
239+
m_parent.INFERENCE_BOX.WIDTH.set(xh - xl);
240+
m_parent.INFERENCE_BOX.HEIGHT.set(yh - yl);
121241
// m_parent.update_box_coordinates();
122242
}
123243

124244
private:
125245
void detach(){
126246
m_overlay.remove_mouse_listener(*this);
127-
m_parent.X.remove_listener(*this);
128-
m_parent.Y.remove_listener(*this);
129-
m_parent.WIDTH.remove_listener(*this);
130-
m_parent.HEIGHT.remove_listener(*this);
131-
m_parent.BOX_COORDINATES.remove_listener(*this);
247+
m_parent.CONTENT_BOX.remove_listener(*this);
248+
m_parent.INFERENCE_BOX.remove_listener(*this);
132249
}
133250

134251
private:
@@ -140,41 +257,10 @@ class BoxDraw::DrawnBox : public ConfigOption::Listener, public VideoOverlay::Mo
140257
std::optional<std::pair<double, double>> m_mouse_start;
141258
};
142259

143-
void BoxDraw::update_box_coordinates(){
144-
std::string box_coord_string = std::to_string(X) + ", " + std::to_string(Y) + ", " + std::to_string(WIDTH) + ", " + std::to_string(HEIGHT);
145-
BOX_COORDINATES.set(box_coord_string);
146-
}
147-
148260

149261

150-
void BoxDraw::update_individual_coordinates(){
151-
std::string box_coord_string = BOX_COORDINATES;
152-
std::vector<std::string> all_coords = StringTools::split(box_coord_string, ", ");
153-
154-
std::string x_string = all_coords[0];
155-
std::string y_string = all_coords[1];
156-
std::string width_string = all_coords[2];
157-
std::string height_string = all_coords[3];
158-
159-
double x_coord = std::stod(x_string);
160-
double y_coord = std::stod(y_string);
161-
double width_coord = std::stod(width_string);
162-
double height_coord = std::stod(height_string);
163-
164-
// cout << box_coord_string << endl;
165-
// cout << std::to_string(x_coord) << endl;
166-
// cout << std::to_string(y_coord) << endl;
167-
// cout << std::to_string(width_coord) << endl;
168-
// cout << std::to_string(height_coord) << endl;
169-
170-
X.set(x_coord);
171-
Y.set(y_coord);
172-
WIDTH.set(width_coord);
173-
HEIGHT.set(height_coord);
174-
}
175-
176262
void BoxDraw::program(SingleSwitchProgramEnvironment& env, ProControllerContext& context){
177-
update_individual_coordinates();
263+
// update_individual_coordinates();
178264
DrawnBox drawn_box(*this, env.console.overlay());
179265
drawn_box.on_config_value_changed(this);
180266
context.wait_until_cancel();

SerialPrograms/Source/NintendoSwitch/DevPrograms/BoxDraw.h

Lines changed: 35 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,45 @@
99

1010
#include "Common/Cpp/Options/FloatingPointOption.h"
1111
#include "Common/Cpp/Options/StringOption.h"
12+
#include "Common/Cpp/Options/GroupOption.h"
13+
#include "CommonFramework/ImageTools/ImageBoxes.h"
1214
#include "NintendoSwitch/NintendoSwitch_SingleSwitchProgram.h"
1315

1416
namespace PokemonAutomation{
1517
namespace NintendoSwitch{
1618

1719

20+
class BoxDrawGroup : public GroupOption, public ConfigOption::Listener{
21+
public:
22+
~BoxDrawGroup();
23+
BoxDrawGroup(
24+
std::string label,
25+
LockMode lock_while_program_is_running,
26+
EnableMode enable_mode = EnableMode::ALWAYS_ENABLED,
27+
bool show_restore_defaults_button = false,
28+
ImageFloatBox box = {0.3, 0.3, 0.4, 0.4}
29+
);
30+
31+
virtual void on_config_value_changed(void* object) override;
32+
33+
private:
34+
std::string make_full_str() const{
35+
return
36+
std::to_string(X) + ", " +
37+
std::to_string(Y) + ", " +
38+
std::to_string(WIDTH) + ", " +
39+
std::to_string(HEIGHT);
40+
}
41+
42+
public:
43+
FloatingPointOption X;
44+
FloatingPointOption Y;
45+
FloatingPointOption WIDTH;
46+
FloatingPointOption HEIGHT;
47+
StringOption BOX_COORDINATES;
48+
};
49+
50+
1851

1952
class BoxDraw_Descriptor : public SingleSwitchProgramDescriptor{
2053
public:
@@ -27,20 +60,14 @@ class BoxDraw : public SingleSwitchProgramInstance{
2760
public:
2861
BoxDraw();
2962

30-
void update_box_coordinates();
31-
void update_individual_coordinates();
32-
3363
virtual void program(SingleSwitchProgramEnvironment& env, ProControllerContext& context) override;
3464

3565
private:
3666
class DrawnBox;
3767

3868
private:
39-
FloatingPointOption X;
40-
FloatingPointOption Y;
41-
FloatingPointOption WIDTH;
42-
FloatingPointOption HEIGHT;
43-
StringOption BOX_COORDINATES;
69+
BoxDrawGroup INFERENCE_BOX;
70+
BoxDrawGroup CONTENT_BOX;
4471
};
4572

4673

0 commit comments

Comments
 (0)