Click here to Skip to main content
15,890,845 members
Articles / Multimedia / GDI+
Article

Drawing Library

Rate me:
Please Sign up or sign in to vote.
4.78/5 (63 votes)
10 Dec 2007CPOL3 min read 293.6K   12.8K   211   117
A library for creating shapes and developing tools.

Screenshot - Painter.JPG

Introduction

This is a generic library for drawing (work in progress). It is composed of some base tools and shapes. It allows you to draw shapes that you want to create, and develop tools to manage your figures.

Using the code

This piece of code describes the implementation of a derived class from Shape and a a derived class from Tool.

C#
public class Ellipse : Shape
{
    public Ellipse()
    {
        Geometric.AddEllipse(new System.Drawing.Rectangle(0, 0, 1, 1));
    }

    public Ellipse(Ellipse ellipse) : base(ellipse)
    {
    }

    public override object Clone()
    {
        return new Ellipse(this);
    }
}
// ....


public class Select : Tool    
{
    .....

    // Override IActions Interface functions

    public override void MouseDown(IDocument document, MouseEventArgs e)
    {
        base.MouseDown(document, e);

        if (SelectShape(document.Shapes, e.Location) == HitPositions.None)
            Select.UnselectAll(document.Shapes);

        if (SelectedShapes != null)
            SelectedShapes(this, Select.GetSelectedShapes(document.Shapes));
    }

    public override void MouseUp(IDocument document, MouseEventArgs e)
    {
        base.MouseUp(document, e);

        document.ActiveCursor = Cursors.Default;
    }
    
    .....
}

It is very important to implement the copy constructor and the function Clone for every new shape, while it is convenient to override the IActions interface during the implementation of a new tool.

Main schemes

In the documentation, there are these schemes:

  • Orange color describes a hot spot class (interface or abstract class usually).
  • Yellow color describes active classes.
  • Blue color describes passive classes (data containers or structs usually).
  • Light grey color describes classes of the framework but not important in the current scheme.
  • Dark grey color describes classes external to the framework.

This scheme represents the actual shapes hierarchy:

Shapes hierarchy

This scheme represents the actual tools hierarchy:

Tools hierarchy

This scheme represents the communication channel between the drawing panel, tools, and shapes:

Hooking Tools-Shapes

The IActions interface contains all the panel actions used by the tools; for example, mouse down and mouse move, and also the paint function. IDocument is an interface, but it is blue because it is only a connection point between tools and shapes, and so it is a passive class.

The following scheme represents the relation between transformers and shapes. Transformers are used to handle shapes moving, so if you want to add any new move, you must only derive two classes, Transformer and CompositeTransformer, and not all the classes in the shapes hierarchy.

Hooking Transformers-Shapes

This scheme represents the actual appearances hierarchy:

Appearances hierarchy

Other schemes are available in the documentation.

Points of interest

To rotate a shape, choose the rotate tool and select the shape. Do a mouse click down and move. To rotate relative to a non-center point, select a shape, click the Ctrl key, do mouse click down, and move.

Rotate example

To deform a shape, change the property Marked to true, and choose the deform tool, do a mouse click down on a marker, and move. Try to group shapes and do the same operations above.

Deform example

Serialization

The serialization operations are made by XmlSerializer. The performance is not very great.

Updates

  • Zoom functionality.
  • Grid on panel.
  • DrawFreeLine tool with possibility to decide the minimum offset between two consecutive points.

Grid example and DrawFreeLine tool

See the Layout options for the Bring To Front and Send To Back functionalities.

Last updates

Added possibility to move shapes with arrows and Control key.

Bug fixes

Modified setter methods of the Text shape to maintain the text state after rotation.

Known bugs

  • Deform tool is not precise on shape border markers.
  • A problem with resize tool and grid enabled.
  • The Undo-Redo mechanism is not precise.

Future developments

  • Improvement of tools (for example, resize).
  • Improvement of performance.
  • Development of other tools.

References

For documentation:

For object-oriented and color theory and other software development information:

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer
Italy Italy
I am a biomedical engineer. I work in Genoa as software developer. I developed MFC ActiveX controls for industrial automation for 2 years and packages for Visual Studio 2005 for 1 year. Currently I'm working in .NET 3.5 in biomedical area.

Comments and Discussions

 
Generalvisual studio C# 2005 Pin
nfasto15-Apr-07 7:14
nfasto15-Apr-07 7:14 
GeneralRe: visual studio C# 2005 Pin
jonnynolimits16-Apr-07 20:39
jonnynolimits16-Apr-07 20:39 
QuestionHow to input the text? Pin
blue_seaing28-Mar-07 5:00
blue_seaing28-Mar-07 5:00 
AnswerRe: How to input the text? Pin
jonnynolimits30-Mar-07 6:04
jonnynolimits30-Mar-07 6:04 
QuestionNew version Pin
mv-da25-Feb-07 8:56
mv-da25-Feb-07 8:56 
AnswerRe: New version Pin
jonnynolimits27-Feb-07 5:54
jonnynolimits27-Feb-07 5:54 
QuestionImage Rotation question Pin
mv-da13-Feb-07 22:07
mv-da13-Feb-07 22:07 
AnswerRe: Image Rotation question Pin
jonnynolimits15-Feb-07 0:34
jonnynolimits15-Feb-07 0:34 
I don't manage the image moving in the Image class.
Here the is the correct code of Image class:

///
/// Image shape.
///

[XmlClassSerializable("image")]
public class Image : Shape
{
#region Added properties to serialize

[XmlFieldSerializable("imageBytes")]
byte[] ImageBytes
{
get { return Globe.Core.Converters.BitmapConverter.BytesFromBitmap(_bitmap); }
set { _bitmap = Globe.Core.Converters.BitmapConverter.BitmapFromBytes(value); }
}

#endregion

#region Constructors

///
/// Default constructor.
///

public Image()
{
}

///
/// Copy constructor.
///

/// <param name="image" />Image to copy.
public Image(Image image) : base(image)
{
_bitmap = image._bitmap.Clone() as Bitmap;
}

///
/// Constructor.
///

/// <param name="bitmap" />Reference bitmap.
public Image(Bitmap bitmap)
{
_bitmap = bitmap.Clone() as Bitmap;

Geometric.AddRectangle(new System.Drawing.Rectangle(new Point(0, 0), _bitmap.Size));
}

#endregion

#region IShape Interface

#region ICloneable Interface

///
/// Clones the shape.
///

/// <returns>
public override object Clone()
{
return new Image(this);
}

#endregion

#region IActions Interface

///
/// Paint function
///

/// <param name="document" />Informations transferred from DrawingPanel
/// <param name="e" />PaintEventArgs
public override void Paint(IDocument document, System.Windows.Forms.PaintEventArgs e)
{
base.Paint(document, e);

PointF[] points = new PointF[] {
Geometric.PathPoints[0],
Geometric.PathPoints[1],
Geometric.PathPoints[3]
};

e.Graphics.DrawImage(_bitmap, points);
}

#endregion

#endregion

#region Properties

Bitmap _bitmap = null;
///
/// Gets or sets the bitmap image.
///

public Bitmap Bitmap
{
get { return _bitmap; }
set
{
_bitmap = value.Clone() as Bitmap;

Geometric.AddRectangle(new System.Drawing.Rectangle(new Point(0, 0), _bitmap.Size));
}
}

#endregion
}

With this correction you have to add another simple class and change a line of code in Rotate tool.
This is the simple class:

///
/// Hand shape.
///

[XmlClassSerializable("hand")]
public class Hand : Image
{
#region Constructors

///
/// Default constructor.
///

public Hand()
{
}

///
/// Copy constructor.
///

/// <param name="image" />Hand to copy.
public Hand(Hand hand) : base(hand)
{
}

///
/// Constructor.
///

/// <param name="bitmap" />Reference bitmap.
public Hand(Bitmap bitmap) : base(bitmap)
{
}

#endregion

#region IShape Interface

#region ICloneable Interface

///
/// Clones the shape.
///

/// <returns>
public override object Clone()
{
return new Hand(this);
}

#endregion

#region IActions Interface

///
/// Paint function
///

/// <param name="document" />Informations transferred from DrawingPanel
/// <param name="e" />PaintEventArgs
public override void Paint(IDocument document, System.Windows.Forms.PaintEventArgs e)
{
e.Graphics.DrawImage(Bitmap, Geometric.GetBounds());
}

#endregion

#endregion
}


This is the line (2 line after the class declaration) to modify in Rotate tool:
Globe.Graphics.Bidimensional.Base.Hand _hand = new Globe.Graphics.Bidimensional.Base.Hand();

Now it should be almost ok.
there is a little problem in Image Paint function. The bitmap is not centered very good...

Thanks a lot for using my library
GeneralRe: Image Rotation question Pin
mv-da16-Feb-07 2:01
mv-da16-Feb-07 2:01 
QuestionText Shape problem Pin
Hayder Marzouk17-Dec-06 23:01
Hayder Marzouk17-Dec-06 23:01 
AnswerRe: Text Shape problem Pin
jonnynolimits18-Dec-06 20:58
jonnynolimits18-Dec-06 20:58 
GeneralRe: Text Shape problem Pin
Mauro Francesconi14-Jun-07 5:34
Mauro Francesconi14-Jun-07 5:34 
GeneralRe: Text Shape problem Pin
jonnynolimits14-Jun-07 21:26
jonnynolimits14-Jun-07 21:26 
GeneralRe: Text Shape problem Pin
Mauro Francesconi15-Jun-07 4:33
Mauro Francesconi15-Jun-07 4:33 
GeneralRe: Text Shape problem Pin
jonnynolimits18-Jun-07 1:29
jonnynolimits18-Jun-07 1:29 
GeneralRe: Text Shape problem Pin
Mauro Francesconi19-Jun-07 22:52
Mauro Francesconi19-Jun-07 22:52 
GeneralRe: Text Shape problem Pin
jonnynolimits20-Jun-07 2:32
jonnynolimits20-Jun-07 2:32 
GeneralRe: Text Shape problem Pin
Mauro Francesconi20-Jun-07 3:43
Mauro Francesconi20-Jun-07 3:43 
GeneralDrawing straight lines Pin
Oppie12-Nov-06 21:05
Oppie12-Nov-06 21:05 
GeneralRe: Drawing straight lines Pin
jonnynolimits12-Nov-06 21:42
jonnynolimits12-Nov-06 21:42 
GeneralExcellect work! Pin
blue_seaing9-Nov-06 14:09
blue_seaing9-Nov-06 14:09 
Questionreal zooming functionality? Pin
marfixianer31-Oct-06 1:50
marfixianer31-Oct-06 1:50 
AnswerRe: real zooming functionality? Pin
jonnynolimits31-Oct-06 5:50
jonnynolimits31-Oct-06 5:50 
GeneralSnap to grid Pin
Oppie26-Oct-06 0:00
Oppie26-Oct-06 0:00 
GeneralRe: Snap to grid Pin
jonnynolimits26-Oct-06 0:28
jonnynolimits26-Oct-06 0:28 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.