#include <xtd/drawing/pens>
#include <xtd/forms/application>
#include <xtd/forms/button>
#include <xtd/forms/form>
#include <xtd/forms/label>
#include <xtd/forms/message_box>
#include <xtd/forms/numeric_up_down>
#include <xtd/forms/open_file_dialog>
#include <xtd/forms/panel>
#include <xtd/forms/track_bar>
namespace painting_example {
class form1 :
public form {
public:
form1() {
text("Painting example");
client_size({640, 480});
panel_colors_container.parent(*this);
panel_colors_container.border_style(forms::border_style::fixed_single);
panel_colors_container.location({10, 10});
panel_colors_container.client_size({512, 32});
for (
auto color : {color::dark_magenta, color::dark_cyan, color::brown, color::dark_blue, color::dark_green, color::dark_red, color::gray, color::dark_gray, color::magenta, color::cyan, color::yellow, color::blue, color::green, color::red, color::white, color::black}) {
auto panel_color = new_ptr<panel>();
panel_color->parent(panel_colors_container);
panel_color->size({32, 32});
panel_color->back_color(
color);
panel_color->dock(dock_style::left);
panel_color->click +=
event_handler {*
this, &form1::choose_current_color};
panel_colors.push_back(panel_color);
}
current_color = panel_colors[panel_colors.size() - 1]->back_color();
panel_colors[panel_colors.size() - 1]->border_style(forms::border_style::fixed_single);
button_clear.parent(*this);
button_clear.text("Clear");
button_clear.location({542, 13});
button_clear.click += [&] {
panel_painting.invalidate();
};
button_open.parent(*this);
button_open.text("Open...");
button_open.location({542, 47});
button_open.click += [&] {
if (new_picture.
width() > 128 || new_picture.
height() > 128)
message_box::show(*this, "The size of the image must be less than or equal to 128 x 128 pixels.", "Painting example", message_box_buttons::ok, message_box_icon::error);
else {
picture = new_picture;
panel_painting.
size({picture.width() * zoom, picture.height() * zoom});
panel_painting.invalidate();
}
}
};
label_zoom.parent(*this);
label_zoom.auto_size(false);
label_zoom.location({10, 60});
label_zoom.anchor(anchor_styles::top | anchor_styles::left);
label_zoom.text("Zoom");
track_bar_zoom.parent(*this);
track_bar_zoom.auto_size(false);
track_bar_zoom.location({60, 55});
track_bar_zoom.anchor(anchor_styles::top | anchor_styles::left);
track_bar_zoom.set_range(1, 50);
track_bar_zoom.tick_style(forms::tick_style::none);
track_bar_zoom.value(zoom);
track_bar_zoom.value_changed += [&] {
zoom = track_bar_zoom.value();
numeric_up_down_zoom.value(zoom);
panel_painting.size({picture.width() * zoom, picture.height() * zoom});
panel_painting.invalidate();
};
track_bar_zoom.size({390, 25});
numeric_up_down_zoom.parent(*this);
numeric_up_down_zoom.location({470, 55});
numeric_up_down_zoom.set_range(1, 50);
numeric_up_down_zoom.value(zoom);
numeric_up_down_zoom.value_changed += [&] {
zoom = as<int>(numeric_up_down_zoom.value());
track_bar_zoom.value(zoom);
panel_painting.size({picture.width() * zoom, picture.height() * zoom});
panel_painting.invalidate();
};
numeric_up_down_zoom.width(52);
panel_main.parent(*this);
panel_main.auto_scroll(true);
panel_main.border_style(forms::border_style::fixed_single);
panel_main.location({10, 90});
panel_main.size({620, 380});
panel_main.anchor(anchor_styles::top | anchor_styles::left | anchor_styles::bottom | anchor_styles::right);
panel_painting.parent(panel_main);
panel_painting.back_color(color::white_smoke);
panel_painting.size({picture.width() * zoom, picture.height() * zoom});
if (e.x() / zoom >= 0 && e.x() / zoom < picture.width() && e.y() / zoom >= 0 && e.y() / zoom < picture.height()) {
picture.set_pixel(e.x() / zoom, e.y() / zoom, e.button() == mouse_buttons::left ? current_color : color::from_argb(0, 0, 0, 0));
panel_painting.invalidate(
rectangle(e.x() / zoom * zoom, e.y() / zoom * zoom, zoom, zoom));
}
};
if (e.button() == mouse_buttons::left && e.x() / zoom >= 0 && e.x() / zoom < picture.width() && e.y() / zoom >= 0 && e.y() / zoom < picture.height()) {
picture.set_pixel(e.x() / zoom, e.y() / zoom, current_color);
panel_painting.invalidate(
rectangle(e.x() / zoom * zoom, e.y() / zoom * zoom, zoom, zoom));
}
};
for (auto y = 0; y < panel_painting.client_size().height(); y += zoom)
for (auto x = 0; x < panel_painting.client_size().width(); x += zoom)
if (picture.get_pixel(x / zoom, y / zoom) != color::from_argb(0, 0, 0, 0))
e.graphics().fill_rectangle(
solid_brush(picture.get_pixel(x / zoom, y / zoom)), x, y, zoom, zoom);
if (zoom > 3) {
for (auto index = 0; index < panel_painting.client_size().width(); index += zoom)
e.graphics().draw_line(pens::light_blue(), index, 0, index, panel_painting.client_size().height());
for (auto index = 0; index < panel_painting.client_size().height(); index += zoom)
e.graphics().draw_line(pens::light_blue(), 0, index, panel_painting.client_size().width(), index);
}
};
}
private:
void choose_current_color(
object& sender,
const event_args& e) {
for (
auto panel : panel_colors)
current_color = as<control>(sender).back_color();
}
int zoom = 20;
panel panel_colors_container;
};
}
auto main() -> int {
application::run(painting_example::form1 {});
}
Represents a strongly typed list of objects that can be accessed by index. Provides methods to search...
Definition list.hpp:71
Encapsulates a GDI+ bitmap, which consists of the pixel data for a graphics image and its attributes....
Definition bitmap.hpp:26
Represents an ARGB (alpha, red, green, blue) color.
Definition color.hpp:49
int32 height() const noexcept
Gets the height, in pixels, of this image.
int32 width() const noexcept
Gets the width, in pixels, of this image.
const drawing::size & size() const noexcept
Gets the width and height, in pixels, of this image.
Stores a set of four integers that represent the location and size of a rectangle.
Definition rectangle.hpp:44
Defines a xtd::drawing::brush of a single color. Brushes are used to fill graphics shapes,...
Definition solid_brush.hpp:30
Represents the base class for classes that contain event data, and provides a value to use for events...
Definition event_args.hpp:18
generic_event_handler<> event_handler
Represents the method that will handle an event that has no event data.
Definition event_handler.hpp:32
The xtd::collections::generic namespace contains interfaces and classes that define generic collectio...
Definition comparer.hpp:15
The xtd::drawing namespace provides access to GDI+ basic graphics functionality. More advanced functi...
Definition brush.hpp:18
The xtd namespace contains all fundamental classes to access Hardware, Os, System,...
Definition xtd_about_box.hpp:10