0

I need to create a simple 2D designer where user can draw shapes (triangles, rectangles, polygons etc) and also change already created shapes. I have three main classes:

  1. Entity class Area. Contains name, list of points (offsets)
  2. Listenable AreaController which exposes AreaControllerState.
  3. AreaControllerState contains areas property. When it changes the listenable notifies listener.
  4. AreaCustomPainter uses AreaControllerState to draw on 2D canvas.

The simple use case: User presses left mouse button as many times as he need to draw a polygon. The double click closes Area. The CustomPaint is re-drawn with new state. Then user may select a drawn shape. When the shape is selected the user moves mouse pointer over some shape vertex (point) which should be highlighted and mouse cursor also must be changed and then user can move that vertex (point) to change the original shape.

The challenge is hardness of aiming of the current mouse pointer to the specific vertex. So to make aiming easy I am going to create a round Path around the vertex with small radius and do check if this "point path" will contain mouse pointer. But here another challenge raised. Since the path radius is a CustomPainter responsibility. I can create point of any radius I want and AreaPainterController should not care which radius is used. The only thing controller should care it is its state which contains list of Areas (and cirtainly points).

But as mentioned above I need to to change the mouse cursor and I can only that from outside of painter class. So I need a way to make posible to know which radius is used for shape vertices paths in parent widget but I coud not figured out the correct one.

I have an idea to to use onPaint callback which will returns the required data but than I need to create a property which is not belongs to state (but simple widget state variable) and I think it is wrong because it looks like two states.

So how can I implement relations between objects which are responsible for their own functionality but one of them can inform another one in corresponding of SOLID principle?

Again I need a way to know the rounded Path (or radius of that path) of the point which is drawn in painter above this painter to have an ability to change mouse cursor.

The simple code:

Listenable(
  onPointerHover: (event) {
    // In this method I need to change the mouse cursor
    // if mouse pointer belongs to the path around some area vertex.
   _controller.handleMouseMove(event); 
  },
  child: AnimatedBuilder(
    animation: _controller.state,
    builder: (context, child) {
      return MouseRegion(
        cursor: _controller.state.mouseCursor,
        child CustomPaint(
          painter: AreaPainter(
            options: AreaPainterOptions(), // similar to theme.
            state: _controller.state,
          ),
        ),
      );
    },
  ),
)
9
  • and why do you need that CustomPaint at all? if you want different shapes use ShapeBorder and normal GestureDetectors at each selected shape vertex Commented Mar 18, 2024 at 20:55
  • @pskink when I said simple "2D designer" I didn't really mean the simplicity. The designer will be used to draw shapes around the rooms of a given floor plan (drawing on top of the image). Rooms can be rectangles, octagons, shapes with any number of vertices, arcs, etc. The drawn figures must be moved, their sizes changed, and their properties changed. The canvas (image) can be scaled and scrolled and all drawn shapes must be scaled and scrolled accordingly. I can't imagine how to apply ShapeBorder? Commented Mar 19, 2024 at 7:30
  • "The canvas (image) can be scaled and scrolled and all drawn shapes must be scaled and scrolled accordingly." use InteractiveViewer then - it seems that you want to "reinvent the wheel" - something like stackoverflow.com/questions/75090991/… Commented Mar 19, 2024 at 7:34
  • Yep. We all always reinvent wheels. That is why we have Photoshop, Paint, AutoCAD etc :) I will see the link you've sent me. Thanks. Commented Mar 19, 2024 at 7:53
  • @pskink but I still didn't understand how can I draw figures line by line. I do not need to place ready shapes. I need to draw them line by line. I.e. mouse click (point) then move mouse, then click (point) etc... double click (the shape/room is ready). You may see the editor here https://www.sweethome3d.com/SweetHome3DJSOnline.jsp Commented Mar 19, 2024 at 7:59

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.