abstract_canvas.h 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. /* abstract_canvas.h - generic canvas which can be edited with tools
  2. * Copyright (C) 2017-2018 caryoscelus
  3. *
  4. * This program is free software: you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License as published by
  6. * the Free Software Foundation, either version 3 of the License, or
  7. * (at your option) any later version.
  8. *
  9. * This program is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. * GNU General Public License for more details.
  13. *
  14. * You should have received a copy of the GNU General Public License
  15. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  16. */
  17. #ifndef STUDIO_CANVAS_ABSTRACT_CANVAS_H_4C76BD67_5064_5848_A03E_71D95507C8B2
  18. #define STUDIO_CANVAS_ABSTRACT_CANVAS_H_4C76BD67_5064_5848_A03E_71D95507C8B2
  19. #include <core/std/memory.h>
  20. #include <core/std/vector.h>
  21. #include <core/std/map.h>
  22. #include <core/std/string.h>
  23. #include <QGraphicsView>
  24. #include <generic/context_listener.h>
  25. class QGraphicsScene;
  26. class QGraphicsItem;
  27. namespace rainynite::studio {
  28. class AbstractCanvasEditor;
  29. class CanvasTool;
  30. /**
  31. * Base class for canvas editable with tools.
  32. *
  33. * Register editors with REGISTER_CANVAS_EDITOR macro
  34. * Register tools with REGISTER_CANVAS_TOOL macro
  35. *
  36. * You can subclass this to have a specific canvas with specific
  37. * tools and/or editors.
  38. */
  39. class AbstractCanvas : public QGraphicsView, public ContextListener {
  40. Q_OBJECT
  41. public:
  42. explicit AbstractCanvas(QWidget* parent = nullptr);
  43. virtual ~AbstractCanvas();
  44. /// Set an image to display below all editors and other elements
  45. void set_background_image(QPixmap const& pixmap);
  46. /// Set transform of background image
  47. void set_bg_transform(QTransform const& transform);
  48. /// Load registered tools for this canvas
  49. void load_registered_tools();
  50. /// Add new editor
  51. virtual void add_editor(shared_ptr<AbstractCanvasEditor> editor);
  52. /// Remove editor
  53. void remove_editor(shared_ptr<AbstractCanvasEditor> editor);
  54. /// Remove all editors
  55. void clear_editors();
  56. /// Get latest editor, if any
  57. shared_ptr<AbstractCanvasEditor> latest_editor() const;
  58. /// Get available tool names list
  59. vector<observer_ptr<CanvasTool>> list_tools() const;
  60. /// Switch to tool
  61. void use_tool(string const& name);
  62. /// Zoom at `point`
  63. void zoom_at(QPoint point, double factor);
  64. /// Set zoom level
  65. void set_zoom(double level);
  66. /// Zoom to show rect area
  67. void zoom_to_rect(QRectF rect);
  68. /// Mirror canvas horizontally (i.e. left-right, along Y axis)
  69. void mirror_horizontally(bool value);
  70. /// Return horizontal mirrored status
  71. bool is_mirrored_horizontally() const;
  72. /// Scroll by `delta` (in view coordinates)
  73. void scroll_by(QPointF delta);
  74. void set_context(shared_ptr<EditorContext> context) override;
  75. Q_SIGNALS:
  76. void zoomed();
  77. void tool_changed(string const& tool);
  78. protected:
  79. void mouseDoubleClickEvent(QMouseEvent* event) override;
  80. void mouseMoveEvent(QMouseEvent* event) override;
  81. void mousePressEvent(QMouseEvent* event) override;
  82. void mouseReleaseEvent(QMouseEvent* event) override;
  83. void wheelEvent(QWheelEvent* event) override;
  84. double zoom_level();
  85. vector<shared_ptr<AbstractCanvasEditor>> const& list_editors() const {
  86. return editors;
  87. }
  88. core::NodeTreeIndex active_node_index;
  89. private:
  90. void add_tool(unique_ptr<CanvasTool> tool);
  91. bool use_tool(observer_ptr<CanvasTool> tool);
  92. private:
  93. unique_ptr<QGraphicsScene> const the_scene;
  94. unique_ptr<QGraphicsPixmapItem> const image;
  95. vector<shared_ptr<AbstractCanvasEditor>> editors;
  96. vector<unique_ptr<CanvasTool>> tools;
  97. map<string, observer_ptr<CanvasTool>> named_tools;
  98. observer_ptr<CanvasTool> current_tool;
  99. };
  100. } // namespace rainynite::studio
  101. #endif