1
0
Fork 0
Aegisub/src/image_position_picker.cpp

133 lines
3.6 KiB
C++

#include "image_position_picker.h"
BEGIN_EVENT_TABLE(ImagePositionPicker, wxPanel)
// some useful events
/*
EVT_MOTION(ImagePositionPicker::mouseMoved)
EVT_LEFT_DOWN(ImagePositionPicker::mouseDown)
EVT_LEFT_UP(ImagePositionPicker::mouseReleased)
EVT_RIGHT_DOWN(ImagePositionPicker::rightClick)
EVT_LEAVE_WINDOW(ImagePositionPicker::mouseLeftWindow)
EVT_KEY_DOWN(ImagePositionPicker::keyPressed)
EVT_KEY_UP(ImagePositionPicker::keyReleased)
EVT_MOUSEWHEEL(ImagePositionPicker::mouseWheelMoved)
*/
// catch paint events
EVT_PAINT(ImagePositionPicker::paintEvent)
//Size event
EVT_SIZE(ImagePositionPicker::OnSize)
EVT_MOUSE_EVENTS(ImagePositionPicker::OnMouseEvent)
END_EVENT_TABLE()
// some useful events
/*
void ImagePositionPicker::mouseMoved(wxMouseEvent& event) {}
void ImagePositionPicker::mouseDown(wxMouseEvent& event) {}
void ImagePositionPicker::mouseWheelMoved(wxMouseEvent& event) {}
void ImagePositionPicker::mouseReleased(wxMouseEvent& event) {}
void ImagePositionPicker::rightClick(wxMouseEvent& event) {}
void ImagePositionPicker::mouseLeftWindow(wxMouseEvent& event) {}
void ImagePositionPicker::keyPressed(wxKeyEvent& event) {}
void ImagePositionPicker::keyReleased(wxKeyEvent& event) {}
*/
ImagePositionPicker::ImagePositionPicker(wxWindow* parent, wxImage i, updator upd) : wxPanel(parent)
{
image = i;
prevW = -1;
prevH = -1;
w = image.GetWidth();
h = image.GetHeight();
update = upd;
}
/*
* Called by the system of by wxWidgets when the panel needs
* to be redrawn. You can also trigger this call by
* calling Refresh()/Update().
*/
void ImagePositionPicker::paintEvent(wxPaintEvent& evt)
{
// depending on your system you may need to look at double-buffered dcs
wxPaintDC dc(this);
render(dc);
}
/*
* Alternatively, you can use a clientDC to paint on the panel
* at any time. Using this generally does not free you from
* catching paint events, since it is possible that e.g. the window
* manager throws away your drawing when the window comes to the
* background, and expects you will redraw it when the window comes
* back (by sending a paint event).
*/
void ImagePositionPicker::paintNow()
{
// depending on your system you may need to look at double-buffered dcs
wxClientDC dc(this);
render(dc);
}
/*
* Here we do the actual rendering. I put it in a separate
* method so that it can work no matter what type of DC
* (e.g. wxPaintDC or wxClientDC) is used.
*/
void ImagePositionPicker::render(wxDC& dc)
{
int neww, newh;
dc.GetSize(&neww, &newh);
if (neww != prevW || newh != prevH)
{
// keep the image proportionate
int ww, hh;
if (double(neww) / w >= double(newh) / h) // too long
{
ww = newh * w / h;
hh = newh;
}
else
{
ww = neww;
hh = neww * h / w;
}
resized = wxBitmap(image.Scale(ww, hh /*, wxIMAGE_QUALITY_HIGH*/));
prevW = ww;
prevH = hh;
dc.DrawBitmap(resized, 0, 0, false);
}
else {
dc.DrawBitmap(resized, 0, 0, false);
}
}
/*
* Here we call refresh to tell the panel to draw itself again.
* So when the user resizes the image panel the image should be resized too.
*/
void ImagePositionPicker::OnSize(wxSizeEvent& event) {
Refresh();
//skip the event.
event.Skip();
}
void ImagePositionPicker::OnMouseEvent(wxMouseEvent& evt)
{
wxPoint pos = evt.GetPosition();
if (evt.Dragging() || evt.LeftDown() || evt.LeftUp())
{
int x = pos.x * w / prevW;
int y = pos.y * h / prevH;
if (x >= 0 && x < w && y >= 0 && y < h)
update(x, y, image.GetRed(x, y), image.GetGreen(x, y), image.GetBlue(x, y));
}
else if (evt.LeftDClick()) {
// Propagate the double click event to submit
evt.ResumePropagation(wxEVENT_PROPAGATE_MAX);
evt.Skip();
}
}