Using My Little Grid (MLG)

Top  Previous  Next

 

Introduction

 

You are now on your way.  How to use MLG will be described in this section. Before including MLG code in your application, please familiarize yourself with it's functions, message, and notifications.     

.   

Also, ensure "MLG.DLL" is also where your application can find it (the best place to put MLG.DLL is in your application folder)   

 

The following is a complete guide to using the MLG Grid Control.   

 

 

Table of Contents     

       1) Activating MLG

       2) Error Handling

       3) Data Validation

       4) Creating a Grid Control

       5) Formatting a Grid Beyond the Switches

       6) Navigating/Editing the MLG Grid Control

       7) Reading from the Grid Control

       8) Writing to the Grid Control

       9) Setting up a callback for the MLG Grid Control

       10) Monitoring Grid Control Notifications

       11) MLG Grid Control sample programs

       12) MLG Compiled with an Static Link Library (SLL)

 

Activating MLG

 

The registered version MLG requires activation to be used. The Demo version of MLG does not require activation but is limited in the number of useable rows and columns.  When you purchase MLG, you should have been provided with a download location to MLG.zip, a password to open the zip file and a procedure to activate MLG. NOTE: If the activation process is not done properly, your program using MLG will generate an X on the grid control.   Please keep the password and activation procedure private.   

 

 

Error Handling

 

There is minimum error checking in MLG.  Some messages return a error if the action fail.  One of particular note and which needs to be checked is the %REDIMARRAY message (and associated ArrayReDim wrapper function).  If an attempt to increase the size of the memory needed to hold the grid data fails then preventative actions needs to be taken.  See the reference for messages and functions to see if errors are reported for particular items.

 

Data Validation

 

This is handled by the programmer and MLG has a set of notification messages to allow good validation.  MLG will attempt to validate cells formatted as dates and number length but lets the parent callback know when it had to alter the typed in contents.

 

 

Creating a MLG Grid Control

 

Using PowerBasic and the MLG.inc include file, the grid control will sometimes automatically be registered with Windows but always call MLG_Init just to be sure.

 

DDT Style

----------------------------------------------

MLG_Init

CONTROL ADD "MYLITTLEGRID", hDlg, %IDC_MLGGRID1, "r100/c10/b3", 4, 4, 510, 348, %MLG_STYLE

CONTROL HANDLE hDlg, %IDC_MLGGRID1 TO hGrid1

 

SDK Style

----------------------------------------------

1) If the MLG.dll needs to be accessed dynamically due to language requirements, its grid control can be registered with the following code:

 

DIM hLib as DWORD

DIM hProc as DWORD

 

hLib = LoadLibrary("MLG.DLL")

IF hLib <> 0 THEN

   hProc = GetProcAddress(hLib, "MLG_INIT")

   IF hProc <> 0 THEN CALL DWORD hProc USING MLG_INIT()

   FreeLibrary hLib

END IF

 

hGrid1 = CreateWindow("MYLITTLEGRID", "r500/c10/b3",%MLG_STYLE,4, 4, 765, 555,hDlg, %IDC_MLGGRID1, GetWindowLong(hDlg, %GWL_HINSTANCE), BYVAL 0)      

 

 

2) The programmer should have access to all messaging but functions will have to be called dynamically as above.  It may be advantageous to load the library once on program start up and free the library when the program shuts down.

 

DIM hLib as DWORD

hLib = LoadLibrary("MLG.DLL")

 

hGrid1 = CreateWindow("MYLITTLEGRID", "r500/c10/b3",%MLG_STYLE,4, 4, 765, 555,hDlg, %IDC_MLGGRID1, GetWindowLong(hDlg, %GWL_HINSTANCE), BYVAL 0)      

 

 

'put code here

 

FreeLibrary hLib

 

3) If using Powerbasic and the MLGPB.inc file, MLG.dll gets loaded statically.  Simple call the MLG_Init subroutine to register MLG with Windows.

 

MLG_Init

hGrid1 = CreateWindow("MYLITTLEGRID", "r500/c10/b3",%MLG_STYLE,4, 4, 765, 555,hDlg, %IDC_MLGGRID1, GetWindowLong(hDlg, %GWL_HINSTANCE), BYVAL 0)

 

 

Compiling the MLG Grid Control with a Powerbasic SLL static link library

 

Define the equate %MLGSLL which will force the compiler not to declare the dependency of the DLL functions.  The equate can be any value.

 

%MLGSLL = 1

#INCLUDE "MLG.INC"

#LINK "MLG.SLL"

 

Also, you will need these four lines in your resource file that attaches to your application.  MLG expects to have these cursors available.

 

SSCUR CURSOR "SSCUR.CUR"

LTCUR CURSOR "CURSORLEFT.CUR"

DNCUR CURSOR "CURSORDOWN.CUR"

TABCUR CURSOR "TABCUR.CUR"

 

 

------------------------------------------------

 

The caption field of the grid creation call is used for a "/" delimited flag string. It is a design feature of MLG to put many of the commonly used options in grid setup as switches.  Additional formatting options are available with MLG's built-in API.  Most of the times grids aren't sexy -  they are workhorses. Here is the meaning of the individual switches:

 

       rx[,y]        x= the number of rows for the grid.  Maximum dimensioned rows is 65,000.  Default is 5 rows.

               y= (optional) specified number of dimensioned additional rows - the default is 100.

       cx[,y]        x= the number of cols for the grid.  Maximum dimensioned columns is 255.

               y= (optional) specified number of dimensioned additional cols - the default is 1.  Default is 5 columns.

 

 

A word is in order on how MLG addresses strings used in the grid.  It is simply a two dimension absolute string array referencing a block of memory created by MLG.  The array is usually dimensioned slightly larger than the grid to easily allow "room to grow".  The default is to dimension 100 additional rows and 1 additional column than actual grid size.  Since it is common to append records to a database, 100 rows may get used up quickly and the MLG will have to request more memory.  In most cases this will be done automatically for you.  Sometimes it is handy to place information about a record "to the right of the grid".  For instance, if a grid has 8 columns but is dimensioned for 9 then string data can be placed in the 9th column but hidden visually from the grid.  Note MLG defaults to dimensioning an additional 100 rows and 1 column if the memory has to be redimensioned automatically by inserting rows/columns or appending rows automatically..

 

fx        x=1 for Courier New, 2 for Times Roman, 3 for Arial (default)

 

sx        x=8 to 16.  Fontsizes for the font picked above.  Note:  additional user defined fonts can be made available by using the MLG API. Font size of 10 is the default.

 

ex        x=1 Return key moves the selection down after having dismissed the edit box in the cell.  If the selection moves past the bottom of the grid it will move up to the top.  The default is not to move to the top when move past the grid bottom.  x=2 is as x=1 but the selection will move over one column when it returns to the top after having moved past the bottom ot the grid.  x=3 is as x=1 but will add a new row to the bottom of the grid if data is in one of the cells of that row.  If additional dimensioning is required, MLG will handle it for you automatically.  Also a "*" will appear in the row header of the bottom row indicating that auto row expansion of the grid is active.  x=4 The edit box is dismissed but the selection will not move from the cell.

 

tx        x=1 Tab key moves the selection right after having dismissed the edit box in the cell.  If the the selections moves past the right of the grid then the selection will move the the first column of the same row.  The default action is not to move back to column 1.  x=2 is as x=1 but will move down one row when moving to the first column after having moved right of the grid.

 

hx        Default is showing both a row header and a column header.  x=1 no row header.  x=2 no column header.  x=3 no row or column header.

 

bx        Default is not to allow block selecting of rows are columns.  Block selection is accomplished by left clicking the mouse in a header and dragging down in the row header or across to the right in the column header.  Selections may be extended by SHIFT left clicking the mouse.  x=1 Allow row selections.  x=2 Allow columns selections.  x=3  Allow both row and columns selections with the added functionally of selecting the entire grid by left click the mouse on the upper left hand corner of the grid (intersection of the row header and column header).  In version 1.12 : x=4 allows only 1 row to be selected, x=5 allows only 1 column to be selected and x=6 allows only 1 row or 1 column to be selected.

 

xx        Comma delimited list of column width start with column (0) - (the width of the row header).  The default column width is 50 for the row header (column(0)) and 100 for the other columns.  For example x20,33,45,22 would set the columns width of the row header to 20 and columns 1 to 3 to 33,45,22 respectively.

 

yx        x= 3 to 16 Extra pixels added to row height in order for the grid to look more appealing.  The default is 2.  Some fonts need more room to look good. The upper range use to be 6 but was increased to 16 in version 3.00.

 

ax        x=1 Will display a right pointing arrow in the selected row header.  x=2 will suppress auto row numbering so the programmer can put in custom text in the header.  The default action is to number the rows.  Note:  if rows are added or deleted, it is up to the programmer to update the row headers.  If sequentially number is desired, the message %MAKEDEFHEADERS can be sent specifying only the row headers to be updated.

 

dx        x=0  No action - both scrollbars are shown (this would only be used to place a minus sign in front of the zero), x=1  Hides the vertical scrollbar, x=2 Hides the horizontal scrollbar, x=3 Hides both scrollbars. If a minus sign is placed in front of 0,1,2,3 then the hiding of the scrollbars and selection box is ignored when the grid is out of focus.

 

wx        x=1 Suppress the user's ability to control column width control with the mouse in the column header.

 

jx        x=1 Comma delimited list of column names starting with column 1.  For example, to place titles in the first 3 columns - j1CustID,Name,Position

 

mx        x=1 Inserts a right click menu into the grid from a comma delimited list. A "-" means a separator.   When right clicking a part of the grid which is not on the active edit box, will bring up the menu.  A notification will indicate which menu item is selected and on which cell the right click happened.  An example would be:  m1Insert Row Before,Insert Row After,-,Delete Row. If x=2 then same as above but the right click menu is for the tabs in a multi-sheet workbook. If x=3 then same as above but the right click menu is for an infobar menu (new to version 3).

 

Z SWITCH IS NEW TO VERSION 2.00

 

zx        x=1 create an array which matches the initial dimensioned size of the grid in order to store individual cell formatting information.  Subsequent increases in grid dimensions will result in automatic increases of the format array up to 65,000 rows.  Large databases should not use this option and probably has no need for individual cell formatting

 

V and U SWITCHES NEW TO VERSION 3.00

 

vx        x=1 the cell text and header text will be vertically justified to the bottom of the cell, x=2 the cell text and header  text will vertically justified to the center of the cell, and x=3 the cell text and header text will be justified to the top of the cell. If x is preceeded by a minus sign then multilines will try to be honored else singleline cells will be enforced.

 

ux        x= string. This is to enact undocumented features of MLG programmed for clients for their specific use but will not "muddy" the water for other users.  The client would have the code to turn on their feature.

 

 

Many standard grids can be set up with these switches only - making MLG a breeze.

 

Formatting a Grid Beyond the Switches

 

Formatting can be thought to be in 2 main areas: 1) Entire grid formatting at the row and/or column level is done with the above switches and the %SETGRIDEXSTYLE message which uses the GridInit structure.  2) On a row and column basis using the %SETROWFORMAT and %SETCOLFORMAT messages which use the  RowColDataType structure.

 

1) Normally the switches will be enough flexibility for workhorse grids.  Only if special fonts or background colors are needed will the extended grid formatting be necessary.

 

2) Formating is done on a column and row basis not cell basis.  A row format for a particular attribute will supercede the column format for that attribute.  For example if column 3 is formatted to be a BLUE color and row 15 if formatted to be a RED color then column 3 will be BLUE except for cell(15,3) which will be RED. Normally formatting is done on a Column basis to match the needs of a field in a database.  Row formatting is only needed on special use grid basis such as Foxpro's Edit mode where records for one record is displayed verically.

 

3) For formatting on the cell level you will have to use the z switch to set up the cell formatting array.

 

See the Structures and Equates topic for more information.

 

 

Navigating/Editing the MLG Grid Control

 

The grid can be navigated with the mouse, keyboard and programmically. 

 

1) The mouse navigation is intuitive and follows the Windows standard.

2) The Enter key and Tab key action can be enhanced with the above mentioned "e" and "t" switches but the general actions are as follows:

ENTER key moves down one cell

SHIFT + ENTER key moves up one cell

TAB key moves right one cell

SHIFT + TAB key moves left one cell

3) The %MLG_SETSELECTED message will set a cell as the selected select and move it into visual view if needed.  The %MLG_SETTOPROW and %MLG_SETLEFTCOL messages will scroll the grid.

4) Once the first character is typed into a newly selected cell, the edit box for that cell will gain focus.

 

Reading from the Grid Control

 

Information can be read from a cell's contents, group of cells contents using an array or associated row/col format from header information.  MLG gives the programmer many way to get cell data out of a grid.

 

1) To retrieve the string contents of one cell using a wrapper Powerbasic function (which works in BSTRs) and it's variant using zero terminated strings.

DIM s AS STRING                'retrieved cell content string

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

 

s=MLG_Get(hGrid,row,col) 'the sheet parameter is optional

 

For non Power Basic languages that do not reference BSTRs see the GetZ function

s=MLG_Getz(hGrid,row,col) 'the sheet parameter is optional

 

2) To retrieve the string contents of an array of cells using a Powerbasic subroutine (which works in BSTRs, proprietary array formats)

DIM s(3 TO 7,1 TO 10) AS STRING                'retrieved cell content string using an array

DIM hGrid AS DWORD                                'handle to the grid

 

MLG_GetEx hGrid,s()                                'result is a filled array with corresponding cell contents

 

3) To retrieve the string contents of one cell using a message

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

 

SendMessage hGrid,%MLG_GETCELL,MAKLNG(row,col),VARPTR(s)

 

4) To retrieve the string contents of one cell using a message

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

DIM mylen AS LONG

 

mylen = 256

SendMessage hGrid,%MLG_GETCELLEX,row,col

SendMessage hGrid,%MLG_GETBUFFER,VARPTR(s),mylen

 

For non Power Basic languages that do not reference BSTRs see the GetZ function, and the message %MLG_GETCELLEX which also with the %MLG_GETBUFFER will retrieve the cell contents up to 1024 characters.

 

5) To retrieve the string contents of one cell using a structure. This is mainly for non Powerbasic languages

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM cs AS CELLDATA        '

DIM hGrid AS DWORD        'handle to the grid

 

cd.MyAction = 0         'zero is get

cd.MyRow = 3       

cd.MyCol = 7

cd.MySheet = 0        

 

SendMessage hGrid,%MLG_CELLDATA,VARPTR(cd),VARPTR(s)

 

6) Use an absolute array in Powerbasic

DIM DimRows AS LONG                'row number

DIM DimCols AS LONG                'column number

DIM MyStr AS STRING

DIM a AS LONG

 

a=SendMessage(hGrid,%MLG_GETARRAYPTR,VARPTR(DimRows),VARPTR(DimCols))

DIM GridData(DimRows,DimCols) AS STRING AT a

MyStr = a(3,5)           'Retrieve cell data at row 3, column 5 into MyStr

 

 

 

Writing to the Grid Control

 

Information can be written to a cell's contents, group of cells contents using an array or associated row/col format from header information.  The cell format items that is written is the %MLG_SETROWEXTRA message to retrieve a record number associated with a row.  Writing cell contents can be done with the %MLG_SETCELL message or with two function if Powerbasic is being used as the programming language.

 

1) To write the string contents of one cell using a wrapper Powerbasic function (which works in BSTRs) or the zero terminate string variant of the function

 

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

DIM refresh AS LONG

DIM s AS string                'written cell content string

MLG_Put hGrid,row,col,VARPTR(s),refresh,sheet  'The sheet parameter is optional

For non Power Basic languages that do not reference BSTRs see the PutZ function.

MLG_Putz hGrid,row,col,VARPTR(s),refresh,sheet  'The sheet parameter is optional

 

2) To write the string contents of an array of cells using a Powerbasic subroutine (which works in BSTRs, proprietary array formats)

DIM s(3 TO 7,1 TO 10) AS STRING 'retrieved cell content string using an array

DIM hGrid AS DWORD 'handle to the grid

 

MLG_PutEx hGrid,s(),refresh,sheet 'result is a filled array with corresponding cell contents.  The sheet parameter is optional.

 

3) To set the string contents of one cell using a message for rows less than 65,000 rows

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

 

SendMessage hGrid,%MLG_SETCELL,MAKLNG(row,col),VARPTR(s) 'no auto refresh

SendMessage hGrid,%MLG_SETCELLR,MAKLNG(row,col),VARPTR(s)'will refresh the grid after changing cell

 

4) To set the string contents of one cell using a message for rows more than 65,000 rows

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM hGrid AS DWORD        'handle to the grid

DIM row AS LONG                'row number

DIM col AS LONG                'column number

DIM l AS LONG                'length of s

 

l= LEN(s)

SendMessage hGrid,%MLG_SETBUFFER,s,l

SendMessage hGrid,%MLG_SETCELLEX,row,column 'no auto refresh

SendMessage hGrid,%MLG_SETCELLREX,row,column'will refresh the grid after changing cell

 

The %MLG_SETCELLEX and %MLG_SETCELLREX are used in conjunction with the %MLG_GETBUFFER and MLG_SETBUFFER messages.

 

For non Power Basic languages that do not reference BSTRs see the PutZ function which will set the cell contents using up to a 1024 character null terminated string.

 

5) To set the string contents of one cell using a structure. This is mainly for non Powerbasic languages

DIM s AS ASCIIZ * 256        'retrieved cell content string

DIM cs AS CELLDATA        '

DIM hGrid AS DWORD        'handle to the grid

 

cd.MyAction = 1         'nonzero is getput

cd.MyRow = 3       

cd.MyCol = 7

cd.MySheet = 0

 

s = "Hi"        

 

SendMessage hGrid,%MLG_CELLDATA,VARPTR(cd),VARPTR(s)

 

6) Use an absolute array in Powerbasic

DIM DimRows AS LONG                'row number

DIM DimCols AS LONG                'column number

DIM a AS LONG

 

a=SendMessage(hGrid,%MLG_GETARRAYPTR,VARPTR(DimRows),VARPTR(DimCols))

DIM GridData(DimRows,DimCols) AS STRING AT a

a(3,5) = "Hi"          'Set cell data at row 3, column 5

 

 

Setting up a callback for the MLG Grid Control

 

Your callback function for the window or dialog containing MLG should probably explicit refresh the grid on window or dialog repaints.  Also if the window or dialog is resizable, don't forget to include the resizing code.  See the Callback topic for details.

 

Monitoring Grid Control Notifications

 

MLG has many notifications back to the parent callback function tell the parent "What's going on" with the grid.  The parent callback should poll for needed information so you program can take action when needed.  See the Notification Reference topic for details.

 

MLG Grid Control sample programs

 

Check out the included demo programs to see how all this fits together in order to put My Little Grid to work for you

 

My Little Grid © Copyright 2012, Petroleum Software Solutions LLC. All rights reserved.