Difference between revisions of "Pascal for Visual Basic users"

From Lazarus wiki
Jump to navigationJump to search
m (→‎Substitution tables: Fix page link)
 
(6 intermediate revisions by 2 users not shown)
Line 1: Line 1:
<!--- {{Pascal for VisualBasic users}} --->
 
 
== Overview ==
 
== Overview ==
This wiki page has been created to help you if you are switching from VisualBasic to FreePascal (the Pascal dialect and compiler used by Lazarus).
+
 
 +
This wiki page has been created to help you if you are switching from Visual Basic to Free Pascal (the Pascal dialect and compiler used by Lazarus).
 
It is not meant to convince you that Lazarus is better than VB (or vice versa).
 
It is not meant to convince you that Lazarus is better than VB (or vice versa).
 
Although VB and Pascal have superficial similarities these two languages differ greatly.
 
Although VB and Pascal have superficial similarities these two languages differ greatly.
Line 7: Line 7:
  
 
== Comparison and assignment of values ==
 
== Comparison and assignment of values ==
 +
 
Values in Pascal are compared using the = operator.
 
Values in Pascal are compared using the = operator.
  
Line 12: Line 13:
  
 
For example:
 
For example:
<syntaxhighlight>
+
<syntaxhighlight lang=pascal>
 
if a = 1 then b := 2;
 
if a = 1 then b := 2;
 
</syntaxhighlight>
 
</syntaxhighlight>
Line 20: Line 21:
  
 
For example:
 
For example:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
for i := 0 to 100 do
 
for i := 0 to 100 do
 
begin
 
begin
Line 28: Line 30:
  
 
== Variables ==
 
== Variables ==
 +
 
=== Declaring variables ===
 
=== Declaring variables ===
 +
 
In Pascal '''all''' variables have to be declared before use, and you have to make the declarations in a special '''var''' section which must precede the code that makes use of the variable.
 
In Pascal '''all''' variables have to be declared before use, and you have to make the declarations in a special '''var''' section which must precede the code that makes use of the variable.
 
You cannot declare a new variable in the middle of code.
 
You cannot declare a new variable in the middle of code.
  
 
For example:
 
For example:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
procedure VarDecl;
 
procedure VarDecl;
 
var
 
var
Line 48: Line 53:
  
 
To initialize a local variable upon declaration the following syntax can be used in procedures and functions only.
 
To initialize a local variable upon declaration the following syntax can be used in procedures and functions only.
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
var
 
var
 
   MyVar1: string  = '';
 
   MyVar1: string  = '';
Line 55: Line 61:
  
 
=== Types of variables ===
 
=== Types of variables ===
Besides the variables known in VB, FreePascal supports unsigned integers.
+
 
 +
Besides the variables known in VB, Free Pascal supports unsigned integers.
 
You should pay special attention not to mix them with signed integers.
 
You should pay special attention not to mix them with signed integers.
  
 
== Loops ==
 
== Loops ==
FreePascal has four kinds of loops.
+
 
 +
Free Pascal has four kinds of loops.
  
 
[[FOR..DO|for... do... ]]
 
[[FOR..DO|for... do... ]]
Line 70: Line 78:
  
 
=== For... do... ===
 
=== For... do... ===
 +
 
This is quite similar to the For.. Next loop in VB, but more limited in syntax. The following restrictions apply in Pascal:
 
This is quite similar to the For.. Next loop in VB, but more limited in syntax. The following restrictions apply in Pascal:
  
Line 79: Line 88:
  
 
For example:
 
For example:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
procedure ForLoop;
 
procedure ForLoop;
 
var
 
var
Line 92: Line 102:
  
 
4. In Lazarus it is possible to loop down when the index is a '''byte''', which is '''not''' possible in VB6.
 
4. In Lazarus it is possible to loop down when the index is a '''byte''', which is '''not''' possible in VB6.
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
procedure ForLoop;
 
procedure ForLoop;
 
var
 
var
Line 104: Line 115:
 
</syntaxhighlight>
 
</syntaxhighlight>
  
5. The value of the counter (i in the example above) cannot be changed programmatically inside the loop. Attempting to do so will throw a compiler error. Instead one could use ''Continue'' to skip execution of a loop:
+
5. The value of the counter (i in the example above) can'''not''' be changed programmatically inside the loop. Attempting to do so will throw a compiler error. Instead one could use ''Continue'' to skip execution of a loop:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
procedure ForLoop;
 
procedure ForLoop;
 
var
 
var
Line 112: Line 124:
 
   for i := 0 to 5 do
 
   for i := 0 to 5 do
 
   begin
 
   begin
     if i=2 then Continue; //Following part of the loop will not be xecuted
+
     if i=2 then Continue; //Following part of the loop will not be executed
 
     ShowMessage (IntToStr (i));
 
     ShowMessage (IntToStr (i));
 
   end; // for i
 
   end; // for i
Line 119: Line 131:
  
 
6. In order to interrupt execution of a loop one could use ''Break''.
 
6. In order to interrupt execution of a loop one could use ''Break''.
 +
 +
<syntaxhighlight lang=pascal>
 +
procedure ForLoop;
 +
var
 +
  i: integer;
 +
begin
 +
  for i := 0 to 5 do
 +
  begin
 +
    if i=2 then
 +
    begin
 +
      ShowMessage (IntToStr (i));
 +
      break;
 +
    end; //if
 +
  end; // for i
 +
end.  // procedure ForLoop
 +
</syntaxhighlight>
  
 
== Functions and procedures ==
 
== Functions and procedures ==
  
Output of functions is supplied as
+
Output of functions is supplied as:
<syntaxhighlight>Result:=Value</syntaxhighlight>
+
 
Note that ''Result:='' does '''not''' act as ''Return''. Function will not exit after assigning it.
+
<syntaxhighlight lang=pascal>Result:=Value</syntaxhighlight>
One should use <syntaxhighlight>exit(Value)</syntaxhighlight> instead.
+
 
 +
Note that ''Result:='' does '''not''' act as ''Return''. Function will '''not''' exit after assigning it.
 +
 
 +
One should use <syntaxhighlight lang=pascal>exit(Value)</syntaxhighlight> instead.
  
 
=== Visibility ===
 
=== Visibility ===
 +
 
In FPC a function or a procedure cannot see another one, which is written after it.
 
In FPC a function or a procedure cannot see another one, which is written after it.
  
 
Example:
 
Example:
  
<syntaxhighlight>
+
<syntaxhighlight lang=pascal>
 
procedure Proc1;
 
procedure Proc1;
 
begin
 
begin
Line 146: Line 178:
 
To enable visibility, disregarding writing order, functions and procedures have to be declared.
 
To enable visibility, disregarding writing order, functions and procedures have to be declared.
  
<syntaxhighlight>
+
<syntaxhighlight lang=pascal>
 
unit MyUnit;
 
unit MyUnit;
 
...
 
...
Line 166: Line 198:
  
 
=== Using default parameters in functions and procedures ===
 
=== Using default parameters in functions and procedures ===
 +
 
In Pascal functions and procedures it is possible for parameters to automatically take default values. However, in the parameter list the parameters that might take default values must be declared as a contiguous list at the end of the parameter declaration part. Also, when a routine with default parameter(s) is subsequently called in your code, you can only specify non-default values beginning at the first parameter which would otherwise take a default value. You cannot specify a non-default value for a later parameter, if there are preceding parameters you have to specify values for which have not also been specified explicitly in the function or procedure call.
 
In Pascal functions and procedures it is possible for parameters to automatically take default values. However, in the parameter list the parameters that might take default values must be declared as a contiguous list at the end of the parameter declaration part. Also, when a routine with default parameter(s) is subsequently called in your code, you can only specify non-default values beginning at the first parameter which would otherwise take a default value. You cannot specify a non-default value for a later parameter, if there are preceding parameters you have to specify values for which have not also been specified explicitly in the function or procedure call.
  
 
For example:
 
For example:
If a procedure is declared (correctly) as follows with two default parameters,
+
 
<syntaxhighlight>
+
If a procedure is declared (correctly) as follows with two default parameters:
 +
 
 +
<syntaxhighlight lang=pascal>
 
procedure SampleProc(parm1: integer; parm2: string= 'something'; parm3:Boolean= True);
 
procedure SampleProc(parm1: integer; parm2: string= 'something'; parm3:Boolean= True);
 
begin
 
begin
Line 177: Line 212:
  
 
it is not possible to call SampleProc as in VB like this:
 
it is not possible to call SampleProc as in VB like this:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
   SampleProc(5,,False);
 
   SampleProc(5,,False);
 
</syntaxhighlight>
 
</syntaxhighlight>
Line 186: Line 222:
  
 
These are valid calls:
 
These are valid calls:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
   SampleProc(5,'something',False);
 
   SampleProc(5,'something',False);
  
Line 197: Line 234:
  
 
== Dynamic arrays ==
 
== Dynamic arrays ==
 +
 
In Pascal the minimum index of a dynamic array is 0, i.e. ''MyArray (1)'' will return the '''second''' elements of an array named ''MyArray''.
 
In Pascal the minimum index of a dynamic array is 0, i.e. ''MyArray (1)'' will return the '''second''' elements of an array named ''MyArray''.
  
Arrays are resized using  
+
Arrays are resized using:
<syntaxhighlight>
+
 
 +
<syntaxhighlight lang=pascal>
 
setlength (MyArray, NewDimension);
 
setlength (MyArray, NewDimension);
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
 
''SetLength'' does not clear the array, i.e. it acts like ''ReDim Preserve'', not like ''ReDim''.
 
''SetLength'' does not clear the array, i.e. it acts like ''ReDim Preserve'', not like ''ReDim''.
  
 
== Translation of some commonly sought commands ==
 
== Translation of some commonly sought commands ==
 +
 
DoEvents = TApplication.ProcessMessages
 
DoEvents = TApplication.ProcessMessages
  
<syntaxhighlight>
+
<syntaxhighlight lang=pascal>
 
var
 
var
 
   app: TApplication;
 
   app: TApplication;
Line 225: Line 266:
 
While the ''OutputDebugString'' printing the number to ''Event Log'', you may do any events with Form without ''Freezing'' except when you close the form, you must wait the loop until finished.
 
While the ''OutputDebugString'' printing the number to ''Event Log'', you may do any events with Form without ''Freezing'' except when you close the form, you must wait the loop until finished.
  
== VB commands, which are not present in fpc/Lazarus ==
+
== VB commands, which are not present in FPC/Lazarus ==
Split - fpc and Lazarus have no native function to split a string into a string array. [http://lazarus-ccr.sourceforge.net/docs/rtl/classes/tstrings.html TStrings] could be used instead of a string array, in case that the string separator is a '''character'''.  
+
 
 +
Split - FPC and Lazarus have no native function to split a string into a string array. [http://lazarus-ccr.sourceforge.net/docs/rtl/classes/tstrings.html TStrings] could be used instead of a string array, in case that the string separator is a '''character'''.  
  
Join - fpc and Lazarus have no native function to join string arrays.
+
Join - FPC and Lazarus have no native function to join string arrays.
  
 
== Debugging ==
 
== Debugging ==
 +
 
Lazarus IDE has no Instant panel.
 
Lazarus IDE has no Instant panel.
  
Line 309: Line 352:
 
| &nbsp; //
 
| &nbsp; //
 
| &nbsp; End of line [[Comments|Comment]] (only one line comment) &nbsp;
 
| &nbsp; End of line [[Comments|Comment]] (only one line comment) &nbsp;
 +
|-
 +
| &nbsp; Exit For &nbsp;
 +
| &nbsp; Break
 +
| &nbsp; Interrupt execution of a loop &nbsp;
  
 
|}
 
|}
 
 
 
 
  
  
Line 333: Line 376:
 
|-
 
|-
 
| &nbsp; Short  
 
| &nbsp; Short  
| &nbsp; [[SmallInt]]
+
| &nbsp; [[Smallint|SmallInt]]
 
| &nbsp; 16-bit
 
| &nbsp; 16-bit
 
| &nbsp; -32768 .. 32767 &nbsp;
 
| &nbsp; -32768 .. 32767 &nbsp;
Line 378: Line 421:
  
 
=== String functions ===
 
=== String functions ===
 +
 
{| class="wikitable"
 
{| class="wikitable"
 
! VB !! [[Pascal]] !! Remark
 
! VB !! [[Pascal]] !! Remark
Line 417: Line 461:
  
 
== Component prefixes ==
 
== Component prefixes ==
 +
 
There is a [http://kodu.ut.ee/~jellen/delphi/cs.html#Components_Instance list of component prefixes] for Delphi, which can be used in Lazarus. Using them might provide better code readability.
 
There is a [http://kodu.ut.ee/~jellen/delphi/cs.html#Components_Instance list of component prefixes] for Delphi, which can be used in Lazarus. Using them might provide better code readability.
  
Line 422: Line 467:
  
 
== Arrays of controls ==
 
== Arrays of controls ==
 +
 
Unlike in VB6 and like in VB.NET arrays of controls cannot be created statically (trough the IDE), and they can be created only dynamically.
 
Unlike in VB6 and like in VB.NET arrays of controls cannot be created statically (trough the IDE), and they can be created only dynamically.
  
 
Example, creating 6 buttons above each other:
 
Example, creating 6 buttons above each other:
  
<syntaxhighlight>
+
<syntaxhighlight lang=pascal>
 
procedure TForm1.FormCreate(Sender: TObject);
 
procedure TForm1.FormCreate(Sender: TObject);
 
var
 
var
Line 442: Line 488:
 
end;   
 
end;   
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
 +
== Visual Basic to Delphi (Pascal) Converters ==
 +
 +
* https://www.marcocantu.com/tools/vb2delphi.htm
 +
* https://cc.embarcadero.com/item/17064
  
  
 
[[Category:Rosetta Stone]]
 
[[Category:Rosetta Stone]]
 +
[[Category:FPC]]

Latest revision as of 07:35, 30 August 2021

Overview

This wiki page has been created to help you if you are switching from Visual Basic to Free Pascal (the Pascal dialect and compiler used by Lazarus). It is not meant to convince you that Lazarus is better than VB (or vice versa). Although VB and Pascal have superficial similarities these two languages differ greatly. Since VB programmers beginning to use Pascal face immediate difficulties in trying to do things which in VB have nice syntax that Pascal does not provide, we focus here on those differences.

Comparison and assignment of values

Values in Pascal are compared using the = operator.

Values in Pascal are assigned using the := operator (there is a : added).

For example:

if a = 1 then b := 2;

Beginning and ending statements

Blocks of Pascal code have no distinguishing end statements for functions, procedures, loops, etc. Pascal needs only begin and end. You can easily add a comment manually following end statements to clarify which named routine corresponds to this particular end;.

For example:

for i := 0 to 100 do
begin
   ...
end; // for i do

Variables

Declaring variables

In Pascal all variables have to be declared before use, and you have to make the declarations in a special var section which must precede the code that makes use of the variable. You cannot declare a new variable in the middle of code.

For example:

procedure VarDecl;
var
  MyVar1: string;
  Myvar2, MyVar3: integer; //Multiple variables can be declared on the same line.
begin
  WriteLn('Print something');
  var MyVar4: string = 'else'; // This declaration is not allowed here - it must be moved three lines above to the var section
  WriteLn('Print something ', MyVar2);
end; //VarDecl

Local variables do not get initialized upon declaration. They get random value (whatever value happen to be on the stack where they landed). Global variables are initialized to zero.

To initialize a local variable upon declaration the following syntax can be used in procedures and functions only.

var
  MyVar1: string  = '';
  MyVar2: integer = 0;

Types of variables

Besides the variables known in VB, Free Pascal supports unsigned integers. You should pay special attention not to mix them with signed integers.

Loops

Free Pascal has four kinds of loops.

for... do...

while... do

repeat... until

for.. in..

For... do...

This is quite similar to the For.. Next loop in VB, but more limited in syntax. The following restrictions apply in Pascal:

1. A for loop counter must be an integer (it cannot be a floating point type).

2. There is no Step property. To emulate the VB Step syntax you have to introduce a second counter variable yourself.

3. To decrement the value of the loop counter from a positive value, you use the keyword DOWNTO in place of TO.

For example:

procedure ForLoop;
var
  i: integer;
begin
  for i := 50 downto 0 do
  begin
     ...
  end; // for i
end.   // procedure ForLoop

4. In Lazarus it is possible to loop down when the index is a byte, which is not possible in VB6.

procedure ForLoop;
var
  i: byte;
begin
   for i := 200 downto 195 do
   begin
      ShowMessage (IntToStr (i));
   end;
end;

5. The value of the counter (i in the example above) cannot be changed programmatically inside the loop. Attempting to do so will throw a compiler error. Instead one could use Continue to skip execution of a loop:

procedure ForLoop;
var
  i: integer;
begin
  for i := 0 to 5 do
  begin
    if i=2 then Continue; //Following part of the loop will not be executed
    ShowMessage (IntToStr (i));
  end; // for i
end.   // procedure ForLoop

6. In order to interrupt execution of a loop one could use Break.

procedure ForLoop;
var
  i: integer;
begin
  for i := 0 to 5 do
  begin
    if i=2 then 
    begin
      ShowMessage (IntToStr (i));
      break;
    end; //if
  end; // for i
end.   // procedure ForLoop

Functions and procedures

Output of functions is supplied as:

Result:=Value

Note that Result:= does not act as Return. Function will not exit after assigning it.

One should use

exit(Value)

instead.

Visibility

In FPC a function or a procedure cannot see another one, which is written after it.

Example:

procedure Proc1;
begin
  Proc2;  //This is not possible
end;

procedure Proc2;
begin
  Proc1; //This is possible
end;

To enable visibility, disregarding writing order, functions and procedures have to be declared.

unit MyUnit;
...
procedure Proc1;
procedure Proc2;
...
implementation

procedure Proc1;
begin
  Proc2;  //This is possible now
end;

procedure Proc2;
begin
  Proc1; //This is possible
end;

Using default parameters in functions and procedures

In Pascal functions and procedures it is possible for parameters to automatically take default values. However, in the parameter list the parameters that might take default values must be declared as a contiguous list at the end of the parameter declaration part. Also, when a routine with default parameter(s) is subsequently called in your code, you can only specify non-default values beginning at the first parameter which would otherwise take a default value. You cannot specify a non-default value for a later parameter, if there are preceding parameters you have to specify values for which have not also been specified explicitly in the function or procedure call.

For example:

If a procedure is declared (correctly) as follows with two default parameters:

procedure SampleProc(parm1: integer; parm2: string= 'something'; parm3:Boolean= True);
begin
end. //proc

it is not possible to call SampleProc as in VB like this:

  SampleProc(5,,False);

This will produce a compiler error.

When calling a procedure (or function), if you specify a parameter which has a default value, you must also specify all parameters that have a default value that are in front of it. So, in the example above if you want the third parameter to be False, then you must also specify the value of second parameter.

These are valid calls:

  SampleProc(5,'something',False);

  SampleProc(5,'nothing');

  SampleProc(5,'');

  SampleProc(5);

Dynamic arrays

In Pascal the minimum index of a dynamic array is 0, i.e. MyArray (1) will return the second elements of an array named MyArray.

Arrays are resized using:

setlength (MyArray, NewDimension);

SetLength does not clear the array, i.e. it acts like ReDim Preserve, not like ReDim.

Translation of some commonly sought commands

DoEvents = TApplication.ProcessMessages

var
  app: TApplication;
  i: integer;
begin
  app := TApplication.Create(nil);

  for i := 0 to 1000000 do
  begin
    app.ProcessMessages; // Handling process messages.
    OutputDebugString(PChar(IntToStr(i)));
  end
end;

While the OutputDebugString printing the number to Event Log, you may do any events with Form without Freezing except when you close the form, you must wait the loop until finished.

VB commands, which are not present in FPC/Lazarus

Split - FPC and Lazarus have no native function to split a string into a string array. TStrings could be used instead of a string array, in case that the string separator is a character.

Join - FPC and Lazarus have no native function to join string arrays.

Debugging

Lazarus IDE has no Instant panel.

In order to debug in Windows the dos prompt windows shall be enabled the following way: Lazarus IDE-> Main menu -> Project -> Project options... -> Compiler Options -> Config and Target -> uncheck Win32 gui application (-WG)

In Linux the console invokes itself.

Then the write and writeln commands can be used to print debug messages.

Compiler might give some more information if the following items are checked in the IDE main menu -> Project -> Project Option -> Compiler Option -> Debugging -> -Ci, -Cr, -Co, -St, -Cr, -Sa.

Substitution tables

VB Pascal Remark
  =     :=   Becomes  
  =     =   Equal
  /     /   Float Division
  \     Div  
  &     +   String concatenation
  MOD   Mod   Modulo operation
  <>     <>   Not equal  
  Not     Not  
  And     And  
  Or     Or  
  Xor     Xor  
  >>     Shr   bit shift right  
  <<     Shl   bit shift left  
  New line     ;   In Pascal lines end with the ; character not by a new line.  
  _       No symbol is required for wrapping a line and new line symbols are acceptable within it.  
  '     //   End of line Comment (only one line comment)  
  Exit For     Break   Interrupt execution of a loop  


VB type Pascal type Size (bits) Range Remark
  SByte     Shortint   8-bit   -128 .. 127  
  Byte     Byte   8-bit   0 .. 255  
  Short   SmallInt   16-bit   -32768 .. 32767  
  Char     Word   16-bit   0 .. 65535  
  Integer     Integer   32-bit   -2147483648..2147483647    
  UInteger     Cardinal   32-bit   0 .. 4294967295  
  Single     Single   32-bit   1.5E-45 .. 3.4E+38     Decimal delimiter in both languages, applied in source code is dot on the line.  
  Double     Double   64-bit   5.0E-324 .. 1.7E+308  
  Boolean     Boolean     True False

String functions

VB Pascal Remark
  &     +   String concatenation
  Format(item, formatstring)   format(formatstring, items)  
  left(some_string,n)   leftstr(some_string, n) or copy (some_string,1,n)  
  Len(some_string)   length(some_string)  
  LCase(some_string)   lowercase(some_string)  
  Mid(some_string, startpos, numChars)   copy(some_string, startpos, numChars)  
  StrReverse(string)   See Palindrome  
  UCase(some_string)   uppercase(some_string)  

Component prefixes

There is a list of component prefixes for Delphi, which can be used in Lazarus. Using them might provide better code readability.

It is also usual to start the name of a type with the capital letter T.

Arrays of controls

Unlike in VB6 and like in VB.NET arrays of controls cannot be created statically (trough the IDE), and they can be created only dynamically.

Example, creating 6 buttons above each other:

procedure TForm1.FormCreate(Sender: TObject);
var
  i: Integer;
  btnArray: array of TButton;
begin
  SetLength(btnArray, 6);
  for i := 0 to 5 do
  begin
    btnArray[i]        := TButton.Create(Self);
    btnArray[i].Left   := 0;
    btnArray[i].Top    := i * 30;
    btnArray[i].Parent := Self;
  end;
end;

Visual Basic to Delphi (Pascal) Converters