Commit 685529ce authored by twanvl's avatar twanvl

ImageValueEditor; slice window; fixed bug in resample

parent be4009b6
......@@ -93,8 +93,8 @@ void resample_pass(const Image& img_in, Image& img_out, int offset_in, int offse
if (out_rem > 0) {
// eat a partial input pixel
totR += in[0] * out_rem;
totR += in[1] * out_rem;
totR += in[2] * out_rem;
totG += in[1] * out_rem;
totB += in[2] * out_rem;
in_rem -= out_rem;
}
// store
......
......@@ -175,30 +175,35 @@ bool CardListBase::canPaste() const {
return wxTheClipboard->IsSupported(CardDataObject::format);
}
void CardListBase::doCopy() {
if (!canCopy()) return;
if (!wxTheClipboard->Open()) return;
wxTheClipboard->SetData(new CardOnClipboard(set, selected_card)); // ignore result
bool CardListBase::doCopy() {
if (!canCopy()) return false;
if (!wxTheClipboard->Open()) return false;
bool ok = wxTheClipboard->SetData(new CardOnClipboard(set, selected_card)); // ignore result
wxTheClipboard->Close();
return ok;
}
void CardListBase::doCut() {
bool CardListBase::doCut() {
// cut = copy + delete
if (!canCut()) return;
doCopy();
set->actions.add(new RemoveCardAction(*set, selected_card) );
if (!canCut()) return false;
if (!doCopy()) return false;
set->actions.add(new RemoveCardAction(*set, selected_card));
return true;
}
void CardListBase::doPaste() {
bool CardListBase::doPaste() {
// get data
if (!canPaste()) return;
if (!wxTheClipboard->Open()) return;
if (!canPaste()) return false;
if (!wxTheClipboard->Open()) return false;
CardDataObject data;
bool ok = wxTheClipboard->GetData(data);
wxTheClipboard->Close();
if (!ok) return;
if (!ok) return false;
// add card to set
CardP card = data.getCard(set);
if (card) {
set->actions.add(new AddCardAction(*set, card));
return true;
} else {
return false;
}
}
......
......@@ -69,9 +69,10 @@ class CardListBase : public wxListView, public SetView {
bool canCut() const;
bool canCopy() const;
bool canPaste() const;
void doCut();
void doCopy();
void doPaste();
// Try to perform a clipboard operation, return success
bool doCut();
bool doCopy();
bool doPaste();
// --------------------------------------------------- : Set actions
......
This diff is collapsed.
//+----------------------------------------------------------------------------+
//| Description: Magic Set Editor - Program to make Magic (tm) cards |
//| Copyright: (C) 2001 - 2006 Twan van Laarhoven |
//| License: GNU General Public License 2 or later (see file COPYING) |
//+----------------------------------------------------------------------------+
#ifndef HEADER_GUI_IMAGE_SLICE_WINDOW
#define HEADER_GUI_IMAGE_SLICE_WINDOW
// ----------------------------------------------------------------------------- : Includes
#include <util/prec.hpp>
class ImageSlicePreview;
class ImageSliceSelector;
class wxSpinEvent;
// ----------------------------------------------------------------------------- : ImageSlice
/// A slice of an image, i.e. a selected rectangle
class ImageSlice {
public:
ImageSlice(const Image& source, const wxSize& target_size);
Image source; ///< The source image
wxSize target_size; ///< Size of the target image
Color background; ///< Color for areas outside the source image
wxRect selection; ///< Area to slect from source
bool allow_outside;
bool aspect_fixed; ///< Aspect ratio lock?
// Filters
bool sharpen;
int sharpen_amount;
/// Enforce relations between values
void constrain();
/// Get the sliced image
Image getSlice() const;
// Zoom factor
inline double zoomX() const { return target_size.GetWidth() / (double)selection.width; }
inline double zoomY() const { return target_size.GetHeight() / (double)selection.height; }
inline void zoomX(double zoom) { selection.width = target_size.GetWidth() / zoom; }
inline void zoomY(double zoom) { selection.height = target_size.GetHeight() / zoom; }
};
// ----------------------------------------------------------------------------- : ImageSliceWindow
/// Dialog for selecting a slice of an image
class ImageSliceWindow : public wxDialog {
public:
ImageSliceWindow(Window* parent, const Image& source, const wxSize& target_size);
/// Return the sliced image
Image getImage() const;
// --------------------------------------------------- : Data
private:
// The slice we are extracting
ImageSlice slice;
// Gui items
ImageSlicePreview* preview;
ImageSliceSelector* selector;
wxRadioBox* size;
wxSpinCtrl* top, *left, *width, *height;
wxCheckBox* fix_aspect;
wxSpinCtrl* zoom, *zoom_x, *zoom_y;
wxSizer* zoom_sizer, *zoom_fixed, *zoom_free;
wxCheckBox* sharpen;
wxSlider* sharpen_amount;
// --------------------------------------------------- : Events
DECLARE_EVENT_TABLE();
void onOk (wxCommandEvent&);
void onSize (wxSizeEvent&);
void onChangeSize (wxCommandEvent&);
void onChangeLeft (wxCommandEvent&);
void onChangeTop (wxCommandEvent&);
void onChangeWidth (wxCommandEvent&);
void onChangeHeight (wxCommandEvent&);
void onChangeFixAspect (wxCommandEvent&);
void onChangeZoom (wxSpinEvent&);
void onChangeZoomX (wxSpinEvent&);
void onChangeZoomY (wxSpinEvent&);
void onChangeSharpen (wxCommandEvent&);
void onChangeSharpenAmount(wxScrollEvent&);
// --------------------------------------------------- : Updating
// Something changed in the selector control, update controls and selection displays
void onSelectionUpdate();
// The manual controls were changed
void onUpdateFromControl();
// Update the values in the controls
void updateControls();
};
// ----------------------------------------------------------------------------- : ImageSlicePreview
/// A preview of the sliced image
class ImageSlicePreview : public wxControl {
public:
ImageSlicePreview(Window* parent, int id, ImageSlice& slice);
/// Notify that the slice was updated
void update();
// --------------------------------------------------- : Data
private:
Bitmap bitmap;
ImageSlice& slice;
bool mouse_down;
int mouseX, mouseY; ///< starting mouse position
wxRect start_selection; ///< selection in slice at start of dragging
// --------------------------------------------------- : Events
DECLARE_EVENT_TABLE();
wxSize DoGetBestSize() const;
void onLeftDown(wxMouseEvent&);
void onLeftUp (wxMouseEvent&);
void onMotion (wxMouseEvent&);
void onPaint(wxPaintEvent&);
void draw(DC& dc);
};
// ----------------------------------------------------------------------------- : ImageSliceSelector
// A overview of the slicing of the image, allows to select the sliced area
class ImageSliceSelector : public wxControl {
public:
ImageSliceSelector(Window* parent, int id, ImageSlice& slice);
/// Notify that the slice was updated
void update();
// --------------------------------------------------- : Data
private:
ImageSlice& slice;
Bitmap bitmap, bitmap_no_sel; ///< Bitmaps showing selection
bool mouse_down;
int mouseX, mouseY; ///< starting mouse position
int dragX, dragY; ///< corner that is being dragged
wxRect start_selection; ///< selection in slice at start of dragging
double scaleX, scaleY; ///< Amount the source image is scaled to fit in this control
static const int border = 8;
// --------------------------------------------------- : Events
DECLARE_EVENT_TABLE();
void onLeftDown(wxMouseEvent&);
void onLeftUp (wxMouseEvent&);
void onMotion (wxMouseEvent&);
void onPaint(wxPaintEvent&);
void onSize(wxSizeEvent&);
// Is the mouse on a (scale) handle?
bool onHandle(const wxMouseEvent& ev, int dx, int dy) const;
// Is the mouse on any handle?
bool onAnyHandle(const wxMouseEvent& ev, int* dxOut, int* dyOut) const;
// Return the position of a handle, dx,dy in {-1,0,1}
wxPoint handlePos(int dx, int dy) const;
void draw(DC& dc);
// Draw a handle, dx and dy indicate the side, can be {-1,0,1}
void drawHandle(DC& dc, int dx, int dy);
void createBitmap();
};
// ----------------------------------------------------------------------------- : EOF
#endif
......@@ -69,7 +69,7 @@ class ValueEditor {
// Deletes the selection from this field editor, cut = copy + delete, returns success
virtual bool doDelete() { return false; }
// Cuts the selection from this field editor
bool doCut() { return doCopy() && doDelete(); }
bool doCut() { return doCopy() && doDelete(); }
/// Initiate pasting in this field editor,
/** should again check if pasting is possible and fail silently if not, returns success */
virtual bool doPaste() { return false; }
......
......@@ -7,7 +7,69 @@
// ----------------------------------------------------------------------------- : Includes
#include <gui/value/image.hpp>
#include <gui/image_slice_window.hpp>
#include <data/format/clipboard.hpp>
#include <data/action/value.hpp>
#include <wx/clipbrd.h>
// ----------------------------------------------------------------------------- :
// ----------------------------------------------------------------------------- : ImageValueEditor
IMPLEMENT_VALUE_EDITOR(Image) {}
void ImageValueEditor::onLeftDClick(const RealPoint&, wxMouseEvent&) {
String filename = wxFileSelector(_("Open image file"), _(""), _(""), _(""),
_("All images|*.bmp;*.jpg;*.png;*.gif|Windows bitmaps (*.bmp)|*.bmp|JPEG images (*.jpg;*.jpeg)|*.jpg;*.jpeg|PNG images (*.png)|*.png|GIF images (*.gif)|*.gif|TIFF images (*.tif;*.tiff)|*.tif;*.tiff"),
wxOPEN);
if (filename.empty()) {
return;
} else {
sliceImage(wxImage(filename));
}
}
void ImageValueEditor::sliceImage(const Image& image) {
if (!image.Ok()) return;
// slice
ImageSliceWindow s(wxGetTopLevelParent(&editor()), image, style().getSize());
if (s.ShowModal() == wxID_OK) {
// store the image into the set
FileName new_image_file = getSet().newFileName(field().name,_("")); // a new unique name in the package
s.getImage().SaveFile(getSet().nameOut(new_image_file), wxBITMAP_TYPE_JPEG);
getSet().actions.add(value_action(valueP(), new_image_file));
}
}
// ----------------------------------------------------------------------------- : Clipboard
bool ImageValueEditor::canCopy() const {
return !value().filename.empty();
}
bool ImageValueEditor::canPaste() const {
return wxTheClipboard->IsSupported(wxDF_BITMAP) &&
!wxTheClipboard->IsSupported(CardDataObject::format); // we don't want to (accidentally) paste card images
}
bool ImageValueEditor::doCopy() {
// load image
InputStreamP image_file = getSet().openIn(value().filename);
Image image;
if (!image.LoadFile(*image_file)) return false;
// set data
if (!wxTheClipboard->Open()) return false;
bool ok = wxTheClipboard->SetData(new wxBitmapDataObject(image));
wxTheClipboard->Close();
return ok;
}
bool ImageValueEditor::doPaste() {
// get bitmap
if (!wxTheClipboard->Open()) return false;
wxBitmapDataObject data;
bool ok = wxTheClipboard->GetData(data);
wxTheClipboard->Close();
if (!ok) return false;
// slice
sliceImage(data.GetBitmap().ConvertToImage());
return true;
}
......@@ -19,6 +19,20 @@
class ImageValueEditor : public ImageValueViewer, public ValueEditor {
public:
DECLARE_VALUE_EDITOR(Image);
virtual void onLeftDClick(const RealPoint&, wxMouseEvent&);
// --------------------------------------------------- : Clipboard
virtual bool canCopy() const;
virtual bool canCut() const { return false; }
virtual bool canPaste() const;
virtual bool doCopy();
virtual bool doPaste();
private:
// Open the image slice window showing the give image
void sliceImage(const Image&);
};
// ----------------------------------------------------------------------------- : EOF
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment