Getting Started with Smart Canvas Game Projects

Introduction

Smart game projects take advantage of an inbuilt facility to run a procedure at set intervals (e.g. GameView.Delay := 20;). There are many fine demonstrations provided with Smart Game Studio. We show simple motion graphics to get you started. Complete beginners should move straight on to our third example, "Moving Ellipse", which looks more like a game.

Here we adapt two applets from our Oxygene tutorial. Our first example shows a second hand of a timepiece rotating by six degrees every second.

If the demonstrations on this page do not run in your current browser, please try another (such as Chrome). If you see no display at school, the security system might have blocked it. You can try instead this direct link to the program running on its own page.

Second Hand

The second example shows a quadratic curve with a moving attractor. If you see no display at school, the security system might have blocked it. You can try instead this direct link to the program running on its own page.

Quad Curve

In each case it was easy to convert the applet code for use in the canvas game template. See the converted code below. We also converted Neil's RollerApplet to RollerJS to show a way of handling input from the mouse.

Second Hand

unit Unit1;

interface

uses 
  System.Types, SmartCL.System, SmartCL.Components, SmartCL.Application,
  SmartCL.Game, SmartCL.GameApp, SmartCL.Graphics;

type
  TCanvasProject = class(TW3CustomGameApplication)
  private
    const HAND_WIDTH = 5;
    width, height: integer;
    hand_length, hand_long: real;
  protected
    procedure ApplicationStarting; override;
    procedure ApplicationClosing; override;
    procedure PaintView(Canvas: TW3Canvas); override;
  end;

implementation

procedure  TCanvasProject.ApplicationStarting;
begin
  inherited;
  GameView.Delay := 1000;
  GameView.Left := GameView.ClientWidth div 2 - 100;
  GameView.Top := 20;
  GameView.Width := 200;
  GameView.Height := 200;
  width := GameView.Width;
  height := GameView.Height;
  hand_length := width * 2 / 5;
  hand_long := hand_length * 4 / 5; // Distance from the spindle to the tip
  GameView.StartSession(True);
end;

procedure TCanvasProject.ApplicationClosing;
begin
  GameView.EndSession;
  inherited;
end;

procedure TCanvasProject.PaintView(Canvas: TW3Canvas);
begin
  Canvas.FillStyle := 'white';
  Canvas.FillRectF(0, 0, width, height);
  Canvas.Translate(width / 2, height / 2);
  Canvas.Rotate(PI / 30);
  Canvas.Translate(-width / 2, -height / 2);
  Canvas.FillStyle := 'green';
  Canvas.FillRectF(width / 2 - HAND_WIDTH / 2, height / 2 - hand_long , HAND_WIDTH, hand_length);
end;

end.
    

Quadratic Curve

unit Unit1;

interface

uses 
  System.Types, SmartCL.System, SmartCL.Components, SmartCL.Application,
  SmartCL.Game, SmartCL.GameApp, SmartCL.Graphics;

type
  TCanvasProject = class(TW3CustomGameApplication)
  private
    width, height: integer;
    i: Integer := -11;
    increment: Boolean := true;
  protected
    procedure ApplicationStarting; override;
    procedure ApplicationClosing; override;
    procedure PaintView(Canvas: TW3Canvas); override;
  end;

implementation

procedure TCanvasProject.ApplicationStarting;
begin
  inherited;
  GameView.Left := GameView.ClientWidth div 2 - 100;
  GameView.Top := 20;
  GameView.Width := 200;
  GameView.Height := 200;
  GameView.Delay := 5;
  width := GameView.Width;
  height := GameView.Height;
  GameView.StartSession(True);
end;

procedure TCanvasProject.ApplicationClosing;
begin
  GameView.EndSession;
  inherited;
end;

procedure TCanvasProject.PaintView(Canvas: TW3Canvas);
begin
  // Clear background
  Canvas.FillStyle := 'red';
  Canvas.FillRectF(0, 0, GameView.Width, GameView.Height);
  if increment then
    inc(i)
  else
    dec(i);
  if (i < -10) or (i > width + 10) then
    increment := not increment;
  Canvas.FillStyle := 'blue';
  Canvas.BeginPath;
  Canvas.MoveToF(0, height / 2);
  Canvas.QuadraticCurveToF(i, i, width, height / 2);
  Canvas.Stroke;
end;

end.
    

Moving Ellipse

Complete beginners can study this code to see how the movement is achieved and then "ring the changes". In order to use this code:
  1. start a new canvas game project named Motion1;
  2. view the Motion1 unit in the text editor;
  3. highlight all the text;
  4. copy all the code below;
  5. paste it to replace the highlighted text.
You could try to:
  • change the colours of the mobile and the GameView;
  • change the ellipse to a circle by changing one value;
  • change the sizes of the mobile and the rectangle in which it moves;
  • make the mobile move diagonally;
  • make the mobile move up and down;
  • make the mobile change shape when it changes direction;
  • draw more than one mobile;
  • find out how to draw other shapes*;
  • find out how to draw an image*.

*See our tutorial on Smart Mobile Studio.

The next page shows an example of a program derived from Motion1.

Motion1 Code for Version 2.1 of Smart Mobile Studio

unit Unit1;

interface

uses
  System.Types, SmartCL.System, SmartCL.Components, SmartCL.Application,
  SmartCL.Game, SmartCL.GameApp, SmartCL.Graphics;

type
  TCanvasProject = class(TW3CustomGameApplication)
  public
    procedure  ApplicationStarting; override;
    procedure  ApplicationClosing; override;
    procedure  PaintView(Canvas: TW3Canvas); override;
  end;

implementation

//Anything in this colour is just a comment.
const  //Write constants in upper case
  MOB_WIDTH = 20;    //Width of mobile stays at 20 pixels
  MOB_HEIGHT = 15;
  MOB_Y = 100;  //Distance from top of GameView to mobile is 100 pixels
var
  MobX: integer; //Distance of mobile from left of GameView is variable.
  GoingRight: Boolean;  //Boolean variable can be True or False.

procedure TCanvasProject.ApplicationStarting;
begin
  inherited;
  GoingRight := True;
  MobX := 5;
  GameView.Delay := 1;           //1 millisecond
  GameView.StartSession(True);
end;

procedure TCanvasProject.PaintView(Canvas: TW3Canvas);  //Repeated every millisecond
begin
  // Clear background with colour teal.
  Canvas.FillStyle := 'teal';
  Canvas.FillRect(0, 0, GameView.Width, GameView.Height);
  //Draw red ellipse.
  Canvas.FillStyle := 'red';
  Canvas.BeginPath;
  Canvas.Ellipse(MobX, MOB_Y, MobX + MOB_WIDTH, MOB_Y + MOB_HEIGHT); //leftX, topY, rightX, bottomY
  Canvas.Fill;
  // Change position of mobile before next paint.
  if GoingRight = True then
    inc(MobX)      //increment MobX (increase it by 1)
  else
    dec(MobX);     //decrement MobX (decrease it by 1)
  // Change direction when right of ellipse is at right of GameView.
  if MobX + MOB_WIDTH = GameView.Width  then
    GoingRight := False;
  if MobX = 0 then
    GoingRight := True;
end;

procedure TCanvasProject.ApplicationClosing;
begin
  GameView.EndSession;
  inherited;
end;

end.

Programming - a skill for life!

How to write programs in Smart Pascal