Personal C Sharp         by    famsoft.org

Home | Demonstrative Examples | PC# Methods | PC# Reference | Links

Examples on Web Page Development

This section is still under construction

                                 DEMONSTRATIVE EXAMPLES
                                 ======================
                                  WEB PAGE DEVELOPMENT
                                  ===================
HTML ELIMINATION:
The asp.net has added a great enhancement to web development by allowing you to do a major
part of your web development programatically. The asp.net page files which use the
extension (.aspx) are not sent by the server to the client's browser directly. They actually
run at the server where an HTML file is generated and sent to the browser instead.
 
Unfortunately, html has not been eliminated entirely. The asp.net web files are required
to contain html tags even if the page was entirely developed using asp.net code.
 
In order to simplify things further while maintaining all the added enhancement and power,
we have developed a software which allows you to write your entire web page file in C#
with absolutely no html. When you add all the simplicity of using PC#'s tools and methods
to the elimination of HTML, you come up with the easiest and most pleasant web development
ever.
 
HOW DOES IT WORK?
 
Here is how it is done:

(1) You write a code file (.cs) as usual which extends class (pasp) In that file,
you supply PC# software with every item which you like to include into the web page and
where you like it to be using the same simple methods which you have been using to set
windows Form controls. The items are set into table cells. Then the tables are set into
the cells of larger tables. This Continues until we end with one large table of the same
size as the page (the root table).  We use the keyname "tb0" for the root table which
contains the entire page data.
 
(2) Now it is time for the (.aspx) file which the browser requires. We need a file which
extends (inherits) the code file above and contains in its html section only one control
which is the root table.  So the (.aspx) files for all pages are the same. The only
difference between one file and another is in the name of the code file it extends.
 
This makes creating the (.aspx) file a repeated job which you need not to do. You create
the code file only then use the tool (pcw) to generate the (.aspx) file.
 
EXAMPLE A: In this example we are going to develop a web page which contains the table
heirarchy necessary for the following several examples. As you can see the page contains
5 empty tables. The top table will contain the page title, an icon and the pages' index.
The second and third  tables will be used to show two new features in each example. The
fourth and fifth tables will display data coming back from the server in response to
events generated by the user at tables 2 and 3 respectively.
=========================================================================================
public partial class a:pasp {                         // Since class name is (a), it must
                                                      // be saved into a file named a.cs
  public override void init() {                       // This is the usual init() method
    base.init();                                      // Initialize pasp class.
  }
  public override void setup() {                      // This is the usual setup method
    //---------------------------------- Page Contents -----------------------------------
      cns="";                                         // tb0 has no container since it is
                                                      // mounted directly on the page.
      cs="tb0";cls="S9g8";fns="trb12";wm("i");        // tb0's installation parameters
    //---------------------------------- tb0's Contents ----------------------------------
      cns="tb0";                                      // Container=tb0 for next 5 tables
      cs="tb1";j=0;k=0;i=2;lf=760;of=100;cls="S9p7";fns="trb12";jd=5;ds="n";wm("i");
      cs="tb2";j=0;k=1;lf=380;of=250;cls="S9p7";fns="trb12";jd=5;wm("i");
      cs="tb3";j=1;k=1;lf=380;of=250;cls="S9p7";fns="trb12";jd=5;wm("i");
      cs="tb4";j=0;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
      cs="tb5";j=1;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
    // Tables will not show up unless they contain something. So, we'll install a literal
    // control into each table containing it's keyname.
    //---------------------------------- tb1's Contents -----------------------------------
      cns="tb1";                                      // tb1 contains next control(s)
      cs="lt1";cis="tb1";wm("i");                     // Literal control containing text
    //---------------------------------- tb2's Contents -----------------------------------
      cns="tb2";
      cs="lt2";cis="tb2";wm("i");
    //---------------------------------- tb3's Contents -----------------------------------
      cns="tb3";
      cs="lt3";cis="tb3";wm("i");
    //---------------------------------- tb4's Contents -----------------------------------
      cns="tb4";
      cs="lt4";cis="tb4";wm("i");
    //---------------------------------- tb5's Contents -----------------------------------
      cns="tb5";
      cs="lt5";cis="tb5";wm("i");
  }
  public override void update() {
    setup();                                          // Execute method setup()
    MakePage(table);                                  // Make the page with tb0 containing
  }                                                   // all its contents.
}
=========================================================================================
HOW TO WRITE THE PROGRAM? Use NotePad. Since "a" has been chosen to
be the name of the class, save the program into a file named "a.cs".
 
HOW TO GENERATE THE WEB (.aspx) FILE? From Command mode, type: 'pcw a' and hit [ENTER].
This should generate the file "a.aspx".
 
HOW TO RUN THE PROGRAM? Type the page's address into your browser's address line and hit
[ENTER]. You may do that locally or using a computer anywhere accross the web. The
page address is in the form:
 
DomainAddress/ApplicationFolder/AspxFile
 
As an example, if your application folder path is: "c:\inetpub\wwwroot\MyFolder", the
page address would be:
 
DomainAddress/Myfolder/a.aspx
=========================================================================================
TUTORIAL:
(1) Your class extends class "pasp". Class "pasp" extends class "System.Web.UI.Page" which
allows it to access all nesessary asp.net software for the page in addition to allowing
you to use mostly all the PC# methods which simplify your programming tasks.
 
(2) One method which you cannot find in class (pasp) is method cm(). Method cm() which is
included into class (pcs) helps you in developing controls which are mounted on window
forms. This method has been replaced with method wm() which is very similar in its
operation to method cm() except that it helps you in developing web controls.
 
(3) Method setup() works the same as it used to do with window forms with few exceptions:
    a) It does not run automatically when your class is initialized. It stays unused until
       Your program calls it from method update() when a specific event takes place.
    b) Controls are not placed using absolute positioning. They are placed into table
       cells. So (j,k) no longer mean the position of a control in pixels, they now mean
       the order of the starting column and row which the control occupies within its
       containing table. Similarly, (i,o) mean the number of columns and rows occupied by
       the control instead of (width,height) in pixels.
    c) Finally, each control is set by calling method wm("i") instead of calling cm("i").
 
(4) Method update() is called each time an event takes place. Whenever a control is
    activated, method update is called with the keyname of the activated control assigned
    to (cs).  However, not all events are caused by a control being activated.
 
    The first event which method update is called for, is the "Page Load" event. It is
    generated when the page is ready to load. The keyname variable (cs) is assigned the
    value "pl" before method update() is called. However, we did not check this value
    in this example since this is the only event which is expected to be received.
 
    When method update() was told that the page is ready to load, it called method setup()
    to read control parameters then it called method MakePage() to load all controls and
    their table containers into the root table "tb0", then load "tb0" into the table
    container which is declared in the ".aspx" file.
 
INSTALLING CONTROLS INTO THEIR CONTAINERS:
 
All the controls of this example are of type (Table).  We want to install tables (tb1:tb5)
into a specific locations in table (tb0)
 
It may sound like a very easy task, but in many cases it is not. What makes this job not
too easy is the conflict between two intelligant entities, you and the browser. You assume
that you know what you are doing and expect the browser to set the table columns and rows
exactly the way you want them to be. The browser assumes that you may not be understanding
what you are doing so it should do things for you in order to improve the look of your
table.
 
Here is what the browser tries to do:
 
(1) If you set the size of your table in pixels, it tries to respect your setting as long
    as the size is equal or more than the size which table contents require. If not, it
    neglects your setting and sizes the table as it sees necessary.
 
(2) It does not make all columns of the table equal in width or all rows equal in height.
    It checks to see the widest object installed into the column (anywhere in the table)
    and makes the column wide enough to contain that object. It applies the same logic
    when it sets row sizes too.
 
(3) It does not display an empty table even if you specify its width and height in pixels.
 
And here is what you can do to get around this problem:
 
(1) Always apply the simplest logic possible in setting your controls.
 
(2) If you get an unexpected layout of your controls do the following:
    a) Make the container table grids show by adding (ib=true) to the table's setup
       parameters. This should give you a clearer picture of what is happening.
    b) Locate the widest control in each column and the tallest control in each row. They
       are the keys to fixing the problem. Readjusting their sizes can change the entire
       layout of the table. Sizes of most controls can be changed by changing the font
       size of the text they contain.
 
Now let us return to the example. Here is how you can determine the number of rows and
columns fot tb0:
 
(1) Locate the row which contains the largest number of controls horizontally. The number
    of columns necessary is equal to the number of controls at that row which is 2.
 
(2) Locate the column which contains the largest number of controls vertically. The number
    of rows necessary is equal to the number of controls at that column which is 3.
 
Here are some comments on the setup data:
 
(1) For the root table (tb0) we did not set values for (j,k,i or o) since it is the root.
    However, these values are necessary for all other controls.
 
(2) If the control should occupy one column we suould supply (i=1), however since this is
    the default we can just assign no value to (i) Method wm("i") changes (i=0) to (i=1)
    internally. Same logic applies to (o).
 
(3) For (tb1): (j=0;k=0;i=2;) means that it occupies two columns and one row (since o is
    not assigned a value) and that the coordinates of the first table cell it occupies
    are (0,0).
 
(4) For (tb2): (j=0;k=1;) Since (i,o) are not assigned values, it occupies one column and
    one row, The coordinates of the first table cell it occupies are (0,1).
 
(5) For (tb3): (j=1;k=1;) Since (i,o) are not assigned values, it occupies one column and
    one row. The coordinates of the first table cell it occupies are (1,1).
 
(6) We have assigned values to (lf,of) for all tables except the root. These values set
    the table sizes (horizontally, vertically) in pixels. Not specifying size for (tb0)
    causes no problem since as mentioned above, the browser will make it large enough to
    contain all the tables which have been installed into it.
 
(7) Colors and fonts have been set as usual. (jd=5) means frame the table with a 5 pixels
    wide frame. It makes them look nice, however you can remove it if you don't like
    frames.
 
(8) As you must know, after method wm("i") completes the installation of each control, it
    resets all parameters. The only exception to this rule is the container name (cns)
    This allows you to assign a value to (cns) one time only before installing a group of
    controls into a new container.
=========================================================================================

exa.jpg

EXAMPLE 1: Now, let us make our first web page. We need to do the following:
(1) Create Application title and install it into the top container (tb1)
(2) Install a business logo at the right side of (tb1)
(3) Create a navigation index at the bottom of (tb1) which allows the user to browse
    through the website.
(4) Remove the pink paint of (tb2) and tile it with the image "flower.jpg instead".
(5) Install a hyper link into (tb2) which the user can click on to order flowers.
(6) Create a table and install it into (tb3).
=========================================================================================
public partial class pg1:pasp {
 
  public override void init() {
    base.init();
  }
  public override void setup() {
    //---------------------------------- Page Contents -----------------------------------
      cns="";                                         // tb0 Container="" since it's
                                                      // mounted directly on the page.
      cs="tb0";cls="S9g8";fns="trb12";wm("i");        // tb0 installation parameters
    //----------------------------------- tb0 Contents -----------------------------------
      cns="tb0";                                      // Container=tb0 for next tables
      cs="tb1";j=0;k=0;i=2;lf=760;of=100;cls="S9p7";fns="trb12";jd=5;ds="n";wm("i");
      cs="tb2";j=0;k=1;lf=380;of=250;ims="flower.jpg";fns="trb12";jd=5;wm("i");
      cs="tb3";j=1;k=1;lf=380;of=250;cls="S9p7";fns="trb12";jd=5;wm("i");
      cs="tb4";j=0;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
      cs="tb5";j=1;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
                                                      // tb2 is tiled with image, all
                                                      // others painted with lt pink color
    //----------------------------------- tb1 Contents ----------------------------------
      cns="tb1";                                      // tb1 is divided into 4 col,3 rows
      cls="r0";fns="trb24";ds="c";os="Web Page Development";wm("dp");
      cs="lt1";j=0;k=0;i=3;ds="c";wm("i");            // Insert Ap title into (cis) Create
                                                      // Literal control, make cs its text
      cs="lt2";j=0;k=1;i=3;cis="Example Number One";ds="c";fns="trb12";wm("i");
                                                      // Create (lt2) containing Pg title
      cs="hl0";j=0;k=2;cis="Example Number One";fns="trb12";cls="s9b0";ds="c";
               urs="
http://www.microsoft.com";wm("i");// Create Hyper text control which
                                                      // displays page 1 when clicked.
      cs="hl1";j=1;k=2;cis="Example Number Two";fns="trb12";cls="s9b0";ds="c";
               urs="
http://www.microsoft.com";wm("i");// Do same for page 2
      cs="hl2";j=2;k=2;cis="Example Number Three";fns="trb12";cls="s9b0";ds="c";
               urs="
http://www.microsoft.com";wm("i");// Do same for page 3
      cs="im0";j=3;k=0;i=1;o=3;ds="e";lf=190;of=90;ims="images\\icon.jpg";jd=5;wm("i");
                                                      // Image, scaled to (190,90) pixels
    //----------------------------------- tb2 Contents ----------------------------------
      cns="tb2";                                      // tb2 is made of 1 col, 1 row
      urs="
http://www.microsoft.com";os="To order flowers, Click Here";
      cls="y0";fns="trb16";wm("a");wm("c");           // Create hyper text link in (cis)
      cs="lt3";ds="n";wm("i");                        // Create (lt3), make (cis) its txt
    //----------------------------------- tb3 Contents ----------------------------------
      cns="tb3";                                      // tb3 is made of 1 col, 1 row
      cls="G5";fns="trb14";ds="c";os="Flower Prices";wm("dl");
                                                      // Insert table's title into (cis)
                                                      // in addition to all coming html:
      i=5;o=65;wm("to");                              // open table,bordr=5, width=65%
      OS[0]="Collection";OS[1]="Price";wm("th");      // Make a 2 column header
      OS[0]="Mixed Tulips";OS[1]="$25.00";wm("td");   // and 3 data rows. All the html
      OS[0]="Color Roses";OS[1]="$30.00";wm("td");    // generated is inserted into (cis)
      OS[0]="Pink Lilies";OS[1]="$50.00";wm("td");    //
      wm("tc");                                       // Add closing table html tags and
      wm("c");                                        // closing tags for other html ones
      cs="lt4";wm("i");                               // Create (lt4), make (cis) its txt
    //----------------------------------- tb4 Contents ----------------------------------
      cns="tb4";                                      // tb4 is made of 1 col, 1 row
      cs="lb10";cis="Server Response: ";wm("i");      // Create (lt10), cis=its txt
    //----------------------------------- tb5 Contents ----------------------------------
      cns="tb5";                                      // tb5 is made of 1 col, 1 row
      cs="lb11";cis="Server Response: ";wm("i");      // Create (lt11), cis=its txt
  }
  public override void update() {
    setup();                                          // Execute method setup()
    MakePage(table);                                  // Make the page
  }                                                   // containing all controls
}
=========================================================================================
TO LEARN HOW TO WRITE THE PROGRAM, GENERATE THE (.aspx) FILE AND TO RUN IT, See Example A
=========================================================================================
TUTORIAL: Here is a description of the controls used in this example:
 
LITERAL CONTROLS: Literal controls are made of pure HTML. As mentioned before, you don't
have to know HTML, method wm() does the job for you. HTML allows us to write any phrase,
using any color, font and indention as we like. It also allows us to make hyper links and
tables.
 
It is good to know that using literal controls is not essential in many cases. We can also
write a phrase using the Label Control, and we can make a hyper link using the HyperLink
control.
 
The Literal Control's parameter which is assigned the HTML is its label (cis). Normally we
use two lines in the setup() method for each Literal control. The first line creates (cis)
and the second line creates all other parameters and calls wm("i").
 
Method wm() contains several modes which create the HTML for you, the display mode wm("d")
is one of them. Where does it display its output? The answer is two places. It can write
the HTML into an HTML file which is not what we need to get into now. The other one is
the string (cis)  It keeps adding it's text output to (cis) each time it's called.
Let us now analyze the Literal Controls used in the example:
 
(1) lt1: The top line of (lt1)'s setup was:
 
      cls="r0";fns="trb24";ds="c";os="Web Page Development";wm("dp");
 
We have called method wm() at mode "dp". This mode starts a new paragraph then displays
the wanted text there. The wanted text is the text assigned to (os). We have also told the
method to use pure red color, TimesRoman, bold, size 24 font and to display the text at
the center.
 
Method wm("dp") has generated several HTML tags to do all the text setup in addition to
the text itself. All the HTML generated is concatenated together and added to (cis) If we
then call the same method to display a new paragraph, the new HTML will also be
concatenated to the current one into (cis)
 
Then the second line came which was:
 
      cs="lt1";j=0;k=0;i=3;ds="c";wm("i");
 
This says create a Literal control which occupies all the 3 columns of (tb1) starting at
cell(0,0) and centered into the 3 table cells.
 
(2) lt2: The label for this one has been a simple short text so its setup was made in
         one line
 
(3) lt3: Here is the setup section for this Literal control:
 
      urs="http://www.microsoft.com";os="To order flowers, Click Here";
      cls="y0";fns="trb16";wm("a");wm("c");           // Create hyper text link in (cis)
      cs="lt3";ds="n";wm("i");                        // Create (lt3), make (cis) its txt
 
The top two lines have created (cis). Method wm("a") was used to generate the HTML "anchor"
tag which makes the Hyperlink. Method wm("a") requires the clickable text assigned to (os)
and the "URL to go to", assigned to (urs) That was done in the top line. The color and
font to display the clickable in  have been also supplied. All generated HTML have been
loaded into (cis) automatically by method wm("a").
 
The third line has created the Literal control stating that it should be placed at the top
(north) of its cell.
 
(4) lt4: This literal control has required a complex label. The first section of the
    label was the table's title which has been created using the code:
 
      cls="G5";fns="trb14";ds="c";os="Flower Prices";wm("dl");
 
Every thing here is similsr to the code used for (lt1) except that we did not want to
write the title at a new paragraph, we wanted to display it directly then move to next
line instead, so we used method wm("dl")
 
Next to that, we wanted to add to (cis) the HTML necessary to create a table. Here is how
it was done:
 
      i=5;o=65;wm("to");                              // open table,bordr=5, width=65%
      OS[0]="Collection";OS[1]="Price";wm("th");      // Make a 2 column header
      OS[0]="Mixed Tulips";OS[1]="$25.00";wm("td");   // and 3 data rows. All the html
      OS[0]="Color Roses";OS[1]="$30.00";wm("td");    // generated is inserted into (cis)
      OS[0]="Pink Lilies";OS[1]="$50.00";wm("td");    //
      wm("tc");                                       // Add closing table html tags and
      wm("c");                                        // closing tags for other html ones
 
The first step is calling wm("to") to generate necessary tags for a table with border
width of 5 pixels and a total width of 65% of its container's width.
 
Next step is to write the table header. All column titles are assigned to OS[] before
calling wm("th").
 
Next is to enter all data rows in the same manner.
 
The last step in creating a table is to close it using method wm("tc") to generate closing
tags for all open table tags.
 
As a precaution, we called wm("c") which checks to see if the generated HTML contains an
HTML tag of any type without its matching closing one. If any was found, it adds the
necessary closing tag.
 
HYPERLINK CONTROLS: The Hyperlink control functions the same as the hyperlinks generated
by the Literal control except that it puts the clickable text into a box which makes it
more suitable for making an index to navigate a site with. It can also be turned into a
clickable image if you supply the image's URL assigned to (ims).
 
IMAGE CONTROLS: This control makes it easy to place an image at any location you choose
in the page. The image's URL is supplied to (ims).  You can scale the image to any size
you want if you assign the wanted (width,height) to (lf,of) respectively.
 
LABLE CONTROLS: They display text similarly to Literal controls except that the text is
inserted into a box.
 
MORE ABOUT (cis): A Literal control is not the only control which uses (cis) as its label.
There are many other controls which do the same. Fortunately you can use the HTML
generating modes of method wm() to display them using any color, font or indention just
like you do with literal controls.
=========================================================================================

ex01a.jpg


                                     MASTER PAGES
                                     ============
 
The ASP.NET 2.0 includes several new features like master pages, custom controls and web
parts which enhance web development. PC# must do her best to implement as many useful
features as possible, however PC# must never go beyond what it is for which are:
 
(1) Making programming as easy and simple as possible.
(2) Performing tasks with the shortest possible code.
(3) Things to memorize must be reduced to minimum.
 
Making you able to write the most powerful web page program possible while abiding with
the rules above requires some careful decision makings.
 
The web page design is modular. This is accomplished by using table containers for each
of its sections. This by itself makes each section a reusable web part without additional
programming complexity.
 
Normally most pages of a website contain common sections like a header, a navigation index
and/or a footer. The page you have created in the previous example shows that clearly.
 
The top table (tb1) with everything it contains is going to be common for all the pages
which we are going to make. Tables tb4 and tb5 are also common. Including these common
parts into every page class we write is a waste of time and resources. The better choice
is to create a master page class which includes the common parts alone and make it execute
together with each page class.
 
In order to create a master page, your class must extend class "System.Web.UI.MasterPage"
instead of class "Page" (Your class extends class "Page" when it extend "pasp")  The master page
file extension should be ".master" instead of ".aspx". Also the ".aspx" files for the
content pages which are generated for you by the tool "pcw" will need to be modified.
 
In order to avoid the master page creation complexity, we use a simpler way to do the same
job.  Our master page code file is the same as any page code file. Instead of using tool
"pcw" to generate the matching ".aspx" file, we use tool "pcwm" which compiles the master
page code file and saves the resulting ".dll" file into the "Bin" subdirectory.
 
The master page class extends class "pasp" which extends "Page". All your page classes will
extend the master class. This means that you have the
following class heirarchy:
 
Page ---> Class pasp ---> Your Master Page Class ---> Your page classes
 
Both "pasp" and the master page classes are stored into the "Bin" subdirectory of your
application's directory in the form of ".dll" files.  Your page classes are kept into your
application directory in the form of ".cs" files.
 
You may have more than one master class although this is not recommended. If you do, you
must make them extend one another. The deepest of them should extend class (pasp) and the
top one should be extended by the page classes.
 
Now we are going to split the class of example 1 into two classes. The first class will be
named "master1" and will include the creation of all the table containers and the population
of tables tb1,tb4 and tb5. The second class will keep the name "pg1" and will include the
population of tables tb2 and tb3 only in addition to method update() which handles all
events of the page.
 
Class "master1" will be extended to include hyperlinks for 10 pages and will also include
a method named PageNumber() which all page classes will be calling in order to make their
page numbers show at the top of the page. Table (tb2)'s background will be painted the same
as all other tables instead of being tiled with an image. Class "pg1" will populate (tb2)
differently in order to maintain the same look despite that change.
 
THE MASTER CLASS:
 
public partial class master1:pasp {                // The master class must extend pasp
                                                   // or a deeper master class
  public override void setup() {
  //---------------------------------- Page Contents -----------------------------------
    cns="";                                         // tb0 Container="" since it's
                                                    // mounted directly on the page.
    cs="tb0";cls="S9g8";fns="trb12";wm("i");        // tb0 installation parameters
  //----------------------------------- tb0 Contents -----------------------------------
    cns="tb0";                                      // Container=tb0 for next tables
    cs="tb1";j=0;k=0;i=2;lf=760;of=100;cls="S9p7";fns="trb12";jd=5;ds="n";wm("i");
    cs="tb2";j=0;k=1;lf=380;of=250;;cls="S9p7";fns="trb12";jd=5;wm("i");
    cs="tb3";j=1;k=1;lf=380;of=250;cls="S9p7";fns="trb12";jd=5;wm("i");
    cs="tb4";j=0;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
    cs="tb5";j=1;k=2;lf=380;of=50;cls="S9p7";fns="trb12";jd=5;wm("i");
  //----------------------------------- tb1 Contents ----------------------------------
    cns="tb1";                                      // tb1 is divided into 4 col,3 rows
     cls="r0";fns="trb24";ds="c";os="Web Page Development";wm("dp");
    cs="lt01";j=0;k=0;i=10;ds="c";wm("i");          // Insert Ap title into (cis) Create
                                                    // Literal control, make cs its text
    cs="lt02";j=0;k=1;i=10;cis="Insert Page's Number Here";ds="c";fns="trb12";wm("i");
                                                    // Create (lt02) containing Pg title
    cs="hl01";j=0;k=2;cis="Page 1";fns="trb12";cls="s9b0";ds="c";urs="pg1.aspx";wm("i");                                                   
    cs="hl02";j=1;k=2;cis="Page 2";fns="trb12";cls="s9b0";ds="c";urs="pg2.aspx";wm("i");
    cs="hl03";j=2;k=2;cis="Page 3";fns="trb12";cls="s9b0";ds="c";urs="pg3.aspx";wm("i");
    cs="hl04";j=3;k=2;cis="Page 4";fns="trb12";cls="s9b0";ds="c";urs="pg4.aspx";wm("i");
    cs="hl05";j=4;k=2;cis="Page 5";fns="trb12";cls="s9b0";ds="c";urs="pg5.aspx";wm("i");
    cs="hl06";j=5;k=2;cis="Page 6";fns="trb12";cls="s9b0";ds="c";urs="pg6.aspx";wm("i");
    cs="hl07";j=6;k=2;cis="Page 7";fns="trb12";cls="s9b0";ds="c";urs="pg7.aspx";wm("i");
    cs="hl08";j=7;k=2;cis="Page 8";fns="trb12";cls="s9b0";ds="c";urs="pg8.aspx";wm("i");
    cs="hl09";j=8;k=2;cis="Page 9";fns="trb12";cls="s9b0";ds="c";urs="pg9.aspx";wm("i");
    cs="hl10";j=9;k=2;cis="Page 10";fns="trb12";cls="s9b0";ds="c";urs="pg10.aspx";wm("i");
    cs="im00";j=6;k=0;o=3;ds="e";lf=190;of=90;ims="images\\icon.jpg";jd=5;wm("i");
                                                    // Image, scaled to (190,90) pixels
  //----------------------------------- tb4 Contents ----------------------------------
    cns="tb4";                                      // tb4 is made of 1 col, 1 row
    cs="lb00";cis="Server Response: ";wm("i");      // Create (lb00), cis=its txt
  //----------------------------------- tb5 Contents ----------------------------------
    cns="tb5";                                      // tb5 is made of 1 col, 1 row
    cs="lb01";cis="Server Response: ";wm("i");      // Create (lb01), cis=its txt
  }
  public void PageNumber(int pgno) {                // Page number insertion method
    cs="lt02";cis="Page Number "+pgno;wm("sl");     // Set the label of (lt02) to display
  }                                                 // the page number supplied.
}
=========================================================================================
Save this class into a file named "master1.cs"  Then, from Command Mode, type:
 
      pcwm master1    [ENTER]
=========================================================================================
THE PAGE CLASS:
public partial class pg1:master1 {                    // All page classes must extend the
                                                      // top of the master class heirarchy
  public override void init() {
    base.init();
  }
  public override void setup() {
      base.setup();                                   // Run setup() of master page first
    //----------------------------------- tb2 Contents ----------------------------------
      cns="tb2";                                      // tb2 is made of 1 col, 1 row
      urs="http://www.microsoft.com";os="To order flowers, Click Here";
      cls="S9";fns="trb16";wm("a");wm("c");           // Create hyper text link in (cis)
      cs="lt3";j=0;k=0;i=2;ds="n";wm("i");            // Create (lt3), make (cis) its txt
      cs="im2";j=0;k=1;ds="se";lf=180;of=200;ims="flower.jpg";wm("i");
      cs="im3";j=1;k=1;ds="sw";lf=180;of=200;ims="flower.jpg";wm("i");
    //----------------------------------- tb3 Contents ----------------------------------
      cns="tb3";                                      // tb3 is made of 1 col, 1 row
      cls="G5";fns="trb14";ds="c";os="Flower Prices";wm("dl");
                                                      // Insert table's title into (cis)
                                                      // in addition to all coming html:
      i=5;o=65;wm("to");                              // open table,bordr=5, width=65%
      OS[0]="Collection";OS[1]="Price";wm("th");      // Make a 2 column header
      OS[0]="Mixed Tulips";OS[1]="$25.00";wm("td");   // and 3 data rows. All the html
      OS[0]="Color Roses";OS[1]="$30.00";wm("td");    // generated is inserted into (cis)
      OS[0]="Pink Lilies";OS[1]="$50.00";wm("td");    //
      wm("tc");                                       // Add closing table html tags and
      wm("c");                                        // closing tags for other html ones
      cs="lt4";wm("i");                               // Create (lt4), make (cis) its txt
  }
  public override void update() {
    setup();                                          // Execute setup()
    MakePage(table);                                  // Make the page 
    PageNumber(1);                                    // Call master1 class's method to
  }                                                   // set page number
}
=========================================================================================
Create the ".aspx" file with the command  pcw pg1 and execute the page pg1.aspx file
exactly as you have been doing before.
=========================================================================================

ex01.jpg

                                INTERACTING WITH USERS
                                ======================
 
Interacting with user is done almost identically as it is done with window forms. PC#
receives all events then calls the update method of your class supplying it with the
keyname of the control where the event has occured assigned to (cs).
 
The first event received is the "Page_Load" event which occures when the page is ready
to be retrieved. Although this event is not generated by a control, PC# makes it
identifiable by assigning "pl" to (cs) before calling method update() when this event is
received.
 
When the user clicks a button, PC# receives this event, checks the button's identity and
assigns the button's keyname to (cs) then calls method update() of your class.
 
In method update(), you can get the latest update for any control by calling wm ("gu")
This allows you to know everthing the user has selected in the page. After analyzing
user selsections, you may like to send him/her a message back. You can do so by assigning
the message to the label (cis) of the Literal or Label control which the user expects to
receive your response at, then call method wm("su") to update the control with the new
label.
 
Example 2: In table 2, we are going to demonstrate how to receive the text which the user
has entered into a text field and send back a confirmation to the user.
 
In table 3, we are going to demonstrate how to create a clickable image.
=========================================================================================
public partial class pg2:master1 {                    // Page class extends master class
  public override void init() {
    base.init();
  }
  public override void setup() {
    base.setup();                                   // Run setup() of master page first
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                      // tb2 is made of 1 col, 2 rows
    cs="tf0";cis="Enter Your Name";j=0;k=0;ds="c";  // tf0 is centered into 1st row
            jf=20;cls="b0y0";fns="trbi12";wm("i");  // tf0 size is 20 chars.
    cs="bt0";cis="Submit";j=0;k=1;ds="c";           // bt0 is centered into 2nd row
             cls="r0g8";fns="trb12";wm("i");        // Its label is "Submit"
  //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                      // tb3 is made of 1 col, 1 row
    cs="hl3";ds="c";ims="pix.jpg";jd=5;             // Clickable image
           cis="Click Here";urs="
http://www.microsoft.com";cls="b0s9";wm("i");
  }
  //------------------------------------------------------------------------------------
  public override void update() {
 
    if(cs.Equals("pl")) {                           // If event is "Page_Load"
      setup();                                      // Execute setup()
      MakePage(table);                              // and Make the page
      PageNumber(2);                                // Calling master class's method
    }                                               // to display this page's number
    if(cs.Equals("bt0")) {                          // If event is: "bt0 clicked"
      cs="tf0";wm("gu");                            // Get update text of tf0 in (cus)
      cs="lb00";cis="You entered: "+cus;wm("sl");   // Modify lb00's text with server
    }                                               // response.
  }
}
=========================================================================================

ex02.jpg

                       USING VARIABLES IN WEB PAGE DEVELOPMENT
                       =======================================
 
All the variables which you declare in your web page class or PC# declares for you are
good for one trip only. This means that you can use them to prepare the page before it is
sent to the user, but after the user clicks a button and you like to work on the page
again, you cannot expect your variables to retain their values.
 
However, ASP.NET allows us to declare variables which retain their values. They are 3
types of variables which retain their values:
 
(1) Page Variables: Page variables retain their values over one page use only. This means
that if the user changes page, the variables are lost.
 
(2) Session Variables: Session variables retain their values over one Session. This means
that if the user changes page, the variables keep their values as long as the session has
not been terminated. If the user stays inactive for 20 minutes, the session terminates
and the variables are lost. The 20 minute limit is a default which can be changed.
 
(3) Application Variables: This is the most durable type (and also the costiest). They
keep their values as long as the application is running and this requires at least one
user to request any page of the application.
 
PC# Simplification:
 
All variables PC# can store and read back for you must be of string type. You can convert
a string to and from any other type using method om().
 
The name of a page variable must end with "_p".
The name of a session variable must end with "_s".
The name of an application variable must end with "_a".
 
Method wm("vs") sets (stores a value into) a variable.
Method wm("vg") gets (retrieves the value of) a variable.
Parameters used with the methods: ks=variable name   os= its value
 
Examples:
 
   (1) To store the string "Apple" into the page variable (Fruit_p):
       ks="Fruit_p";os="Apple";wm("vs");
 
   (2) To Get the value of the Session variable (Fruit_s):
       ks="Fruit_s";wm("vg");// The obtained value will be assigned to (os)
 
   (3) To store the string "Orange" into the application variable (Fruit_a):
       Application.Lock();     // Lock application to keep other pages out temporarily
       ks="Fruit_a";os="Orange";wm("vs");
       Application.UnLock();   // Unlock the application
 
Look at example 3 carefully. We need to lock the application before modifying an
application variable in order to avoid data corruption. This practice is commonly used
with threads.
 
We are not going to do the locking in the next example since we expect you to be the only
user.
 
If you try to get a variable which has not been stored or its place has been corrupted,
you should end with an exception. However method wm() does its best to prevent this from
happening. So, most likely, you'll end with getting the value (os="") instead.
 
Example 3:
LEFT SECTION:  Install a calendar control. Get the date the user has selected and
               display it.
RIGHT SECTION: Create 3 variables, an application var, a session var and a page var.
               Install a button control and increment all var's each time the button
               is clicked.
=========================================================================================
public partial class pg3:master1 {
  public override void init() {
    base.init();
  }
  public override void setup() {
    base.setup();                                   // Run setup() of master page first
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                      // tb2 is made of 1 col, 1 row
    cs="ca0";j=0;k=0;fns="trb8";ib=true;cls="r0g8"; // calendar control, show grid lines
             ds="c";lf=100;of=100;jd=5;kd=1;wm("i");// Borders=5 pxls, CellSpacing=1 pxl
  //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                      // tb3 is made of 1 col, 1 row
    cs="bt0";cis="Increment Counters";ds="c";       // button control
             fns="trb14";cls="b0y0";wm("i");
  }
  //-----------------------------------------------------------------------------------
  public override void update() {
  //------------------------------------ Page Load ------------------------------------
    if(cs.Equals("pl")) {                           // If event is "Page_Load"
      ks="c_a";wm("vg");                            // test to see if variable is null
      ob=false;if(os.Length<1) ob=true;             // Use ob as a flag of being null
      if(ob || !IsPostBack) {                       // If sample was found null for any
        ks="c_a";os="0";wm("vs");                   // reason or if this was first page
        ks="c_s";os="0";wm("vs");                   // retrieval, store"0" into all
        ks="c_p";os="0";wm("vs");                   // 3 var's.
      }
      setup();                                      // Execute setup()
      MakePage(table);                              // and make page.
      PageNumber(3);                                // Calling master class's method
    }                                               // to display this page's number
  //----------------------------------- Calendar Update ----------------------------------
    if(cs.Equals("ca0")) {                          // If Calendar date selected
      cs="ca0";wm("gu");                            // Get Calendar update (date in cus)
      cs="lb00";cis="You selected: "+cus;wm("sl");  // Display date.
    }
  //----------------------------------- Variable Updates ----------------------------------
    if(cs.Equals("bt0")) {                          // If button clicked
      wm("l");                                      // Add "leave as is" tag <pre> to cis
      cis+="c_a=";ks="c_a";wm("vg");om("ti");       // Get application var, convert to int
      o++;om("fi");cis+=os;ks="c_a";wm("vs");       // increment it,display it,save it.
 
      cis+="    c_s=";ks="c_s";wm("vg");om("ti");   // Do same to session var.
      o++;om("fi");cis+=os;ks="c_s";wm("vs");
      cis+="    c_p=";ks="c_p";wm("vg");om("ti");   // Do same to page var.
      o++;om("fi");cis+=os;ks="c_p";wm("vs");
      wm("c");                                      // Close all HTML tags
      cs="lb01";ds="c";wm("sl");                    // Display text in (cis)
    }
  }
}
=========================================================================================
TUTORIAL:
CALENDAR CONTROL: There are 3 settings which you need to know about when you install a
                  calendar control:
(1) Availability of grid seperation lines: If you want them to appear, supply (ib=true;)
(2) Cell Spacing: You may specify the seperation line width in pixels assigned to (kd)
(3) Border: If you want a border around the calendar assign its width in pixels to (jd)
 
When you select a date from the calendar, your selection goes directly to the server, you
don't need to click a "submit" button to fire the event.
 
VARIABLES: Practice with clicking the button to see how each of the 3 variables react
when you do it.  Then do the following:
 
(1) Close the browser window then start a new one. You'll find that all 3 counters
    have been reset. This is because your session has been the only one requesting the
    page. When it was terminated the page was closed. So all var's lost their values.
(2) Start a second browser window, load the same page and cilck the button 3 times. Return
    back to first window and click the button once. You'll notice that all counters have
    advanced by 1 except c_a which has advanced by 4. This is because application
    variables are common for the two sessions while both page and session variables
    are not.
(3) Leave the first window untouched until the session times out (normally in 20 minutes),
    then click the button once. You'll notice that the session variable c_s is the only
    one which has been reset. The page and application var's have stayed the same.
=========================================================================================

ex03.jpg


                         WORKING WITH MORE COMPLICATED FORMS
                        =====================================
 
FORM CONTROLS: Here is a list of the most commonly used controls in forms:
 
TEXT FIELD: This is the most common control in forms. Here are some of its setup features:
(1) To make it a "Password field", add (ib=true) to its setup parameters.
(2) To make it "Read Only" text field, add (ob=true).
(3) To make it large enough for (n) chars, all visible, add (jf=n)
(4) To make it large enough for a maximum of (m) chars (visible and invisible), add (jd=m)
(5) To make it contain a default text, add (cus="the text")
 
TEXT AREA: This is a multi-line text field. Here are some of its setup features:
(1) To make it "Read Only" text field, add (ob=true).
(2) To make it large enough for (x) chars and (y) lines, all visible, add (jf=x;kf=y;)
(3) To make it large enough for a maximum of (m) total chars (visible and invisible),
    add (jd=m)
(4) To make it contain a default text, add (cus="the text")
 
CHECK BOX: We use it when we expect the user to select more than one item.
  To make it "selected" by default, add (cus="1") to its setup parameters.
 
RADIO BUTTON: We use it when we expect the user to select only one item.
  To make it "selected" by default, add (cus="1") to its setup parameters.
 
Naming Check Boxes and Radio Buttons:
 
These two control types are used as groups. You may include more than one group of Check
boxes or Radio Buttons in your form. This requires a special naming convention.
 
The keyname for any control of these two types must be made of 4 chars like "rb25". In
this name "2" is the group number which this Radio Button belongs to. You can have upto
9 Check Box groups and 9 Radio Button groups. Their numbers should be between 0 to 8.
Group number "9" is reserved for internal use.
 
DROP DOWN LIST: This control allows the user to select an item from a list of items.
  To supply the item list assign it to CIS[]. You may make the first item (CIS[0]) the
  title of the Drop Down List or make it seperate. To set a default selection, assign
  tho index of the item to be selected to (cui).
 
CONTROL LABELS:
 
We always assign the label to (cis). The label of a Button and the label of a
"Label control" are printed on them. The size of the label actually sets the size
of those two controls. You can always resize those controls by changing the font size
or text of their labels.
 
For a "Check Box" and "Radio Button", the label always sets to the right of the control.
 
For most other controls we can do a lot more with labels. We can set them above, below,
to the left or to the right of their controls. We can also load them with the html
necessary to set their color, fonts, locations and much more. We have already done some
of that in previous examples.
 
To set the label location relative to its control assign the label direction code to (os)
the label direction code can be ("n","s","e" or "w") meaning that the label should be set
(above, under, right of or left of) its control (respectively)  The default is "n".
 
For a Drop Down List control, We may use the top item of its item list as the label.  If
we decide to do so, we make no assignment to (cis) and assign the label to CIS[0] instead.
 
OTHER COMMON SETUPS:
 
(1) cns:     Keyname of the table container of the control.
(2) (j,k):   Order of the first cell in the table container which the control occupies
             horizontally and vertically.
(3) (i,o):   Number of cells which the control occupies horizontally and vertically.
(4) (lf,of): Width and Height in Pixels.
(5) jd:      Border width
(6) cls:     Combined Foreground-Background color code.
(7) fns:     Font code.
(8) cts:     Tooltip's text which appears when mouce pointer is placed over the control.
(9) id:      Tab index. Sets the order at which you move through controls by using the
             Tab key.
 
SUBMITTING THE FORM:
 
We expect you to include a button which the user clicks after completing a form. ASP.NET
allows most controls to generate their own events when the user changes their content.
This means that if the user types something wrong into a text field or checks a check box
by mistake, the data may immediately be sent to the server. We don't receive such events
since the user must be allowed to inspect what he/she has done and make all
the corrections necessary before submitting the form. However, if you like to handle the
events of any control by yourself, you can always get the control's object by assigning
its keyname to (cs) and calling wm("O")
 
We handle only 3 events, "Page_Load", "Button_Click" and "Calendar's Date change".
 
GETTING CONTROL's UPDATE:
 
After the user hits the "Submit" button, PC# receives the event, obtains the keyname of
the button and assigns it to (cs), then calls method update().
 
In method update(), the first thing to do is to use method  wm("gu") to get the latest
update for all the controls which you expect the user to have changed. Here is how it
works for each control:
 
TEXT FIELDS AND TEXT AREAS: Calling the method returns the text which the user has
  entered assigned to (cus)
 
DROP DOWN LISTS: Calling the method returns the selected item's index assigned to (cui)
 
CHECK BOXES AND RADIO BUTTONS: These controls can either be checked individually or as
  groups. To check them individually, assign the control's keyname to (cs) and call
  wm("gu"). If the control was selected, you will receive (cus="1"). If it was not, you
  will receive (cus="") or (cus="0").
 
  To check them as groups, let have application examples:
  Check box groups: Assume that your form contains a check box group which is made of
  "cb10","cb11","cb12". As you must know, the group number of the three button group
  is "1".  To check the update of this group call the method as follows:
 
      cs="cb1*";wm("gu");
 
  The method will return the control update array CUS[] containing "1" into each row which
  represents a checked button and "0" into each row which has not been checked.
 
  So, if the user has checked "cb10" and "cb12" and left "cb11" unchecked, you'll get:
  CUS[0]="1", CUS[1]="0" and CUS[2]="1".
 
  Radio Button groups: For a Radio button group made of the four buttons "rb30","rb31",
  "rb32" and "rb33" you check the group's update by:
 
     cs="rb3*";wm("gu");
 
  The method will return the control update integer (cui) assigned the order of the
  selected button. So, if the user has selected "rb32", you'll get (cui=2).
 
Example 4: We'll demonstrate the installation and event handling of a form which contains
           Text fields, Text area, Drop Down List, Check box group and Radio Button group
           in addition to Labels and Buttons.
=========================================================================================
public partial class pg4:master1 {
  public override void init() {
    base.init();
  }
  public override void setup() {
    base.setup();                                   // Run setup() of master page first
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                      // tb2 made of 3 col's, 5 rows
    cs="lb0";cis="Personal Information";j=0;k=0;i=3;ds="c";cls="s9G1";fns="trb14";wm("i");
    cs="tf0";cis="First Name";j=0;k=1;jf=17;ds="w";cls="b0o5";fns="trb12";
            cts="Your First Name";wm("i");          // Tool tip added to this control
    cs="tf1";cis="Last Name";j=1;k=1;i=2;jf=15;ds="e";cls="b0o5";fns="trb12";wm("i");
    cs="tf2";cis="Street Address";j=0;k=2;i=3;jf=44;ds="w";cls="b0o5";fns="trb12";wm("i");
    cs="tf3";cis="City";j=0;k=3;jf=15;ds="w";cls="b0o5";fns="trb12";wm("i");
    cs="tf4";cis="State";j=1;k=3;jf=5;ds="w";cls="b0o5";fns="trb12";wm("i");
    cs="tf5";cis="Zip";j=2;k=3;jf=5;ds="w";cls="b0o5";fns="trb12";wm("i");
    cs="ch0";cui=0;j=0;k=4;i=2;ds="w";              // 1st item is the title
    CIS=new string[]{"Years at this residency","Less than Two years","Two Years or more"};
           cls="b0o7";fns="trb12";wm("i");
    cs="bt0";cis="Submit";cus="submit";j=1;k=4;ds="e";cls="r0";fns="trb12";wm("i");
  //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                      // tb3 contains following items
    cs="lb1";cis="Additional Information";j=k=0;i=3;ds="c";cls="s9G1";fns="trb14";wm("i");
    cs="lb2";cis="Optional Information:";j=0;k=1;ds="w";cls="b0p7";fns="trb12";wm("i");
    cs="cb00";cis="Over 65";j=1;k=1;ds="w";cls="b0p7";fns="trb12";wm("i");
    cs="cb01";cis="Retired";j=2;k=1;ds="e";cls="b0p7";fns="trb12";wm("i");
    cs="lb3";cis="Method of payment:";j=0;k=2;ds="w";cls="r0p7";fns="trb12";wm("i");
    cs="rb00";cis="MasterCard";cus="0";             // First button selected as default
              j=1;k=2;ds="w";cls="r0p7";fns="trb12";wm("i");
    cs="rb01";cis="Visa";cus="1";j=2;k=2;ds="e";cls="r0p7";fns="trb12";wm("i");
    cs="tf6";cis="Credit Card number";j=0;k=3;jf=19;ds="w";cls="S9s9";fns="trb12";wm("i");
    cs="tf7";cis="Exp Date";j=1;k=3;jf=5;ds="c";cls="S9s9";fns="trb12";wm("i");
    cs="tf8";cis="V Code";j=2;k=3;jf=3;ds="e";cls="S9y7";fns="trb12";wm("i");
    cs="ta0";cis="Special Instructions";j=0;k=4;i=3;o=2;jf=34;kf=2;ds="w";
             cls="S9g8";fns="crb12";wm("i");
    cs="bt1";cis="Submit";j=2;k=6;i=3;ds="c";cls="r0";fns="trb12";wm("i");
  }
  //-----------------------------------------------------------------------------------
  public override void update() {
  //------------------------------------ Page Load ------------------------------------
    if(cs.Equals("pl")) {                               // If event is "Page_Load"
      setup();                                          // Execute setup()
      MakePage(table);                                  // Make the page
      PageNumber(4);                                    // Call master1 class's method to
    }                                                   // to display this page's number
  //------------------------------------ bt0 Click -------------------------------------
    if(cs.Equals("bt0")) {                              // If "bt0" clicked
    // Var's used: ns=Name, rs=Years of residency       // Will check tf0, tf1 & ch0
                                                        // only as samples.
      cs="tf0";wm("gu");ns=cus+" ";                     // assign First name to (ns)
      cs="tf1";wm("gu");ns+=cus;                        // add last name to (ns)
      cs="ch0";wm("gu");                                // Get ch0's update (cui=sel indx)
      if (cui==1) rs="Less than 2";else if (cui==2) rs="Two or more";
      cis+="Name: "+ns+"<br>"+"Residency years: "+rs;   // Make output string
      cs="lb00";wm("sl");                               // Display it into "lb00"
    }
  //------------------------------------ bt1 Click -------------------------------------
    if(cs.Equals("bt1")) {                              // If "bt1" clicked
    // Var's used: ps=Optional Information, ds=Credit Card Name
      cs="cb0*";wm("gu");                               // Get update for checkbox group
      if (CUS[0].Equals("1")) ps+="Over 65,";           // Assign selected item(s) to (ps)
      if (CUS[1].Equals("1")) ps+="Retired,";
      cs="rb0*";wm("gu");                               // Get update for Radio Button grp
      if (cui==0) ds="MasterCard";else ds="Visa";       // Assign selected item to (ds)
      cis+="Op. Information: "+ps+"<br>"+"Credit Card: "+ds;
      cs="lb01";wm("sl");                               // Display results
    }
  }
}
=========================================================================================

ex04.jpg

                                       DATA VALIDATION
                                       ===============
 
The asp.net allows validating data entered by users into a form at their browser before
sending the data to the server. This saves time especially at high traffic time when it
takes too long to make a trip to the server and back.
 
PC# has simplified the validation process significally. All you do is add between 1-3
parameters to your control's setup data to do the validation. There are 3 types of
client side validations:
 
(1) REQUIRED FIELD VALIDATION: This is to insure that the user has entered data into
    the field before clicking the submit button. If the user has not, he gets a message
    to remind him to do so and the data is not sent to the server.
 
(2) RANGE VALIDATION: If the data entered into the field was outside expected range, a
    warning message is given to the user and the data is not sent to the server.
 
(3) COMPARE VALIDATION: If the data entered into the field was higher, lower, equal or
    not equal to a specific value or to the data entered into another field, the user
    gets a warning message and the data is not sent to the server.
 
HOW TO DO IT: There are three variables which controls the validation process. These
variables are (vlb, vlc and vls) As you must know their types are (bool, char and string)
respectively. You may add one or more if these variables to the setup data of one control
in order to validata its data.
 
(1) If you don't want to validate a field, add none of them to its setup data.
(2) If you like to make sure the that the field is not blank, add (vlb=true;)
(3) If you like to make sure that the data entered is within a particular range, assign
    the two limits to (vls) and the type code to (vlc) as will be explained next.
(4) If you like the data entered into a field to be compared against a value or against
    data entered into another field, assign an expression indicating the comparison wanted
    to (vls) and the data type which the comparison will be based on to (vlc)
 
HOW TO PREPARE (vls):
 
To do range validation: vls=min:max where min and max are the minimum and maximum allowed
limits respectively.
Example:vls="0:5" means that data in the field must not be outside the range 0:5.
 
To do compare validation: Assign the operation followed with the value or control to
compare with to vls. Operation can be one of (=, !=, <, <=, >, >=)  
Examples: vls="=5" means that data entered into the field must be equal to "5".
          vls="!=5" means that data entered into the field must not be equal to 5.
          vls="=tf0" means that data data entered into the field must be equal to the data
                     entered into the field (tf0)
 
HOW TO PREPARE (vlc):
 
vlc is assigned the code for the type upon which the comparison is based. It can be:
i=int     d=double     s=string     D=date     C=Currency.
Example: vlc='i' means compare the two values as integers.
         vlc='s' means compare the two values as strings.
 
COMPARING CLIENT SIDE TO SERVER SIDE VALIDATION:
 
Client side validation saves time, so it is good to use for most simple validations.
However, you must know that this "mechanical" kind of validation is never a match to
the server side validation in which you use your full programming ability and resources
to insure that the data entered by the user is valid.

EXAMPLE 5: This example shows how to do both client side and server side validation.
=========================================================================================
public partial class pg5:master1 {
  public override void init() {
    base.init();
  }
  public override void setup() {
    base.setup();                                   // Run setup() of master page first
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                          // tb2 contains following items
    cs="lb0";cis="Personal Information";j=0;k=0;i=3;    // Form title
             ds="n";cls="s9G1";fns="trb14";wm("i");
    cs="tf0";cis="User ID";vlb=true;j=0;k=1;i=3;jf=18;  // Use ID, RequiredField
             ds="w";cls="b0o5";fns="trb12";wm("i");     // validation (RFV) only
    cs="tf1";cis="Password";vlb=true;j=0;k=2;ib=true;   // Password, RFV only.  (ib=true)
            jf=18;ds="w";cls="b0o5";fns="trb12";wm("i");// makes it a password field.
    cs="tf2";cis="Password Again";j=1;k=2;i=2;ib=true;  // "Pass Again" field. RFV+Compare
                 vlb=true;vls="=tf1";vlc='i';jf=18;     // validation based on "Integer"
                 ds="e";cls="b0o5";fns="trb12";wm("i"); // data type.
    cs="lb1";cis="Method of payment:";j=0;k=3;ds="w";cls="b0p7";fns="trb12";wm("i");
    cs="rb00";cis="MasterCard";cus="0";j=1;k=3;ds="w";cls="b0p7";fns="trb12";wm("i");
    cs="rb01";cis="Visa";cus="1";j=2;k=3;ds="e";cls="b0p7";fns="trb12";wm("i");
    cs="tf6";cis="Credit Card number";vlb=true;j=0;k=4; // Card number, RFV only. This
            jf=19;ds="w";cls="S9s9";fns="trb12";wm("i");// field also validated at server
 
    cs="tf7";cis="Exp Date";vlb=true;j=1;k=4;jf=5;      // Exp Date, RFV only. This field
            ds="c";cls="S9s9";fns="trb12";wm("i");      // is also validated at server.
    cs="tf8";cis="V Code";vlb=true;vls="0:999";vlc='i'; // RFV + Range validation as (int)
            j=2;k=4;jf=3;ds="e";cls="S9y7";fns="trb12";wm("i");
    cs="bt0";cis="Submit";j=2;k=6;i=3;ds="c";cls="r0";fns="trb12";wm("i");
    //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                          // tb3 contains following items
    cs="lb3";cis="Validation";j=0;k=0;i=3;ds="n";       // Title
            cls="s9G1";fns="trb14";wm("i");
    cs="vs0";j=0;k=1;i=3;cls="r0p7";fns="trb12";wm("i");// Validation Summary Control
    cs="lb4";j=0;k=2;i=3;cls="r0p7";fns="trb12";wm("i");// Label to display server valid.
  }
  //-----------------------------------------------------------------------------------
  public override void update() {
  //------------------------------------ Page Load ------------------------------------
    if(cs.Equals("pl")) {                               // If event is "Page_Load"
      setup();                                          // Execute setup()
      MakePage(table);                                  // Make the page
      PageNumber(5);                                    // Call master1 class's method to
    }                                                   // to display this page's number
  //------------------------------------ bt0 Click -------------------------------------
    if(cs.Equals("bt0")) {
    // Var's used: ns=C Card Number after non-digit char's removed, a=asc code
    //             m,y=Month, Year entered by user.  a,b=This Month, This Year
    //             es=Error Message string
    // ------------------------ Validating Credit Card Number ------------------------
      cs="tf6";wm("gu");                            // Get Card Number text into (cus)
      ns="";es="";                                  // Initialize both strings
      char[] CC=cus.ToCharArray();                  // Convert cus to Char Array
      for(int i=0;i<cus.Length;i++) {               // Scan (cus) characters
        a=(int)CC[i];                               // Get asc value of each char
        if(a>47 && a<58) ns+=CC[i];                 // If a digit, add char to (ns)
      }
      if (ns.Length!=16) es+="* Please re-enter your Credit Card Number.<br>";
                                                    // If resulting (ns) was not 16
                                                    // chars long, add error message
    // -------------------- Validating Credit Card Expiration Date --------------------
      cs="tf7";wm("gu");                            // Get Expiration Date into (cus)
      if (cus.Length<5 || cus.IndexOf("/")<2) {     // If not 5 chars long and contains
        es+="Please re-enter your Credit Card Expiration Date.";
      }                                             // (/) at the middle, add error msg
      else {                                        // Else:
        os=cus;oc='/';om("s");                      // Seperate month, year
        os=OS[0];om("ti");m=o;                      // Convert each to type (int) and
        os=OS[1];om("ti");y=o;                      // assign to m,y respectively.
        os="";sm("dd");                             // Get today's date in short format
        os=os.Substring(0,3)+os.Substring(8,2);     // Pick (mm/yy) section
        oc='/';om("s");                             // Seperate month, year
        os=OS[0];om("ti");a=o;                      // Convert each to type (int) and
        os=OS[1];om("ti");b=o;                      // assign to a,b respectively
        if (y<b || (y==b && m<a)) es+="* Your Credit Card has expired.";
      }                                             // Compare enterd (m,y) with (a,b)
                                                    // Add error msg if card expired.
      if (es.Length==0) es="* Thank you. You have completed the form successfully.";
                                                    // If no error added so far, add
                                                    // "Successful data entry" message
      cs="lb4";cis=es;wm("sl");                     // Display error msg string at lb4
    }
  }
}

=========================================================================================

ex05.jpg


                                          GRAPHICS
                                         ==========
 
Including dynamically generated Graphics into your web pages has become a very simple
task, thanks to the techniques PC# uses for drawings. If you remember, when you draw on a
window form, you don't draw on the form directly. Instead, you draw on the Default
Graphical Device (bio) which is a bitmap object large enough to take all your drawings
and is created automatically for you during initialization. This is exactly what you need

when you draw on a web page.
When you write a web page class which extends class (pasp), you have no window form to
draw on, but the Graphical Output Device (bio) is still available. So, you use the same
code which you could have used if you have been drawing on a window form with absolutely
no difference. PC# will then send (bio) with all your drawings dynamically to your page.
 
Now, you may like to ask "Can the drawings be included into the same class with all other
controls?". No, unless you have saved your bitmap object into a file at the server in
advance. If you like to send your drawings dynamically, you must use two seperate classes,
the main class which includes the setup data for all controls and a second class which
includes the code for drawings. The main class should include an Image control whose image
file name is the name of the ".aspx" file of your drawing class.
 
The reason for not mixing the two, is that each page must have its "Content Type"
specified. The content type for the main page is "text/html" while the content type for
the drawing page is "image/jpeg". The main page is the page the user asks for. After the
user's browser receives the page, it finds that there is an image to be drawn at a
location in the page, so it returns to the server and asks for the image's file which is
your drawing file.
 
Your drawing class is exactly the same as any page class. It extends (pasp) class and
should be saved into a ".cs" file then tool "pcw" should be used to create its ".aspx"
file. The drawing class should include no setup() method. All drawing code should be in
method update(). Her is how to make your drawing code:
 
(1) Open a new dynamic bitmap drawing operation. This is done by calling method wm("bo")
    after assigning the wanted width and height of (bio) to (lf,of) respectively.
 
(2) Write your drawing code exactly as you do when you draw on a window form.
 
(3) Close the bitmap drawing operation. This is done by calling wm("bc"). This will save
    your bitmap (bio) to the page's output stream then dispose all graphical objects.
 
EXAMPLE 6: We are going to see how to modify the code used in window form's drawing
examples which we have seen before so that they draw dynamically into a web page.
 
Example 8 was to draw a piece of jewelrey. Since the only advantage in dynamic web
drawing is in allowing user interaction, we'll modify that example so it allows the user
to select the pearl colors.
 
Example 13 has demonstrated how window form controls and drawings can interact together.
It showed how to draw a triangle, square, circle and a pentagon using colors which are
selectable by the user. We'll see how to modify it so it does the same accross the web. 
=========================================================================================
THE MAIN CLASS (class pg6)
 
public partial class pg6:master1 {                    // Class extends master1 as uasual
  public override void init() {                   
    base.init();                                      // Initialize pasp
  }
  public override void setup() {
    base.setup();                                     // Execute setup() of master1 class
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                        // tb2 is made of 2 cols, 2 rows
    cs="ch0";j=0;k=0;ds="c";cls="S9g7";fns="trb12";   // Pearl color drop list
       CIS=new string[]{"Pearl Color","Red","Green",  // First item is the title
       "Blue","Magenta","Cyan","Orange","Pink","Yellow"};wm("i");
    cs="bt0";j=0;k=1;cis="Redraw";cls="r0g7";fns="trb12";ds="c";wm("i");
                                                      // Redraw button
    cs="im1";cis="";j=1;k=0;o=2;ds="c";lf=of=200;     // Image control where the drawing
       ims="jewel.aspx";wm("i");                      // will be, ims=the ".aspx file"
  //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                        // tb3 is made of 3 cols, 2 rows
    cs="ch1";j=0;k=0;ds="c";cls="S9g7";fns="trb12";   // Shape selection drop list
       CIS=new string[] {"Select a Shape",            // First item is the title
       "Triangle","Square","Circle","Pentagon"};wm("i");
    cs="bt1";j=1;k=0;cis="Redraw";cls="r0g7";fns="trb12";ds="c";wm("i");
                                                      // Redraw button
    cs="ch2";j=2;k=0;ds="c";cls="S9g7";fns="trb12";   // Shape color drop list
       CIS=new string[] {"Select a Color","Red","Green","Blue","Black"};wm("i");
    cs="im2";j=0;k=1;i=3;ds="c";lf=370;of=200;        // Image control sets drawing
       ims="shapes.aspx";wm("i");                     // location and file name
  }
  //-----------------------------------------------------------------------------------
  public override void update() {                    
  //------------------------------------ Page Load ------------------------------------
    if(cs.Equals("pl")) {                             // If event is "Page_Load"
      setup();                                        // Execute setup()
      if(!IsPostBack) {                               // If first trip to retrieve page
        ks="PearlColor_s";os="p0";wm("vs");           // Save initial color code ("p0")
                                                      // as a session variable
        ks="shapes_s";os="    ";wm("vs");             // Save initial "shape colors"
      }                                               // string also as a session variable
      MakePage(table);                                // Make the page to be sent
      PageNumber(6);                                  // Call master1 class's method to
    }                                                 // set page number.
  //------------------------------------ bt0 Click -------------------------------------
    if(cs.Equals("bt0")) {                            // If button (bt0) clicked:
      cs="ch0";wm("gu");                              // Get ch0's update (cui=index)
      os=" rgbmcopy".Substring(cui,1)+"0";            // Form color code
      if (cui==0) os="p0";                            // if (cui=0) use default color.
      ks="PearlColor_s";wm("vs");                     // Save selected color as a session
    }                                                 // variable.
   //------------------------------------ bt1 Click -------------------------------------
   if(cs.Equals("bt1")) {                            // If button (bt1) clicked:
    // var's used: x=Order number of selected shape in (ch0)
    //             ys=Order number of selected color in (ch1) represented as a string
      cs="ch1";wm("gu");                              // Get ch1's update, assign selected
      x=cui-1;                                        // index to (x) after being adjusted
      cs="ch2";wm("gu");                              // Get ch2's update. If was item 0,
      ys=" ";                                         // assign space to (ys)
      if (cui>0) ys=""+(cui-1);                       // else ys=adjusted (cui) as string
      ks="shapes_s";wm("vg");                         // Get stored shape colors string.
      if(os.Length<4 || x==-1) {os="    ";x=0;}       // If not valid or if user selected
                                                      // item 0 (which means no selection)
                                                      // fill all 4 positions with spaces
      os=os.Substring(0,x)+ys+os.Substring(x+1);      // Else put user selected index at
                                                      // correct position of the string
      ks="shapes_s";wm("vs");                         // Save string as a session variable
    }
  }
}
 
CLASS jewel
 
public partial class jewel:pasp {            // Class extends (pasp) which
                                             // contains all PC# methods
  public override void init() {
    base.init();                             // Initialize pasp
  }
  public override void update() {
    if(cs.Equals("pl")) {                    // If event is "Page_Load"
      lf=of=200;wm("bo");                    // Open new bitmap operation using bitmap of
                                             // size 200 X 200 pixels.
      cls="p7";gm("ec");                     // Paint background with same color as page
  // ------------ This section is cpied from the Window forms drawing example -----------
  // ----------------------- Except for the lines marked with '**' ----------------------
      lf=of=170;gm("ce");                    // Create the circular gold plate
      cls="o5y5";gm("spl");                  // Prepare linear gradient brush for it
      gm("grf");                             // then render-fill the gold plate.
      lf=6;of=50;gm("c=");                   // Create hexagon shape object at center.
      cls="r0";ks="r";gm("grs");             // Draw the object using sp effects-refl at
      jf=45;cls="b0";ks="r";gm("grs");       // center in red, then repeat 6 times using
      jf=-45;cls="b0";ks="r";gm("grs");      // different colors and different locations
      jf=22;kf=40;cls="g0";ks="r";gm("grs");
      jf=-22;kf=40;cls="m0";ks="r";gm("grs");
      jf=22;kf=-40;cls="m0";ks="r";gm("grs");
      jf=-22;kf=-40;cls="g0";ks="r";gm("grs");
      lf=of=25;gm("ce");                     // Create a circle at center (pearl)
      ks="PearlColor_s";wm("vg");            // ** get color code stored as session var
      if(os.Length<2) os="p0";               // ** If not valid use pink color as default
      cls=os;                                // ** Assign code to (cls)
      for (int x=0;x<20;x++) {               // Draw it 20 times using sp effects-refl.
        jf=80;kf=18*x;kb=true;               // at locations around the plate. Polar
        ks="r";gm("grs");                    // coord's are used for specifying locations
      }
  // -------------------------------------------------------------------------------------
      wm("bc");                              // Close bitmap operation
    }
  }
}

CLASS shapes:
 
public partial class shapes:pasp {
  public override void init() {
    base.init();
  }
  public override void update() {
    //  var's  ss=Shape colors               // ss is a 4 char string representing the 4
    //         s=Shape's order number        // shapes in order. Each char contains the
    //         c=Color order number          // order of the color code to draw the shape
                                             // it represents with.
    if(!cs.Equals("pl")) return;             // If not Page_load event, return
    ks="shapes_s";wm("vg");ss=os;            // Get ss string stored as session variable
    lf=370;of=200;wm("bo");                  // Open new bitmap operation using bitmap of
                                             // size 370 X 200 pixels
    cls="p7";gm("ec");                       // Match image background color with page's
      string mode;                           // Mode can be "f" / "d" meaning fill or draw
      for (s=0;s<ss.Length;s++) {            // Scan (ss) characters
        os=ss.Substring(s,1);                // Assign each char to (os)
        if (os.Equals(" ")) c=-1;            // If os=space, Color is indeterminable, make
        else {                               // (c=-1) else:
          om("ti");c=o;                      // convert (os) to int and assign to c
          cls="r0 g0 b0 S9 ".Substring(3*c,2); // Get (cls) for selected color
        }
        mode="f";if(c==-1) {cls="S9";mode="d";}// If (c=-1),object will be drawn in black
        gm("sps");                           // Create solid pen/brush for the color
        if (s==0) {                          // If item 0 was selected, draw-fill triangle
          jf=-125;kf=45;lf=3;of=95;ls="c="+mode;gm();
        }
        else if (s==1) {                     // If item 1 was selected, draw-fill square
          jf=125;kf=50;lf=of=70;ls="cr"+mode;gm();
        }
        else if (s==2) {                     // If item 2 was selected, draw-fill circle
          jf=-125;kf=-50;lf=of=85;ls="ce"+mode;gm();
        }
        else if (s==3) {                     // If item 3 was selected, draw-fill pentagon
          jf=125;kf=-50;lf=5;of=95;ls="c="+mode;gm();
        }
      }
      wm("bc");                              // Close bitmap operation.
  }
}
=========================================================================================
HOW TO GENERATE NECESSARY FILES:
 
(1) Save all three classes into code files, named "pg6.cs", "jewel.cs" and "shapes.cs".
 
(2) Use the tool (pcw) to generate necessary (.aspx) files as follows (from command mode):
    pcw pg6    [ENTER]
    pcw jewel  [ENTER]
    pcw shapes [ENTER]
    This should generate the files "pg6.aspx", "jewel.aspx" and "shapes.aspx".
 
The only file the user needs to know about is "pg6.aspx". When this file is requested by
the browser all files will be used together to generate the page.
=========================================================================================
TUTORIAL: Here are some comments:
 
(1) The main page and the graphics pages are seperate pages, so in order to make them
    communicate we cannot use page variables, we must use at least session variables.
 
(2) In the update() method of the main class, user selection is received and stored as
    session variables, which are read by the graphics classes and their drawings are set
    accordingly.
 
(3) The "Drop Down List" (Sorry its symbol is 'ch' because we used to call it "choice")
    returns to us the user selection in the form of an integer assigned to its control
    update variable (cui). The value in (cui) is the order number of the selected item
    within all items of the list.
 
    The first item (cui=0) is the list's title. If the user has selectsd this item, it
    means that he has made no choice. In case of the Jewelry drawing, we have considered
    this to be an indication that the user wants to select the default color. In case of
    the Shapes drawing, we have cosidered selecting no color for a shape to mean that the
    user wants to draw the shape without filling.
 
(4) In case of the Jewelry drawing, the item to pass from the main class to the drawing
    class is the pearl's color code. In case of the Shapes drawings, we have 4 shapes
    each of them may be drawn in one of 4 colors. So, we have used a 4 char long string,
    each of its char's represents one shape at the same order as their orders in the list
    which is (Triangle-Square-Circle-Pentagon). We insert at each character the order
    number of the color the user wants to draw the shape in. A space at the location of
    one shape means that the user wants to draw that shape without filling. At the start
    the string contains 4 spaces, so all shapes are drawn without filling.
 
(5) A Graphics class is the same as any page class except that it contains no setup()
    method and it receives only one event which is the "Page_Load". When this event is
    received, it generates its drawings. We make (.aspx) files for them as we do with
    all other page classes.
 
(6) Notice that none of the code files are compiled. The ASP.NET receives them as is and
    compiles them internally. The only file which has been compiled is the master class.
    it is compiled into the library file (master1.dll) which must reside into the "Bin"
    sub directory of the application directory.
=========================================================================================
CAN WE COMBINE THE 3 FILES INTO ONE:
 
You maybe wondering if we can eliminate the two graphic generating files "jewel" and
"shapes" and combine them with "pg6" file. Yes we can if we use "Query Strings".
 
You know that you can combine several applications into one desktop program by writing the
code of each application into a seperate block or group of blocks. Then, using command
line arguments to execute each application individually. If you don't remember how it is
done, see the section of the Reference manual for desktop applications under the title
"Command Line Arguments".
 
In Web applications, we can do the exact same thing using "Query string".
 
Query String: Query string does the same as command line arguments for web pages. To
add arguments to a web page add the question mark symbol '?' at the end of the page's URL
followed with a combination of "Key=Value" elements. For example:
http://www.xxx.com?x=50   will take you to the page at "http://www.xxx.com" and lets the
page know that the value of key (x) is "50".
 
One important thing to know is that all keys are considered to be of type string, so the
query string (x=50), actually mean that the string (x) is equal to "50".
 
Method wm() at mode "rq" reads the query string for you and extracts the values which
corresponds to any key which you supply it with. Notice that in general, each key may have
more than one value. Here is how to do it, if you like to get the value of key (x) in the
example above you would supply the name of the key to (ks) and call the method as follows:
 
ks="x";wm("rq");
 
The value returned is the array OS[] containing all the values which correspond to key (x).
Since you are expecting only one value, your value will be stored into the first element,
so you should get OS[0]=50 and all other array elements should be empty.
 
If the URL used to retrieve the page contained no cuery string you should get OS[0]="" and
all other elements of the array should return the same value.
 
Now let us see how to modify the file "pg6.cs" so files "jewel.cs","jewel.aspx",
"shapes.cs" and "shapes.aspx" can be all eliminated.
 
(1) In method setup(), the two image files "jewel.aspx" and "shapes.aspx" which are used
for the setup of controls "im1" and "im2" will be renamed to "pg6?block=1" and
"pg6?block=2" respectively. This means that they will be in the same page at different
blocks.
 
(2) The code used to generate the drawings will be moved to methods jewel() and shapes()
located into "pg6.cs".
 
(3) At the start of method's update, the value of the query string "block" will be
obtained and if found to be equal to "1" or "2", the corresponding drawing method will
be executed. Notice that class "pasp" which we are extending, does not have a definition
for the old block number variables (bli) and (blp). The block which we are now using is
of a string type and you must define it at the top of the page class.
 
Here is the new modified listing of "pg6.cs":
 
=========================================================================================
public partial class pg6:master1 {                    // Class extends master1 as uasual
  string block="";                                    // Declare the string var (block)
  public override void init() {                   
    base.init();                                      // Initialize pasp
  }
  public override void setup() {
    base.setup();                                     // Execute setup() of master1 class
  //----------------------------------- tb2 Contents ----------------------------------
    cns="tb2";                                        // tb2 is made of 2 cols, 2 rows
    cs="ch0";j=0;k=0;ds="c";cls="S9g7";fns="trb12";   // Pearl color drop list
       CIS=new string[]{"Pearl Color","Red","Green",  // First item is the title
       "Blue","Magenta","Cyan","Orange","Pink","Yellow"};wm("i");
    cs="bt0";j=0;k=1;cis="Redraw";cls="r0g7";fns="trb12";ds="c";wm("i");
                                                      // Redraw button
    cs="im1";cis="";j=1;k=0;o=2;ds="c";lf=of=200;     // Image control where the drawing
       ims="pg6.aspx?block=1";wm("i");                // will be, same page.
  //----------------------------------- tb3 Contents ----------------------------------
    cns="tb3";                                        // tb3 is made of 3 cols, 2 rows
    cs="ch1";j=0;k=0;ds="c";cls="S9g7";fns="trb12";   // Shape selection drop list
       CIS=new string[] {"Select a Shape",            // First item is the title
       "Triangle","Square","Circle","Pentagon"};wm("i");
    cs="bt1";j=1;k=0;cis="Redraw";cls="r0g7";fns="trb12";ds="c";wm("i");
                                                      // Redraw button
    cs="ch2";j=2;k=0;ds="c";cls="S9g7";fns="trb12";   // Shape color drop list
       CIS=new string[] {"Select a Color","Red","Green","Blue","Black"};wm("i");
    cs="im2";j=0;k=1;i=3;ds="c";lf=370;of=200;        // Image control sets drawing
       ims="pg6.aspx?block=2";wm("i");                // location.
  }
  //-----------------------------------------------------------------------------------
  public override void update() {                    
  //------------------------------------ Page Load ------------------------------------
    if(cs.Equals("pl")) {                             // If event is "Page_Load"
      ks="block";wm("rq");block=OS[0];                // Get the block number (string)
      if (block.Equals("1")) {jewel();return;}        // Call jewel() if block="1"
      if (block.Equals("2")) {shapes();return;}       // Call shapes() if block="2"
      setup();                                        // If neither one, Execute setup()
      if(!IsPostBack) {                               // If first trip to retrieve page
        ks="PearlColor_s";os="p0";wm("vs");           // Save initial color code ("p0")
                                                      // as a session variable
        ks="shapes_s";os="    ";wm("vs");             // Save initial "shape colors"
      }                                               // string also as a session variable
      MakePage(table);                                // Make the page to be sent
      PageNumber(6);                                  // Call master1 class's method to
    }                                                 // set page number.
  //------------------------------------ bt0 Click -------------------------------------
    if(cs.Equals("bt0")) {                            // If button (bt0) clicked:
      cs="ch0";wm("gu");                              // Get ch0's update (cui=index)
      os=" rgbmcopy".Substring(cui,1)+"0";            // Form color code
      if (cui==0) os="p0";                            // if (cui=0) use default color.
      ks="PearlColor_s";wm("vs");                     // Save selected color as a session
    }                                                 // variable.
   //------------------------------------ bt1 Click -------------------------------------
   if(cs.Equals("bt1")) {                            // If button (bt1) clicked:
    // var's used: x=Order number of selected shape in (ch0)
    //             ys=Order number of selected color in (ch1) represented as a string
      cs="ch1";wm("gu");                              // Get ch1's update, assign selected
      x=cui-1;                                        // index to (x) after being adjusted
      cs="ch2";wm("gu");                              // Get ch2's update. If was item 0,
      ys=" ";                                         // assign space to (ys)
      if (cui>0) ys=""+(cui-1);                       // else ys=adjusted (cui) as string
      ks="shapes_s";wm("vg");                         // Get stored shape colors string.
      if(os.Length<4 || x==-1) {os="    ";x=0;}       // If not valid or if user selected
                                                      // item 0 (which means no selection)
                                                      // fill all 4 positions with spaces
      os=os.Substring(0,x)+ys+os.Substring(x+1);      // Else put user selected index at
                                                      // correct position of the string
      ks="shapes_s";wm("vs");                         // Save string as a session variable
    }
  }
  // ================================== jewel method ====================================
  void jewel() {
    lf=of=200;wm("bo");                    // Open new bitmap operation using bitmap of
                                           // size 200 X 200 pixels.
    cls="p7";gm("ec");                     // Paint background with same color as page
 
  // ------------ This section is cpied from the Window forms drawing example -----------
  // ----------------------- Except for the lines marked with '**' ----------------------
    lf=of=170;gm("ce");                    // Create the circular gold plate
    cls="o5y5";gm("spl");                  // Prepare linear gradient brush for it
    gm("grf");                             // then render-fill the gold plate.
    lf=6;of=50;gm("c=");                   // Create hexagon shape object at center.
    cls="r0";ks="r";gm("grs");             // Draw the object using sp effects-refl at
    jf=45;cls="b0";ks="r";gm("grs");       // center in red, then repeat 6 times using
    jf=-45;cls="b0";ks="r";gm("grs");      // different colors and different locations
    jf=22;kf=40;cls="g0";ks="r";gm("grs");
    jf=-22;kf=40;cls="m0";ks="r";gm("grs");
    jf=22;kf=-40;cls="m0";ks="r";gm("grs");
    jf=-22;kf=-40;cls="g0";ks="r";gm("grs");
    lf=of=25;gm("ce");                     // Create a circle at center (pearl)
    ks="PearlColor_s";wm("vg");            // ** get color code stored as session var
    if(os.Length<2) os="p0";               // ** If not valid use pink color as default
    cls=os;                                // ** Assign code to (cls)
    for (int x=0;x<20;x++) {               // Draw it 20 times using sp effects-refl.
      jf=80;kf=18*x;kb=true;               // at locations around the plate. Polar
      ks="r";gm("grs");                    // coord's are used for specifying locations
    }
    wm("bc");                              // Close bitmap operation
  }
  // ================================== shapes method ====================================
  void shapes() {
    //  var's  ss=Shape colors               // ss is a 4 char string representing the 4
    //         s=Shape's order number        // shapes in order. Each char contains the
    //         c=Color order number          // order of the color code to draw the shape
                                             // it represents with.
    ks="shapes_s";wm("vg");ss=os;            // Get ss string stored as session variable
    if(ss.Length<4) ss="    ";               // If var lost or corrupted use default
    lf=370;of=200;wm("bo");                  // Open new bitmap operation using bitmap of
                                             // size 370 X 200 pixels
    cls="p7";gm("ec");                       // Match image background color with page's
    string mode;                             // Mode can be "f" / "d" meaning fill or draw
    for (s=0;s<ss.Length;s++) {              // Scan (ss) characters
      os=ss.Substring(s,1);                  // Assign each char to (os)
      if (os.Equals(" ")) c=-1;              // If os=space, Color is indeterminable, make
      else {                                 // (c=-1) else:
        om("ti");c=o;                        // convert (os) to int and assign to c
        cls="r0 g0 b0 S9 ".Substring(3*c,2); // Get (cls) for selected color
      }
      mode="f";if(c==-1) {cls="S9";mode="d";}// If (c=-1),object will be drawn in black
      gm("sps");                             // Create solid pen/brush for the color
      if (s==0) {                            // If item 0 was selected, draw-fill triangle
        jf=-125;kf=45;lf=3;of=95;ls="c="+mode;gm();
      }
      else if (s==1) {                       // If item 1 was selected, draw-fill square
        jf=125;kf=50;lf=of=70;ls="cr"+mode;gm();
      }
      else if (s==2) {                       // If item 2 was selected, draw-fill circle
        jf=-125;kf=-50;lf=of=85;ls="ce"+mode;gm();
      }
      else if (s==3) {                       // If item 3 was selected, draw-fill pentagon
        jf=125;kf=-50;lf=5;of=95;ls="c="+mode;gm();
      }
    }
    wm("bc");                                // Close bitmap operation.
  }
}

ex06.jpg