You are on page 1of 550

Discovering

Training Guide
Copyright 2004 Data Access Corporation DATA ACCESS WORLDWIDE 14000 S.W. 119 Avenue Miami, Florida 33186 USA Revision Date: January 8, 2004 * This manual applies to Visual DataFlex Revision 9.1 Part No.: 917900 .

COPYRIGHT NOTICE Copyright 2004 DATA ACCESS CORPORATION. All rights reserved. No part of this publication may be reproduced, or distributed, transmitted, transcribed, stored in a retrieval system, or translated into any human or computer language, in any form or by any means, electronic, mechanical, magnetic, optical, manual, or otherwise, or disclosed to third parties without the express written permission of Data Access Corporation, 14000 SW 119 Avenue, Miami, Florida, 33186, USA.

DISCLAIMER Data Access Corporation makes no representation or warranties, expressed or implied, with respect to the software or this publication, or any Data Access Corporation product, including but not limited to warranties of merchantability or fitness for any particular purpose. Data Access Corporation reserves to itself the right to make changes, enhancements, revisions and alterations of any kind to this manual and / or its accompanying software without obligation to notify any person, institution, or organization of such changes, enhancements, revisions, and alterations.

TRADEMARKS DataFlex is a registered trademark of Data Access Corporation. Crystal Reports is a registered trademark of Seagate Corporation Microsoft Windows is a registered trademark of Microsoft. Multi-Edit is a registered trademark of American Cybernetics All other brand and product names are trademarks or registered trademarks of their respective companies.

More Information on Object Oriented Programming & Visual DataFlex


The most current data is posted on our web site. Visit us on the Internet at http://www.dataaccess.com/. Free product upgrades, white papers and even access to the newsgroups are accessible via our web site. The newsgroup has a wealth of information to support all of our products. Additionally, it is a meeting place for the Data Access community. Usersranging in experience from first time computer users to experienced MIS professionalsshare ideas and help each other. This is an invaluable aid during the learning process and will serve as an excellent resource during projects. The newsgroup contains code examples, questions, and answer, etc. from Data Access Corporation and other users. By frequenting the newsgroup, you can learn the language faster and more efficiently. Additionally, once you're confident in your knowledge, you can assist other new users in learning the product as well.

Discovering Visual DataFlex

Table of Contents

Table of Contents
Introduction ..................................................................................................................... 19
How to Use the Manual .........................................................................................................20 Classroom Environment: .......................................................................................................20 Self Taught Method: ..............................................................................................................20 Reading List To Excel Quickly..............................................................................................21

Lesson 1............................................................................................................................ 23 Getting Ready ............................................................................................................. 23


Requirements .........................................................................................................................24 How Items Will Be Displayed ...............................................................................................25 Naming Conventions .............................................................................................................27

Lesson 1 Lab ............................................................................................................... 28


Did You Discover? ................................................................................................................29

Lesson 2............................................................................................................................ 31 Creating Workspaces & Database Files................................................................... 31


Application Building Outline Used by the Labs ....................................................................32 Outline of Project Database Tables .......................................................................................33 Definition Files - .DEF Files..................................................................................................34 Workspace Subdirectories .....................................................................................................40 Starting the Studio .................................................................................................................45 Creating Workspaces .............................................................................................................46 Workspace Pathing ................................................................................................................50 The Goal ................................................................................................................................51 Database Builder Utility ........................................................................................................54 Data Access Corporation 5

Table of Contents

Discovering Visual DataFlex

Database Builders Lock........................................................................................................55 Using Context Sensitive Help ................................................................................................56 The Fields Tab.......................................................................................................................57 Good File Relationships are the Key! ....................................................................................57 The Index Tab........................................................................................................................58 The Parameters Tab ...............................................................................................................59

Lesson 2 Lab ............................................................................................................... 60


Database BuilderBuilding Database Tables.......................................................................63 Copy Test Data ......................................................................................................................63 Creating a Database Table from Scratch................................................................................64 Adding Database File Names Directly into Filelist................................................................66 Use a .DEF File to Create a Database Table..........................................................................68 Did You Discover? ................................................................................................................73

Lesson 3............................................................................................................................ 77 Building Views & Components................................................................................. 77


Selection Lists........................................................................................................................78 Creating New Application .....................................................................................................80 Button Bar .............................................................................................................................88 Tools Pull-Down....................................................................................................................89 Database Selector Tool..........................................................................................................90 DDO Tree Button ..................................................................................................................91 Which Related Field? ............................................................................................................93 Object Properties Tool...........................................................................................................94 Setting Object Properties .......................................................................................................95 Controls Palette Tool .............................................................................................................97 Selecting Tab pages & Tabdialogs ........................................................................................98 Base Tab page........................................................................................................................99 Data Tab page......................................................................................................................100 Using the Data Tab page......................................................................................................101 6 Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Base Containers Tab page ...................................................................................................102 Data Containers Tab-page ...................................................................................................103 Non-Visible Tab page..........................................................................................................104 Object Placement Tools.......................................................................................................106 Alignment Palette Tool........................................................................................................107 Popup Menus .......................................................................................................................108 Arrange Objects Tool ..........................................................................................................109 Nudge Objects Tool.............................................................................................................110 Resolution Check Tool ........................................................................................................111 Object-Order Definition Tool ..............................................................................................112 Drag Lock ............................................................................................................................113 Lost Objects in the Studio (recovering objects not visible on screen) .................................115 Cutting & Pasting Objects to Different Containers..............................................................116 Anchors & Min/Max Size....................................................................................................118

Lesson 3 Lab ............................................................................................................. 121


Creating Selection Lists .......................................................................................................121 Attaching Selection Lists in the DataDictionary..................................................................126 Using Application Wizard ...................................................................................................129 Creating the Empl View Without Wizards .......................................................................135 Attaching a New View to the Application ...........................................................................142 Compiling Code & Testing..................................................................................................143 Adding Pictures to Records .................................................................................................144 Did You Discover? ..............................................................................................................145

Lesson 4.......................................................................................................................... 147 Generated Code ........................................................................................................ 147


Editors Full Source Mode...................................................................................................148 The Big Picture....................................................................................................................149 Activating Views .................................................................................................................153 Creating Templates..............................................................................................................154 Data Access Corporation 7

Table of Contents

Discovering Visual DataFlex

Manual Code That the Studio Can Read..............................................................................155 1. Manual Code in the .SRC file (via the Studio) ................................................................155 2. Manual Code in Visual Objects (via the Studio) .............................................................156 3. Manual Code in the DataDictionary Objects (via the Studio)..........................................157

Lesson 4 Lab ............................................................................................................. 159


Creating an Invoice Style View Template ...........................................................................160 Adding Manual Code to Objects .........................................................................................162 Creating Dept/Empl View Using View Templates ...........................................................172 Grid Options ........................................................................................................................175 Changing Navigation ...........................................................................................................176 Did You Discover? ..............................................................................................................179

Lesson 5.......................................................................................................................... 181 Data Dictionarys Part 1 ........................................................................................... 181


DataDictionary Classes the .DD File ................................................................................182 Business Rules .....................................................................................................................183 DataDictionary Class & DataDictionary Object Differences...............................................184 Building DataDictionarys for Database Files ......................................................................185 Field Settings .......................................................................................................................186 Field Options .......................................................................................................................186 Field Validation ...................................................................................................................188 Modal Objects are Popups...................................................................................................189 Using Validation Tables ......................................................................................................190 Field Masking ......................................................................................................................199 Appearance Tab...................................................................................................................203 Other Tab page ....................................................................................................................205 Checkbox Option .................................................................................................................205 Status Help...........................................................................................................................206 Simple Default Value...........................................................................................................207 Entry/Exit/Validation Messages ..........................................................................................208 8 Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Entry & Exit Messages ........................................................................................................209 Auto-Assigning Numbers.....................................................................................................212 External Structure ................................................................................................................213

Lesson 5 Lab ............................................................................................................. 214


Building DataDictionarys for All Database Files ................................................................214 Setting Field Options ...........................................................................................................215 Setting Field Validation .......................................................................................................216 Validation Tables.................................................................................................................217 Setting Field Masking..........................................................................................................220 Setting Appearance Tab.......................................................................................................221 Setting Status Help ..............................................................................................................222 Field_Default_Value Property.............................................................................................223 Auto-Assigning Numbers.....................................................................................................224 Changing an Objects Class .................................................................................................225 Did You Discover? ..............................................................................................................226

Lesson 6.......................................................................................................................... 227 Data Dictionarys Part 2 ........................................................................................... 227


Methods Tab........................................................................................................................228 Options Tab .........................................................................................................................229 Foreign Field Options ..........................................................................................................229 Error Handling.....................................................................................................................229 Structures Tab......................................................................................................................230 Cascade Delete ....................................................................................................................231 Database Explorer................................................................................................................232

Lesson 6 Lab ............................................................................................................. 233


Methods Tab........................................................................................................................233 Structures Tab......................................................................................................................236 Initializing Auto-Assign Number.........................................................................................237 Did You Discover? ..............................................................................................................238 Data Access Corporation 9

Table of Contents

Discovering Visual DataFlex

Lesson 7.......................................................................................................................... 239 Connecting Parts ...................................................................................................... 239


Differences between the DD Class Files and DDOs ............................................................240 Connecting DDs to DDs within the DataDictionary Class...................................................243 Connecting DDOs to DDOs within the View ......................................................................245 Connecting DEOs to DDOs within the View.......................................................................248 Object Nesting .....................................................................................................................250 Encapsulation of DDO Structures........................................................................................251

Lesson 7 Lab ............................................................................................................. 252


Completing the DDO Structure of Our Views .....................................................................252 Did You Discover? ..............................................................................................................253

Lesson 8.......................................................................................................................... 255 Constraints................................................................................................................ 255


Constraining Records...........................................................................................................256 Constrain_File Property.......................................................................................................256 OnConstrain Procedure........................................................................................................260

Lesson 8 Lab ............................................................................................................. 262


Building Constraints in Selection Lists................................................................................263 Building Constraints that Change ........................................................................................264 Did You Discover? ..............................................................................................................265

Lesson 9.......................................................................................................................... 267 All about Messages................................................................................................... 267


The Link Between Messages and Procedures/Functions .....................................................268 Triggering Messages (Event Driven) ...................................................................................269 Focus Object & Self.............................................................................................................270 Sending a Message ..............................................................................................................271 Access Methods ...................................................................................................................272 Forwarding & Delegating (location of methods) .................................................................273

10

Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Self Access Method Works by Delegation ..........................................................................275 Relaying a Message (Breaking Encapsulation sort of)..................................................276 Neighborhoods.....................................................................................................................278 Broadcast Command............................................................................................................280 Delegate Send ......................................................................................................................281 Using Online Documentation Commands.........................................................................282 Changing Behavior of Existing Messages ...........................................................................283 Augmenting a Message........................................................................................................283 Canceling a Message ...........................................................................................................284 Overriding a Message ..........................................................................................................284 Adding (creating) a Message ...............................................................................................284 Using Online Documentation Procedures.........................................................................285 Using Online Documentation Class Hierarchy .................................................................286 Local Variables....................................................................................................................287 On_Key Commands.............................................................................................................288 Properties (creating) ............................................................................................................289 Properties (Set & Get Commands) ......................................................................................290 Object Properties .................................................................................................................290 Item Properties.....................................................................................................................291 Procedures ...........................................................................................................................292 Functions .............................................................................................................................293 Functions as Expressions .....................................................................................................294 Categories of Messages .......................................................................................................295 Delegation & the Importance of Container Objects.............................................................296 On Procedures (Events)....................................................................................................298 Using OnClick Event ...........................................................................................................299 Using OnActivateApp Event ...............................................................................................299 Using OnMaxText Event .....................................................................................................299 Creating Buttons ..................................................................................................................300 Creating Checkboxes & Radios ...........................................................................................301 Data Access Corporation 11

Table of Contents

Discovering Visual DataFlex

Lesson 9 Lab ............................................................................................................. 303


Checking the Servers: ..........................................................................................................305 Properties (the global variables) .......................................................................................307 Highlighting a Grid Row .....................................................................................................315 Did You Discover? ..............................................................................................................318

Lesson 10........................................................................................................................ 321 Items & Predefined Classes..................................................................................... 321


Items - Zero-Based ..............................................................................................................322 Referencing Items Outside the Current Object ....................................................................323 Grid - Column Properties.....................................................................................................324

Lesson 10 Lab ........................................................................................................... 325


Creating Timers ...................................................................................................................325 Did You Discover? ..............................................................................................................332

Lesson 11........................................................................................................................ 335 Troubleshooting........................................................................................................ 335


Studio Databases..................................................................................................................336 Troubleshooting Hints .........................................................................................................337 1. 2. 3. 4. 5. 6. 7. Compile Each View Separately..................................................................................338 Checking File Relationships.......................................................................................339 Checking for Unique Index on the Parent Related Field ............................................342 Rebuilding the DDO Tree Within the View...............................................................343 Checking the Data ......................................................................................................345 Debugging Compiler Errors & using a .PRN file.......................................................346 Create a Small Test Program......................................................................................349

8. The Debugger Runtime problems:...............................................................................350

Lesson 11 Lab ........................................................................................................... 352


Debugger Breakpoints .........................................................................................................352 Debugger Watches...............................................................................................................353 Did You Discover? ..............................................................................................................354 12 Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Lesson 12........................................................................................................................ 355 Waves and Bitmaps.................................................................................................. 355


Displaying Bitmaps from a Database File............................................................................356 Displaying Bitmaps as a Backdrop ......................................................................................357 Wave Files - Applications with Sound.................................................................................359 Creating a Wave File ...........................................................................................................360 Embedded Bitmaps..............................................................................................................361

Lesson 12 Lab ........................................................................................................... 363


Did You Discover? ..............................................................................................................364

Lesson 13........................................................................................................................ 365 DDs Local Buffers & Procedures .......................................................................... 365
Changing Field Values - DataDictionarys Local Buffers ...................................................366 Optimizing Field_Exit_Msg ................................................................................................368 Important DataDictionary Procedures .................................................................................373 Procedure Creating ..............................................................................................................374 Procedure Update & Backout ..............................................................................................375 Functions Validate_Save & Validate_Delete.......................................................................376 Procedures Save_Main_File & Delete_Main_File ..............................................................377

Lesson 13 Lab ........................................................................................................... 378 Lesson 14........................................................................................................................ 385 Classes Within the Studio........................................................................................ 385
Building New Subclasses.....................................................................................................386 Switching Classes the Studio Uses ......................................................................................388 Creating SubClass Layering.................................................................................................389 Templates (Speeding Development)....................................................................................392 DFS files ..............................................................................................................................393 Saving a DFS: ......................................................................................................................394 Inserting a DFS ....................................................................................................................395

Data Access Corporation

13

Table of Contents

Discovering Visual DataFlex

DFO Files ............................................................................................................................396 Using Subclasses in the Studio ............................................................................................399 Local & Global directories ..................................................................................................401

Lesson 14 Lab ........................................................................................................... 402


Steps to Add a New Class to the Controls Palette ...............................................................402 Did You Discover? ..............................................................................................................407

Lesson 15........................................................................................................................ 409 Batch Processing....................................................................................................... 409


Business Process Objects (BPO) .........................................................................................410 Batch Process using DDOs ..................................................................................................412

Lesson 15 Lab ........................................................................................................... 414


BPO to Update Company Fields in Dept Records ...............................................................414 BPO to Log Employees Out at End of Day .........................................................................417

Did You Discover?.................................................................................................... 421 Lesson 16........................................................................................................................ 423 Reporting................................................................................................................... 423


Comparing the Reporting Methods......................................................................................424 BasicReport Class................................................................................................................424 WinReport (WinPrint) .........................................................................................................424 CrystalReport Class .............................................................................................................424

Lesson 16 Lab ........................................................................................................... 425


Using WinPrint Report Wizard............................................................................................425 Using Crystal Report Wizard...............................................................................................432 Adding a Print Button to an Entry View..............................................................................438 Did You Discover? ..............................................................................................................444

Appendix A..................................................................................................................... 445 Did you Discover Answers................................................................................... 445


Lesson 1 - Discover Answers...............................................................................................446 14 Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Lesson 2 - Discover Answers...............................................................................................447 Lesson 3 - Discover Answers...............................................................................................449 Lesson 4 - Discover Answers...............................................................................................452 Lesson 5 - Discover Answers...............................................................................................454 Lesson 6 - Discover Answers...............................................................................................455 Lesson 7 - Discover Answers...............................................................................................456 Lesson 8 - Discover Answers...............................................................................................457 Lesson 9 - Discover Answers...............................................................................................459 Lesson 10 - Discover Answers.............................................................................................463 Lesson 11 - Discover Answers.............................................................................................464 Lesson 12 - Discover Answers.............................................................................................465 Lesson 13 - Discover Answers.............................................................................................466 Lesson 14 - Discover Answers.............................................................................................468 Lesson 15 - Discover Answers.............................................................................................471 Lesson 16 - Discover Answers.............................................................................................472

Appendix B..................................................................................................................... 473 Problems & Solutions .............................................................................................. 473


Popup Messages/Questions..................................................................................................474 On_Key {to object} parameter ...........................................................................................475 Auto Activate First View .....................................................................................................476 ToolTip................................................................................................................................477 Multiple directories in a Path...............................................................................................478 Checking filename is only 15 Characters.............................................................................479 Procedure Set.......................................................................................................................480 Retrieving data from the Windows Registry........................................................................481 Deployment..........................................................................................................................482 Saving Resources:................................................................................................................483 Customizing error messages: ...............................................................................................484 Adding your own Utilities....................................................................................................485 Data Access Corporation 15

Table of Contents

Discovering Visual DataFlex

Maintain Class-Lists ............................................................................................................486 Field_Default_Value Property.............................................................................................487

Appendix C..................................................................................................................... 489 Core Information ..................................................................................................... 489


Accelerator Keys .................................................................................................................490 Studio Hot Keys...................................................................................................................492

Visual DataFlex Core Information ......................................................................... 495


The Main Utilities................................................................................................................496 File Relationships ................................................................................................................497 Some Sample Relationships.................................................................................................498 Data Integrity.......................................................................................................................500 What Happens During a Save to Keep the Related Fields the Same?..................................501 File Normalization ...............................................................................................................502 DataFlex File Extensions .....................................................................................................503 Maintenance of Files............................................................................................................504

OOP Core Information............................................................................................ 506


Definition of Classes and Objects:.......................................................................................507 Procedures & Local Variables .............................................................................................510 Multiple DataDictionary Objects (DDOs) ...........................................................................512 Encapsulation.......................................................................................................................514 Message Forwarding............................................................................................................516 Event Driven........................................................................................................................518 Building New Classes:.........................................................................................................519 The UIMS............................................................................................................................520 Summary..............................................................................................................................522 Prior DataFlex Users ...........................................................................................................523 Prior DataFlex Procedural Users .........................................................................................523 Prior DataFlex Character-Based OOP Users .......................................................................523 Everyone New to VDF8 ......................................................................................................523 16 Data Access Corporation

Discovering Visual DataFlex

Table of Contents

Glossary.......................................................................................................................... 525 Evaluation ...................................................................................................................... 549

Data Access Corporation

17

Table of Contents

Discovering Visual DataFlex

18

Data Access Corporation

Discovering Visual DataFlex

Introduction

Introduction
Discovering Visual DataFlex is a training guide designed to introduce users to Visual DataFlex object-oriented Windows programming. The manual was written for Visual DataFlex to be used in a classroom environment or as a Self-taught study guide. Visual DataFlex revision 9.1 will be required when using this manual since the packages and features of this revision are used. Some familiarity with DOS, Microsoft Windows and general computer skills is necessary to accomplish the labs. The manual covers items ranging from beginning to advanced level skills. Students with prior object oriented and or DataFlex programming experience may wish to jump over sections. Review the topics covered in a Lesson to determine if you wish to skip a lesson. If you do skip Lessons, the Lab sections normally will have to be completed since each Lab builds on prior work.

Data Access Corporation

19

Introduction

Discovering Visual DataFlex

How to Use the Manual


The manual covers topics that will be helpful to a broad range of reader experiences. Some of the topics will be simple and some more advanced. If you fall into any of the following categories, you may find it helpful to read the appropriate Core Information sections in Appendix C before continuing. New DataFlex Users Procedural Programmers Appendix C DataFlex Core Information Appendix C OOP Core Information

DOS Object Oriented Programmers Appendix C OOP Core Information Prior VDF Users Appendix C Prior VDF Users

Classroom Environment: A hands-on classroom is the recommended setting for using this manual. The Self-study method is possible, but classroom interaction and the aid of an instructor will enhance the learning process. If you are interested in locating a class near you, please call one of our Training Centers. Visit our Web site for contact information.

Self Taught Method: This manual can also be used as a Self-study guide. Before beginning, check the next few pages to ensure you have all needed equipment/software. The manual is broken up into Lessons, Labs and Did You Discover? questions. The Did You Discover? sections are NOT quizzes! Some of the topics are not even covered in the lesson. They are intended as extra information and to challenge the students. Do not use them as a test of your knowledge, but as an additional learning tool to cover more information. You will find the answers to these questions in Appendix A. Included on the training CD that comes with the training manual is a FinishedExampleZip.Exe file. This Self-extracting zip file contains all the files created throughout the course of the manual, as they will appear at the end of the manual. If you have any problems, unzip this file into a separate directory so you may compare your files to them.

20

Data Access Corporation

Discovering Visual DataFlex

Introduction

Reading List To Excel Quickly


A well thought-out training plan must be implemented. This plan should include all of the DataFlex documentation. The documentation is full of fabulous examples. No matter if you attend a class or use this manual as a Self-study guide, this recommended study list would speed you along to success. Before attending class: Review Appendix C sections appropriate for your experience level Read entire Visual DataFlex Quick Start manual Run all Example Applications. This will demonstrate the look and feel for the many window controls available. The examples are available by clicking Start | Programs | Visual DataFlex | Sample Applications. After class: Review this training manual Read entire Visual DataFlex Developing Applications manual Read entire Language Guide in the on-line help Experiment with the code from the Example Applications. When changing the Workspace in the Studio you will see all the example workspaces. The manual code additions in these samples are full of useful ideas. These examples are also great areas to test and learn new features. If you would like to experiment with a new property simply test it out in one of the examples.

Data Access Corporation

21

Introduction

Discovering Visual DataFlex

More books to read: Book Title The Windows Guidelines for software design Visual Interface Design Windows 32 API Bible XML in 24 Hours MSDN (internet) Ask your Bookstore for this ISBN number 1-55615-679-0 0-471-13419-8 1-57169-009-3 0672319500
http://msdn.microsoft.com

22

Data Access Corporation

Discovering Visual DataFlex

Lesson 1 Getting Ready

Lesson 1
Getting Ready
This lesson ensures that we have the required equipment and software. The setup CD that comes with this manual has all the needed files that are used throughout the manual

Topics in this Chapter:


Requirements How Items will be Displayed Naming Conventions Lab1

Data Access Corporation

23

Lesson 1 Getting Ready

Discovering Visual DataFlex

Requirements
Computer Intel Pentium based PC or higher Computer mouse installed 32 Meg RAM (64 MB NT; 2000; XP; 2003) bare minimum Microsoft Windows 98 SE; ME; NT4; 2000, XP, 2003 Visual DataFlex revision 9 .1 with Documentation installed. (200 MB Hard Disk space required for full installation) Crystal Reports & DataFlex for Crystal Driver (this is optional if you do not have these products you may skip this section in the reporting lesson) SVGA 800x600 or higher resolution
Figure 1

Note: The Workspace Wizard uses theProjects folder as the default location for new workspaces. This manual will use this projects directory, but it is suggested that you change this location and point it to an area where you wish all your development work to be done.

* New service packs (when available) can be downloaded from http://www.dataaccess.com/ web page from the Download pull-down area.

24

Data Access Corporation

Discovering Visual DataFlex

Lesson 1 Getting Ready

How Items Will Be Displayed


Instructions/Commands
Instructions requiring action will be displayed with a bold top & bottom line. Completion of these instructions is required for the sample program to operate. Sometimes symbols are used. Example: [ = Click left mouse button File | Options Means select File from the menu bar and then select Options from the pull down.

Symbols: Many look very similarattention to detail is necessary! Symbol Description Click the right mouse button. Click the left mouse button. Double click the left mouse button. Press the Escape Key. Press the Enter Key (Return Key) Control Key Press the Shift Key Press the Tab Key Press the Page Up Key Press the Page Down Key Left Dragging: Hold left mouse key down while moving the mouse to a new location and then releasing.

] [ / E R C S T u d ;

Data Access Corporation

25

Lesson 1 Getting Ready

Discovering Visual DataFlex

Informative Text:

Informative data will be displayed in this font and will be used to explain topics. Do not confuse informative text with instructions/commands. Text in this printing style is used to explain topics. Even if screen shots are included no action is required on your computer.

Code:

The lab exercises will be making many modifications to the generated code. A file called Code_Mod.TXT is available on the CD that accompanies this manual. When asked to make code modifications, open this file in your editor and cut and paste the modifications into the application. Code Available = Code_Mod.TXT
Object Outer_container is a dbcontainer3d // Areas that are shadowed are areas of interest, // or to show where code has been added or modified. // The comment partial code addition/modification will appear next to addition/modification partial // a line when only part of the code has been added or modified. Object Customer_Name is a dbForm Set Location to 5 12 Set Size to 45 5 : // A colon is used to show the code has been abbreviated End_Object

Notes:
Notes will be displayed like this. If a note is directed to only certain students (example: for users of prior revisions of DataFlex) it will state this in parentheses at the beginning of the note so students can skip over notes that do not pertain to them.

26

Data Access Corporation

Discovering Visual DataFlex

Lesson 1 Getting Ready

Naming Conventions
It is recommended that you use Hungarian notation when naming classes; objects; properties; constants and variables. This will increase readability of your code and will eliminate the problem of duplicating names.

Prefix c o p C_ g

Meaning Class Object Property Constant Global variable Local variable (no prefix) SubPrefix (for properties; constants; global and local variables b d h i n r s v Sub-SubPrefix (for handles) ho ie

Sample cSuperEditor oPrintButton piCounter C_Version gsMaxUsers iTeamCount Meaning Boolean (true/false) Date Handle Integer Number Real String Variant Handles for object IDs Integer enumerators*

All prefixes except for Constants (C_) are lowercase. * Enumerators are the replacement value of a parameter constant.

Data Access Corporation

27

Lesson 1 Lesson 1 Lab

Discovering Visual DataFlex

Lesson 1 Lab
Description: Preparation work to get hardware and software ready:

Tasks: Ensure that your computer has VDF 9.1 installed and you meet all the hardware and software requirements listed in this lesson.

28

Data Access Corporation

Discovering Visual DataFlex

Lesson 1 Lesson 1 Lab

Did You Discover?


1. Which Appendix in this manual has basic information on the DataFlex language?

2. Create names for the following items:

Sample Name A Local Boolean Variable A Local Integer Variable A Global Integer Variable A Global String Variable A Class An Object An Integer Property A String Property A Variant Property A Constant A Local Integer Variable (used to hold an object ID)

Data Access Corporation

29

Lesson 1 Lesson 1 Lab

Discovering Visual DataFlex

30

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Lesson 2
Creating Workspaces & Database Files
This lesson gives a brief outline of the application to be created. Creating workspaces and the use of Database Builder for creating the database structure are covered.

Topics in this Chapter:


Application Building Outline used by the Labs Outline of Project Database Tables Definition Files - .DEF Files Workspace Subdirectories Starting the Studio Creating Workspaces Workspace Pathing The Goal Database Builder Utility Database Builders Lock Using Context Sensitive Help The Field Tab Good File Relationships are the Key! The Index Tab The Parameters Tab Lab 2 Database Builder - Building Database Tables Copy Test Data Creating a Database Table from Scratch Adding Database File Names Directly into Filelist Use a .DEF File to Create a Database Table

Data Access Corporation

31

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Application Building Outline Used by the Labs


We will be using the Visual DataFlex tools in the next few lessons to accomplish all of these steps from within the Studio. 1. Create a Workspace 2. Create Data Files 3. Create simple Views (create simple data entry code first to help fine-tune our Data Dictionarys) 4. Create Data Dictionarys. These contain our business rules such as: Auto-Assign Employee number on new saves Set default values Set up Status Help lines Set up Entry options such as CapsLock and AutoFind Field Masking Validation Tables Error Messages

5. Create Templates 6. Create complex Views (add manual code to increase functionality) 7. Add more bells and whistles to our existing application 8. Create Batch Processing 9. Multiple methods of creating reports

32

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Outline of Project Database Tables


A brief description of the files: Filenames & #s COMPANY (#1) DEPT (#10) EMPL (#20) TIMECARD (#60) WK_SUM(#80) SYSFILE (#200) Description Company information Department information with total number of employees. Employee Detail information Time records to log time in and out Collection of daily times A one-record file that stores system information, such as the next employee number.

Arrow points to parent file: #200 - SysFile #1 - Company File

#10 - Dept File

#20 - Empl File

#80 - Wk_Sum File

#60 - TimeCard File

Note: The Company file will NOT be added until a later lesson.

Data Access Corporation

33

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Definition Files - .DEF Files


DEF files are ASCII files that show field, index, and file relationship information. They are displayed here simply for reference. We will use them later in the lab to quickly create our files.
Company.DEF
----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 20:18 PAGE: 1 FILE DEFINITION FOR FILE: COMPANY (# 1) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : Company USER DISPLAY NAME : Company DATAFLEX FILE NAME : COMPANY ----------------------------------------------------------------------------RECORD LENGTH : 34 ( USED: 34 ) MAX NUMBER OF RECORDS : 10000 ( USED: 1 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) FILE LOGIN PARAMETER : SYSTEM FILE : NO ----------------------------------------------------------------------------NUM --1 2 3 FIELD NAME --------------COMPANY_CODE NAME TOTAL_BUDGET TYPE SIZE OFFST IX ---- ----- ----- -ASC 4 ASC 25 5 NUM 8.2 30 RELATES TO FILE.FIELD --------------------------------1 1

INDEX# FIELDS DES U/C ------ --------------- --- --1 CODE NO YES

LENGTH LEVELS SEGMENTS MODE ------ ------ -------- ------4 2 1 ON-LINE

34

Data Access Corporation

Discovering Visual DataFlex Dept.DEF

Lesson 2 Creating Workspaces & Database Files

----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 12:38 PAGE: 1 FILE DEFINITION FOR FILE: DEPT (# 10) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : Dept USER DISPLAY NAME : Dept DATAFLEX FILE NAME : DEPT ----------------------------------------------------------------------------RECORD LENGTH : 1152 ( USED: 1053 ) MAX NUMBER OF RECORDS : 100 ( USED: 3 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES In another lab, we will add LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES another field and link it to TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) the Company file. FILE LOGIN PARAMETER : SYSTEM FILE : NO ----------------------------------------------------------------------------NUM --1 2 3 4 5 FIELD NAME --------------DEPT_CODE NAME NUMBER_OF_EMPL BUDGET COMMENTS TYPE SIZE OFFST IX ---- ----- ----- -ASC 4 1 1 ASC 20 5 NUM 2.0 25 2 NUM 6.2 26 TEX 1024 30 RELATES TO FILE.FIELD ---------------------------------

INDEX# FIELDS DES U/C ------ --------------- --- --1 DEPT_CODE NO YES 2 NUMBER_OF_EMPL RECNUM NO NO NO NO

LENGTH LEVELS SEGMENTS MODE ------ ------ -------- ------4 1 1 ON-LINE 4 1 2 ON-LINE

Data Access Corporation

35

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex Empl.DEF


----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 15:40 PAGE: 1 FILE DEFINITION FOR FILE: EMPL (# 20) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : Empl USER DISPLAY NAME : Employee DATAFLEX FILE NAME : EMPL ----------------------------------------------------------------------------RECORD LENGTH : 512 ( USED: 406 ) MAX NUMBER OF RECORDS : 10000 ( USED: 10 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) FILE LOGIN PARAMETER : SYSTEM FILE : NO ----------------------------------------------------------------------------NUM --1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 FIELD NAME --------------CODE LAST_NAME FIRST_NAME SOC_SEC_NUMBER ADDRESS CITY ST ZIP PHONE HIRE_DATE DEPT PAY_TYPE PAY_RATE LOGGED TERM_DATE COMMENTS PICTURE_ID TYPE SIZE OFFST IX ---- ----- ----- -NUM 4.0 1 1 ASC 20 3 2 ASC 20 23 2 ASC 9 43 3 ASC 30 52 ASC 12 82 ASC 2 94 ASC 10 96 ASC 14 106 DAT 6 120 ASC 4 123 3 ASC 1 127 NUM 6.2 128 ASC 1 132 4 DAT 6 133 TEX 256 136 ASC 15 392 RELATES TO FILE.FIELD ---------------------------------

DEPT.FIELD_1 (10,1)

INDEX# FIELDS DES U/C ------ --------------- --- --1 CODE NO NO 2 3 LAST_NAME FIRST_NAME DEPT LAST_NAME FIRST_NAME SOC_SEC_NUMBER LOGGED LAST_NAME FIRST_NAME RECNUM SOC_SEC_NUMBER NO NO NO NO NO NO NO NO NO NO NO YES YES YES YES YES NO NO NO NO NO NO

LENGTH LEVELS SEGMENTS MODE ------ ------ -------- ------2 2 1 ON-LINE 40 53 4 5 2 4 ON-LINE ON-LINE

44

ON-LINE

ON-LINE

36

Data Access Corporation

Discovering Visual DataFlex TimeCard.DEF

Lesson 2 Creating Workspaces & Database Files

----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 12:38 PAGE: 1 FILE DEFINITION FOR FILE: TIMECARD (# 60) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : TimeCard USER DISPLAY NAME : TimeCard DATAFLEX FILE NAME : TIMECARD ----------------------------------------------------------------------------RECORD LENGTH : 384 ( USED: 265 ) MAX NUMBER OF RECORDS : 10000 ( USED: 0 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) FILE LOGIN PARAMETER : SYSTEM FILE : NO ----------------------------------------------------------------------------NUM --1 2 3 4 5 6 7 FIELD NAME --------------EMPL_CODE DATE HOURS MINUTES IN_OR_OUT MEMO REASON_CODE TYPE SIZE OFFST IX ---- ----- ----- -NUM 4.0 1 1 DAT 6 3 1 NUM 2.0 6 1 NUM 2.0 7 1 ASC 1 8 3 TEX 256 9 ASC 1 265 4 DES --NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO U/C --NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO NO RELATES TO FILE.FIELD --------------------------------EMPL.FIELD_1 (20,1)

INDEX# FIELDS ------ --------------1 EMPL_CODE DATE HOURS MINUTES IN_OR_OUT RECNUM 2 DATE HOURS MINUTES EMPL_CODE RECNUM IN_OR_OUT EMPL_CODE RECNUM REASON_CODE EMPL_CODE RECNUM

LENGTH LEVELS SEGMENTS MODE ------ ------ -------- ------11 3 6 ON-LINE

10

ON-LINE

ON-LINE

ON-LINE

Data Access Corporation

37

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex Wk_Sum.DEF


----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 12:38 PAGE: 1 FILE DEFINITION FOR FILE: WK_SUM (# 80) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : Wk_Sum USER DISPLAY NAME : Wk_Sum DATAFLEX FILE NAME : WK_SUM ----------------------------------------------------------------------------RECORD LENGTH : 25 ( USED: 22 ) MAX NUMBER OF RECORDS : 60000 ( USED: 0 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) FILE LOGIN PARAMETER : SYSTEM FILE : NO ----------------------------------------------------------------------------NUM --1 2 3 4 5 6 7 8 9 10 11 FIELD NAME --------------EMPL_CODE YEAR WEEK_NUMBER SUN_HOURS MON_HOURS TUE_HOURS WED_HOURS THU_HOURS FRI_HOURS SAT_HOURS WEEKLY_TOTAL TYPE SIZE OFFST IX ---- ----- ----- -NUM 4.0 1 1 NUM 4.0 3 1 NUM 2.0 5 1 NUM 2.2 6 NUM 2.2 8 NUM 2.2 10 NUM 2.2 12 NUM 2.2 14 NUM 2.2 16 NUM 2.2 18 NUM 4.2 20 2 DES --NO NO NO NO NO U/C --NO NO NO NO NO RELATES TO FILE.FIELD --------------------------------EMPL.FIELD_1 (20,1)

INDEX# FIELDS ------ --------------1 EMPL_CODE YEAR WEEK_NUMBER 2 WEEKLY_TOTAL RECNUM

LENGTH LEVELS SEGMENTS MODE ------ ------ -------- ------5 3 3 ON-LINE

ON-LINE

38

Data Access Corporation

Discovering Visual DataFlex SysFile.DEF

Lesson 2 Creating Workspaces & Database Files

----------------------------------------------------------------------------DATE: 06/01/2002 TIME: 12:38 PAGE: 1 FILE DEFINITION FOR FILE: SYSFILE (# 200) ----------------------------------------------------------------------------DRIVER NAME : DATAFLEX FILE ROOT NAME : SysFile USER DISPLAY NAME : SysFile DATAFLEX FILE NAME : SYSFILE ----------------------------------------------------------------------------RECORD LENGTH : 39 ( USED: 39 ) MAX NUMBER OF RECORDS : 1 ( USED: 0 ) FILE COMPRESSION : NONE RE-USE DELETED SPACE : YES LOCKING TYPE : FILE HEADER INTEGRITY CHECKING : YES TRANSACTION TYPE : CLIENT ATOMIC RECORD IDENTITY INDEX : 0 ( 0 , 0 ) FILE LOGIN PARAMETER : SYSTEM FILE : YES ----------------------------------------------------------------------------NUM --1 2 3 FIELD NAME --------------CORP_NAME LAST_EMPL_NUM LOCAL_STATE TYPE SIZE OFFST IX ---- ----- ----- -ASC 35 1 NUM 4.0 36 ASC 2 38 RELATES TO FILE.FIELD ---------------------------------

Data Access Corporation

39

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Workspace Subdirectories
A workspace is the work area for your application. Workspace subdirectories will keep all of our application files neatly separated. The directory structure after a new workspace is created for the ABC Corporation would have eight subdirectories (AppHtml; AppSrc; Bitmaps; Data; DDSrc; Help; IdeSrc; Programs).

Figure 2

Within the Studio:


Tools | Configure Environment | General Tab

Used by the Workspace the Look at Wizards as the default area options to create the workspace dialog Close the

Figure 3

Note Keeping the workspace name and application name the same will simplify things. 40 Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

To separate your many applications into structured grouping you can create multiple divisions to organize your workspaces. The Order workspace is organized under the DAW | Examples | Windows divisions. It was created in the sub-directory structure of Examples | Windows | Order

File | Select Workspace After you are done looking at this dialog then close it using the X close button at the top.

Figure 4

Figure 5

Data Access Corporation

41

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

This chart shows in which subdirectory your files will be located. Workspace Directory: AppHtml AppSrc Extension & Description of Files Contained in the Directory: Application Html (for web applications) Studio Data Files abData CFG WorkspaceName.cfg holds embedded resources DG Dialog files INC Include files MN Menu files Precompiled package files: FLP Precompiled package (with P option) PKI Precompiled package (with P option) FLD Precompiled package (with PZ option) PKD Precompiled package (with PZ option) PRP Precompiled package (with PF option) PKG Custom Package/Class files PRN Compiling list when f option used RV Report View files SL Selection list files SRC Source code files TRC Trace files created by using debugger TRE Studios temporary files VW View files Bitmap files the application uses, such as Company Logos; icons (.ICO); and movies. These are only needed if they where NOT embedded within the EXE. User Files? No No

Bitmaps

Yes, unless embedded

42

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Workspace Directory: Data

Extension & Description of Files Contained in the Directory: Filelist.CFG Lists all data file names DAT Data files HDR Header files K# Index (Key) files RPT Crystal Report files TAG Field name file VLD Variable Length Data (If using other databases, they would also be stored here) DataDictionary Data Files DDDATA DD Data Dictionary files FD File Definition DEF ASCII Definition files Help files created for your application IDEClasses.DFC Studios Class-List for workspace BMP Bitmaps for the New Classes DFC DataFlex Class files DFO DataFlex Object Preference files DFS DataFlex Subcomponent files TPD Template Dialog files TPL Template List files TPR Template Report files TPV Template View files EXE OCP WS Compiled Code ActiveX control preference files Holds pathing & application information

User Files? Yes

DDSRC

No

Help IDESrc

Yes No

Programs

Yes

Studio temp file to compile a single program idetestrun_X.exe

Note: The workspace subdirectories help the developer separate the files required by the user from the files only required by the developer. The last column indicates the directories required by the End Users. These directories must be deployed with your application. Data Access Corporation 43

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

44

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Starting the Studio


The Studio gives the developer quick access to the utilities and tools.

[ Start [ Programs [ Visual DataFlex 9.1 [ Visual DataFlex Studio

Figure 6

Data Access Corporation

45

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Creating Workspaces
Our first task when starting a new application will be to create a new workspace.

File | New Workspace

Figure 7

46

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

[ Learn More [ Next

Figure 8

Do not miss these two periods!

[ Learn More Class.VDF. Finished Example Finished Example [ Next

Figure 9

Data Access Corporation

47

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

[ Learn More [ Next button

The prompt button allows you to browse directories to make a selection. We will leave the default location.
Figure 10 Warning: Most of the time you will have your own directory area where you will store your workspaces.

[ Learn More [ OK

Figure 11

48

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Upon completion of the workspace wizard, this is what has happened: Our new Finished Example workspace directory and eight subdirectories have been created. The Studio default workspace has been changed to our newly created workspace. A few files have been inserted into these subdirectories that are used by the Studio (abData & ddData) and other files such as a blank Filelist.CFG. (If any of these files already exist in these directories, they will NOT be over-written). The new files that will be used to create all new workspaces are copied from the \Usr\New directory. The workspace has been registered in the workspace.ini file located in the \Bin directory. This allows the Studio to keep track of all workspaces and can be modified using the Studios Workspace pulldown menu and option Properties or Workspace Manager.

Figure 12

A WorkspaceName.WS file was created in the \Programs directory. This file is shown on the next page.

Data Access Corporation

49

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Workspace Pathing In order to locate files a special .WS file is created in the \Programs directory. The contents are listed below. . i.e.; The DataPath is used to find the database table files. Multiple directories can be listed by separating them with a semicolon. Class.VDF.Finished Example.WS
[Workspace] Home=..\ AppSrcPath=.\AppSrc AppHTMLPath=.\AppHtml BitmapPath=.\Bitmaps IdeSrcPath=.\IdeSrc DataPath=.\Data DDSrcPath=.\DdSrc Description=Finished Example HelpPath=.\Help ProgramPath=.\Programs FileList=.\Data\Filelist.cfg

The Studio interface to update this file:

Workspace | Workspace Manager

Figure 13 50 Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

The Goal
Looking at the finished application will give us a better understanding of the code that we will be building. The manual code additions will be more meaningful if you see the finished application in operation.

We will use a Self-extracting zip file that will install the finished version of the program. This will allow us to see what we are building and have completed files to compare to if help is needed.

Close all VDF utilities Insert training CD into drive [ Start [ Run Use the browse button to point to your CD drive then double click on Finished ExampleZip.EXE Do not change Unzip to folder unless you created the workspace in a different location [ Unzip Button

Figure 14

Data Access Corporation

51

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Open Windows Explorer Go to the Drive and directory where your workspace is created [ Finished Example [ Programs / Finished Example.exe

Figure 15

52

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

We will be building 6 views and 2 reports plus miscellaneous test views.


Select Views from the menu to open each of the views and see how the application operates. Add a few records if you like. Close the application and return to the Studio

Figure 16

Things to note: New Employee records automatically have the next available number assigned The Departments and Employee Views show only the associated Employees in the grid that belong to the Department record in the top of the view. Click on the prompt buttons. These are buttons with three dots on them . Running totals in the Dept and Company records update when a new Empl/Dept record is updated. Process a few employees out with the Logging out View Then use the button to batch process the remaining employees out. Use the Report Pull-Down to check out the reports that will be created.

Data Access Corporation

53

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Database Builder Utility


Database Builder utility can be started from the Studio or from the Windows Start Menu. When started from the Studio the workspace is synchronized with the Studios workspace. This utility is where database files and DataDictionary class files are created and maintained.

Database | Database Builder

Figure 17

combo box will also open files

File | Open [ Empl File [ Open Button

Figure 18 54 Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

Database Builders Lock

Figure 19

The Green/Red lock toggles to indicate when the file structure (first 3 tabs) can be altered. Green indicates an exclusive lock on the file, giving a green light to change the file structure.

The last four tabs will be disscussed in a later lesson. They create the DataDictionary file (.DD). Changes to these last four tabs can be made with the lock set to red or green.

Data Access Corporation

55

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

Using Context Sensitive Help


On-line Help is available to obtain a full explanation of any Database Builder option.

[ Lock Icon (so it is green) [ Parameters Tab [ Client Atomic 1 Scroll down to the Transaction Type explanation

Figure 20

56

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

The Fields Tab

[ Fields Tab

This tab allows changes to the fields in the database.


Figure 21

Good File Relationships are the Key!


The Relates to column in the grid above is the key to success in VDF. If you are unsure on how to set up file relationships read the File Relationship section in Appendix C and look up this topic in the other DataFlex manuals. The basic building blocks of a VDF application are based on File relationships. They must be created correctly!

Data Access Corporation

57

Lesson 2 Creating Workspaces & Database FilesDiscovering Visual DataFlex

The Index Tab

[ Index Tab

Figure 22

Spinform to cycle through the 15 indexes

A prompt is available to make adding segments to an index easier. Click on the Name>> label to popup the field list. Pressing F4 (the prompt key) or Insert Button also brings up this popup.

58

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Creating Workspaces & Database Files

The Parameters Tab

[ Parameters Tab

Remember on-line help is always available.

Figure 23

Data Access Corporation

59

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

Lesson 2 Lab
Description: Practice creating a workspace and database tables:

Tasks: Create a new workspace for our application.

Within the Studio: File | New Workspace

Figure 24

60

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

[ Next

Figure 25

[ Select Group [ Class [ VDF [ OK CorporationX Record Keeping for CorporationX [ Next

Figure 26

Data Access Corporation

61

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

[ Next button

The prompt button allows you to browse directories to make your selection.

Figure 27

[ OK

Figure 28

62

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Database BuilderBuilding Database Tables


Visual DataFlex uses a file called Filelist to store the names of all database tables used in an application. There are three ways to add database table names to the Filelist.cfg file. 1. Create a database table from scratch 2. Add the database file name directly to filelist 3. Use a .DEF file to create a database table File Number 10 20 60 80 200 Rootname Dept Empl TimeCard Wk_Sum SysFile DEF Filename Dept.DEF Empl.DEF TimeCard.DEF Wk_Sum.DEF SysFile.DEF The file numbers are important because they will determine the relationships among the files

Copy Test Data


To speed things along we will be using a Self-extracting .ZIP file that will copy test data and .DEF files into our workspace. This test data will be helpful in seeing the operation of our views that we create in the next few lessons.
Close all VDF utilities Insert training CD into drive [ Start (MS Windows) [ Run Use the browse button to point to your CD drive then double click on CorporationXZip.EXE Do not change Unzip to folder unless you created the workspace in a different location [ Unzip Button

Figure 29

Data Access Corporation

63

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

Creating a Database Table from Scratch Our first added file will be the SysFile.

From the Studio:


Database | Database Builder

Figure 30

64

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Within DBB
File | New 200 SysFile [ OK

Figure 31

Enter the fields from the chart [ Parameters tab [ System file File | Save [ OK [ OK

Figure 32

Field Name Corp_Name Last_Empl_Num Local_State

Type ASCII NUMERIC ASCII

Size 35 4 2

Data Access Corporation

65

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

Adding Database File Names Directly into Filelist If the database tables already exist, you can just add them to the current Filelist.CFG. This will not wipe out the existing data in these files.

Filelist | New Entry

Figure 33

10 Dept Department Dept [ OK

Figure 34

66

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Filelist | New Entry 20 Empl Employee Empl [ OK

Figure 35

Data Access Corporation

67

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

Use a .DEF File to Create a Database Table Loading TimeCard & Wk_Sum files from .DEF files will create empty database tables with defined fields and indexes.

File | Load DEF

Figure 36

80 Wk_Sum Wk_Sum.def [ OK

Figure 37 Warning! Make sure the file number is correct according to the chart or you will get an Unable to commit the Structure changes error. This error says that the .DEF that you are using has a relationship to a file number that does not exist.

68

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

[ Save Button

Figure 38

[ OK [ OK (on the next dialog)

Figure 39

Data Access Corporation

69

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

File | Load DEF 60 TimeCard TimeCard.def [ OK [ Save Button [ OK [ OK

Figure 40

70

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Database Builder creates a DataDictionary file (.DD file) every time it creates a database file. We will cover these DD files in depth in another lesson but for now, we need to connect the Data Dictionarys together properly. This is done by the required child and required parent lists that will Combobox match the file relationships.

Use the combobox to open all files except DataFlex error file [ Yes to any question on creating new .DD files

Figure 41

Data Access Corporation

71

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

[ Empl File Dialog [ Structures tab [ Delete Button until all files are removed in the section called Required Child files [ Magic Wand button Repeat these steps in the section called Required Parent files Save the file

Figure 42

Magic Wand Button Delete Button

Repeat these steps on all files except SysFile

If files are listed in any of these areas, it is best to remove them and then press the wand button. The magic wand will add files to the area but it will not remove files that are there incorrectly. (incorrect files could have been added manually or by relationships that no longer exist).

The SysFile is a system file (a one record file). It will not be listed as a Required Child or Parent file since it has no file relationships. Therefore, it does not need the structures tab updated.

72

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Did You Discover?


1. Printed in this lesson was a DEF for the TimeCard file that shows its file structure. Without modifications to the TimeCard file, can it have a child file attached to it? Why or Why not? (look in the Appendix C for relationship rules for help)

2. The lock in the upper right corner must be green to make changes to the first three tab pages. When opening a file it always comes up in red - Is there a way to default it to green?

3. When adding a new field in Database Builder, are the Add and Insert buttons required to add a new field?

4. When loading a complete file structure (with many relationships) into a new Filelist.CFG, is it important to load the .DEF files in any special file number position? Why?

Data Access Corporation

73

Lesson 2 Lab Creating Workspaces & Database Files

Discovering Visual DataFlex

5. Write down 3 different ways to open a database file in DDB. (open, not create)

6. What is End User Mode and how do you set up Database Builder in End User Mode? (hint look this up in the on-line help under the index tab)

74

Data Access Corporation

Discovering Visual DataFlex

Lesson 2 Lab Creating Workspaces & Database Files

Data Access Corporation

75

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Lesson 3
Building Views & Components
The Studio is a powerful utility that allows you to not only generate Views and Selection Lists but also generate and maintain a full application.

Topics in this Chapter:


Selection Lists Application Wizard Button Bar Tools Pull-Down Database Selector Tool DDO Tree Button Which Related Field? Object Properties Tool Setting Object Properties Controls Palette Tool Selecting Tab pages & TabDialogs Base Tab page Data Tab page Using the Data Tab page Base Containers Tab page Data Containers Tab page Non-Visible Tab page Object Placement Tools Alignment PaletteTool
Data Access Corporation 77

Popup Menu Arrange Objects Tool Nudge Objects Tool Resolution Check Tool Object-Order Definition Tool Drag Lock Lost Objects in the Studio Cutting & Pasting Objects Anchors & Min/Max Size Lab 3 Creating Selection Lists Attaching Selection Lists Using Application Wizard Creating the Empl View without Wizards Attaching a New View to the Application Compiling Code & Testing Adding Pictures to Records

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Selection Lists
Selection Lists or Lookup Lists as they are also called allow the user to call up a list to make a selection from one of the existing records in the database. The selection list is called up by clicking on the prompt button or pressing F4 while the cursor is in that object.

When your program is running this is what a selection list will look like:

Prompt button from the view pops-up selection list

Selection List

Figure 43

78

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

There are two Steps to create a Selection List:

1. Within the Studio, create the Lookup List New Lookup Button The New Lookup button will create a blank lookup ready to add the file.fields to display. We will see this later in the lab

Figure 44

2. Within Database Builder, attach it to one or more fields

Figure 45

We will create multiple selection lists later in the lab.

Data Access Corporation

79

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Creating New Application


The Application Wizards will quickly generate the code for an application. It will create the outermost container with the main menu bar and the first view. Additional views can then be added later. We will create a small test program in order to check out the many tools of the Studio.

File | New Program

Figure 46

80

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

MDI Application Wizard [ OK

Figure 47

MDI (Multiple Document Interface) style is where the application window has a number of iconizable document windows which fit within it. This saves clutter on the desktop since iconizing or moving the parent window iconizes or moves all the child windows. MDI contrasts with SDI (Single Document Interface) in which windows are not constrained within one parent window, and normal practice is to run one instance of the application per document.

MDI Application Wizard Use this option to start the wizard that will build your MDI Application shell and one or more views Basic Application Use this option to create a very basic interface. The sample is a Hello World, which can be built upon to meet your application requirements. MDI Application Use this option to create the MDI application without starting the wizard.

Data Access Corporation

81

Lesson 3 Building Views & Components

Discovering Visual DataFlex

TestStudio [ Next

Figure 48

[ Next

Figure 49

82

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

TestView [ Next

Figure 50

[ Next

Figure 51

Data Access Corporation

83

Lesson 3 Building Views & Components

Discovering Visual DataFlex

[ Dept DataDictionary C+[ Empl DataDictionary [ Next

Figure 52

Normally all Data Dictionarys in the file structure are selected. Later, we will learn that this view will only allow employee records to be saved but not deleted.

84

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Employee [ Next

The main data dictionary is the central file used in the view (it is not the childmost file). More on this topic later.
Figure 53

/ Empl file [ Code field [ Last_name field [ First_name field [ Next

Figure 54

Data Access Corporation

85

Lesson 3 Building Views & Components

Discovering Visual DataFlex

[ Finish

Figure 55

/ TestView

Double clicking on the view name will open the view. TestView

Figure 56

86

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Resize the container objects as shown by selecting the objects and dragging the corners larger.

Make sure you experiment with all the tools The purpose of the Test Application is to practice using the Studio tools!
Figure 57

Data Access Corporation

87

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Button Bar
Many of the options for the Menu Pull-downs are available from the button bar

Move your mouse over the buttons on the button bar to see the tool tip of each button [ second to the last button on bottom row to open the Code Explorer

Figure 58

88

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Tools Pull-Down
The Tools pull-down lists the many tools available to us. These tools allow you to enhance the views that the wizard has started, or totally create views without the help of the wizard. There are hot keys listed in many of the pull-downs, learning these will increase your productivity. There is also a list of hot keys listed Appendix B. Open the first three tools. They are used in the basic building of the objects in the view

Tools | Database Selector Tools | Object Properties Tools | Controls Palette As we cover the tools experiment with them to see how to create objects within a view

Figure 59

Data Access Corporation

89

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Database Selector Tool


The Database Selector allows you to drag database fields into your component creating data-aware objects.

The top row of buttons allows you to select from the most-commonly-used data-aware objects. Double Clicking on the file icon will expand the file to show the field list. Selection of a range of fields is done by clicking on the first field in the range and then shift clicking on the last field in the range. This will selected all fields between. The fields will be displayed in the same order that they are listed in the Database Selector. They can then be rearranged to your desired location.

[ DDO tree button

Figure 60

90

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

DDO Tree Button The DataDictionary Object Button calls up an important dialog. Many complex topics stem from this dialog. We will be calling up this dialog in many labs. In Lesson 6 we will fully discuss the linkage between DataDictionarys. In Lesson 8 we will see this dialog again when troubleshooting problems. For now, simply look over what is available concentrating on two main topics: 1. The Main DDO is the central file for finding. In our sample program the Main DDO is the Empl DDO. The file relationship does NOT determine the Main DDO. It is also not necessarily the child-most file. You determine the Main DDO by determining the main file for finding in the view. Therefore, you must determine how the view will operate. In our example, when an Employee record is found all other files will fill in their corresponding record(s). We will see later that all Client (Child) DataDictionarys to the Main DDO should normally be constrained to the Main DDO. 2. Normally all the Data Dictionarys in the file structure are listed. Notice the child files to the Empl file are not listed. This was done to demonstrate that deleting records would not be allowed, we will correct this in another lesson.
Expand the view by clicking on all the + symbols and seeing what is available [ Close button

Figure 61

Data Access Corporation

91

Lesson 3 Building Views & Components

Discovering Visual DataFlex

[ Automatic Class Selection button / Dept Icon to expand the field list [ Dept.Dept_Code field ; Dept_Code field to the view

Automatic Class Selection Button

; Dept Code object larger (by dragging the left or right side)

Figure 62

92

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Which Related Field?


Always reference the Parent-related field in a view!

Before we start on this topic, lets explain the term Record Buffer. For each database file opened in a program, a section of memory large enough to hold one record is set aside. This memory storage area is refered to as a Record Buffer. When a record is read it is placed into this record buffer (memory area). During a save operation the data is moved from the screen to the record buffer and then moved from the record buffer to the hard drive. Whenever you reference a file.field name (ex: Move Miami to Customer.City), you are referencing the record buffer memory area for that field. The database should be locked when making changes to the record buffer.

During a save operation, the parent related field(s) is moved from the Parent record buffer to the Child record buffer. If a child related field is used in a view, it will be overwritten by the data from the parent during the save operation. In this example the Dept_Code is the relating field. Empl.Dept field relates to Dept.Dept_Code. When referencing the Dept code, you should place the field from the parent (Dept.Dept_Code). The save operation will move the Dept_Code data from the parent record buffer to the child record buffer. If we mistakenly entered the Child related field, the Studio (when generating the code) will replace it with the Parent related field and add a note in the source code that this correction replacement was made.

Figure 63 Data Access Corporation 93

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Object Properties Tool


Name of the Object This can be changed Object Class The Object Properties allows you to change the most common property settings for an object.

[ on the Label Value area Type Department Code: R

Label Property

Figure 64

94

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Setting Object Properties

Many Object Properties will have a popup listing the valid choices. Simply right click on the property line to see the list of valid entries.

] Right Click on Form_Border [ Border_None ] Label_Justification_Mode [ jMode_Top ] Right Click Color Experiment with the color settings on different objects for a full explanation refer to the on-line help

Figure 65

Notice in the TestView where the labels are positioned. Your labels may be offset to the left with a large space between the label and the object. We will learn how to change this default in later lesson when we talk about DFOs. For now changing the Label_Col_Offset property to 0 and Label_Justification_Mode property to jMode_Right will adjust the label to the object.

Data Access Corporation

95

Lesson 3 Building Views & Components

Discovering Visual DataFlex

[ Database Tab

The Database tab-page of the Object Properties dialog is used to assign values to entry items (file.fields or expressions) and connect the currently selected DataEntry object to a DataDictionary object. This page is only used by DEOs (Data Entry Object db classes). If the current object is not a DEO, all items on this tab page will be shadowed.
Figure 66

Data Source Use the radios to connect a file.field, an expression or variable. If the selected object is row-based, (e.g. dbGrid), use the spin buttons to rotate through the columns of the object and change the file.field or expression for each column in turn.

The bottom part of the Database tab page is used to set and display the appropriate DDO server for the object. The server will provide the save/find/clear&delete functionality to the object. We will cover this in detail in another lesson on connecting DEOs to DDOs. Since save operations propagate up, we will leave the Server set to Empl_DD.

Note: A file.field can be changed into an expression by adding parentheses. Adding parentheses around the Dept.Dept_Code will shadow the object, disallowing user entry during runtime.

96

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Controls Palette Tool


The Controls Palette in the Studio contains the most commonly used classes from which objects are built, The classes are separated into groups on several tab-pages.

Figure 67

Base and Base Containers tab pages contain non-data-aware controls. Data and Data Containers tab pages contain data-aware controls. Non Visible tab page contains non-visual or modal controls.

Data Access Corporation

97

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Selecting Tab pages & Tabdialogs


[ Data Containers Tab page on the Controls Palette ; dbTabDialog to the view Notice the black selection squares showing the TabDialog is selected [ in the middle of the Tab page Notice the black squares turn into white squares showing the Tab page is selected Bring up the Object Properties dialog Again toggle the selection between TabDialog (click the tab area) and Tab page (click the page area). The object properties will change accordingly Resize the TabDialog (to resize or move the TabDialog, black squares must be showing) [ Base Tab page in the Controls Palette ; two Textboxes into the Tab page Change the textbox Object names and Labels to BoxA and BoxB

Figure 68

dbTabDialog

Object and Label

It is a good habit to always rename the object name to a meaningful name. The object name is how you will refer to the object when sending messages directly to it. The Language Guide & Appendix C have the suggested naming conventions. All object names should start with a lowercase o.

98

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Base Tab page

Figure 69

Controls on this page are general-purpose and are not data-aware. Base objects can be placed inside of Data or Base type containers. Class Name Edit Button Checkbox SpinForm LineControl Radio ComboForm Classes that objects can be built from: A multi-line text-based control. The control automatically wraps words between lines and has a vertical and horizontal scrollbar. Used to create a user event. Used to toggle a Boolean value. Displays data and permits the incrementing and reduction of available values. Draws a 3-D line on a container. Can only be used within a RadioGroup container, to show the current selection from a group of mutually exclusive options. Combines the functionality of the Form class with that of a standard Windows drop-down list. This class is used when it is appropriate to supply a form with a list of static options. Simple class to enter single-line information. Used to display a bitmap. Displays multi-row, multi-column lists, Used to display a list of values in a single column. Used to display a text in a container. You may not need to use this class too often, as the Label property of most classes provides the functionality automatically. A control to provide users with a visual control to 'slide' through a range of values. A control to show the progress on a lengthy process. A control to displays an AVI animation clip without audio. A control to display a hierarchical list of items that can expand and collapse the associated list of sub items.

Form BitmapContainer Grid List Textbox

TrackBar cProgressBar cAnimation TreeView

Data Access Corporation

99

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Data Tab page

Figure 70

Controls on this page are data-aware and are used to display data from, and enter data into, a database. Data-aware objects can be placed only inside of data-aware containers. Class Name dbEdit dbCheckbox dbSpinForm dbComboForm Classes that objects can be built from: Displays database data on multiple lines. Used with Text fields. Displays Boolean-style database data in a checkbox. Displays database data and permits the incrementing and reduction of available values. Combines the functionality of the dbForm class with that of a standard Windows drop-down list. This class is used when it is appropriate to supply a dbForm with a list of static options. dbForm dbBitmap dbGrid dbList dbTrackBar Displays database data on one line. Displays the bitmap file listed in the database field. A multi-row, multi-column object to enter data into. A multi-row, multi-column object to view data in. Displays database data on a track bar

Note: The db prefix added to the above class names flags them as data-aware classes.

100

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Using the Data Tab page

Right click on the first tab page Select Add Tab page

Figure 71
WU[ Data Tab page on the Controls Palette ; Drag a dbGrid into tab page2 and enlarge it ; Drag these fields from the Database Selector to the dbGrid Code Last_Name First_Name To delete a tab page: Select tab page2 Right click on tab page2 Select the Delete Tab page option

dbGrid
Figure 72 Data Access Corporation 101

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Base Containers Tab page

Figure 73

Controls on this page are containers designed to hold non-data-aware controls. Class Name Group RadioGroup Container3d TabDialog Classes that objects can be built from: Used to contain non-data-aware controls. Visually drawn with a 3d-line border with a label in the top left corner. Used to group Radio objects within a Group. A general-purpose container that has a 3-D appearance. A container that holds Tab page objects. It is very useful for conserving screen space.

102

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Data Containers Tab-page Data Containers are used to group data-aware DEOs (data-entry objects). They must be placed inside a db-type container themselves (dbView or dbContainer or ReportView).

Figure 74

Controls on this page are containers used to hold other data-aware controls. Class Name dbGroup dbContainer3d dbTabDialog Classes that objects can be built from: A container with a label in its top-left corner. A container with a border that makes it visually appear raised. Tabs are a great way to display large amounts of data neatly on the screen. The dbTabDialog holds a single dbTab page object and allows you to add more dbTab pages. A container to contain and provide coordinated access to dbTabView objects. Each TabView displays a standalone view with its own DataDictionary structure. Use the dbTabDialog to display many TabViews on multiple unrelated datafiles (like maintenance views), where you can consolidate the number of views in your overall application. A container to group Radio objects whose value is of a single data-entry element.

dbTabDialogView

dbRadioGroup

Data Access Corporation

103

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Non-Visible Tab page

Figure 75

Controls on this page do not create a visual control during runtime or create a modal control that will have to be called. They will generate a visual icon in the Studio so you may click on it to add manual code in the code editor. Class Name BusinessProcess OpenDialog SaveAsDialog FontDialog Classes that objects can be built from: To perform a batch process on an applications database files. To provide access to the Windows file-open dialog. It permits users to select an existing file or enter a name to create. To provide access to the Windows file-save dialog. Objects of this class enable users to enter file names. To permit users to select fonts. It is an encapsulation of the Windows Common Font Dialog. All aspects of the dialog can be set before it is displayed, and queried upon its return. The PrintDialog class is a wrapper for the Windows Print dialog box. This dialog box is used to specify the properties of a print job. This class is intended to be used with the CrystalReport class exclusively The Array class is a general storage device. It is used to store all data types and its size grows dynamically to accommodate the storage requirements. Data elements in the array are accessed by an integer index. To assemble and maintain a set of unique values, with operations to add, remove, and find elements.

PrintDialog

Array

Set

104

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

dfTimer cImageList

Objects of this class can be used to trigger an event after a certain amount of time has passed. An imagelist is a collection of images of the same size, each of which can be referred to by its index. Imagelists are used to efficiently manage large sets of images, which can then be shared by multiple objects. A single imagelist object can provide images to the TreeView, cToolbar and TabDialog classes. The ColorDialog class provides an interface to the Windows standard Color dialog. The dialog will maintain its own list of custom colors and return the selected RGB color. Simple MAPI consists of functions for sending mail, receiving mail and sending documents. Consider MAPI as a transport mechanism for mail and fax messages. To create a simple object without any special methods found in superclasses. You can use cObject to create your own subclasses.

ColorDialog

cMapiHandler

cObject

Data Access Corporation

105

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Object Placement Tools


The object placement tools are used to align objects in the view.

Close all open tools, then: Tools | Alignment Palette Tools | Arrange Objects Tools | Nudge Object Tools | Resolution Check As we cover the tools experiment with each of them to see how to arrange objects within a view. Remember this is only a test view and its whole purpose is to test the tools!

Figure 76

106

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Alignment Palette Tool


This tool will help align the objects. If the alignment results are not what you desired, simply select Edit | Undo immediately after any of the Alignment buttons to return the objects to their original positions.

Figure 77

4 | 5

The first four buttons justify the tagged objects to match an edge of the first selected object. Therefore, it is important which object is selected first. 1. Align tagged objects to the left 2. Align tagged objects to the right 3. Align tagged objects to the top (left justify) (right justify) (top justify)

4. Align tagged objects to the bottom (bottom justify)

The last four buttons equally space the tagged objects. Buttons 5 & 6 space objects equally between the first and last objects selected. Buttons 7 & 8 space the objects within the container object. Buttons 7 & 8 also rearrange and list the objects in the order that they are tagged. When spacing more than three objects, it may be better to use the Arrange Object tool. This is because when placing the objects evenly within the space if a remainder exist, the last object cannot be placed correctly. 5. Align tagged objects from top to bottom 6. Align tagged objects from left to right 7. Align tagged objects from top to bottom in parent object 8. Align tagged objects from left to right in parent object

Note: The last two buttons are the only alignment tools that will rearrange the objects in the order they were selected. This allows you to quickly rearrange objects just by selecting them in the desired order.

Data Access Corporation

107

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Popup Menus
Right Click on an object. Alignment can be done from the popup menu.

] one of the textboxes [ Center [ Horizontally

Figure 78

108

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Arrange Objects Tool

This tool is used to resize and/or space objects. Activate one or both parts of the tool with the Active checkbox. After you apply the change to the selected objects, uncheck the Active checkbox and your X Y settings are still available.

Figure 79

X setting adjust left - right Y settings adjust up - down

Note: The Alignment Palette described earlier can either space the objects between the first and last tagged object or within the parent object. The Arrange Object tool will leave the first tagged object in place and then apply the exact X or Y coordinate spacing between other tagged objects. This method will give better results in some situations. This will be noticeable when more than three objects are selected and the available free space to divide among the objects cannot be done equally.

Data Access Corporation

109

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Nudge Objects Tool


Used to move or size objects.

Repositioning objects can be done by selecting a group of objects and dragging them to a new location or selecting the objects and using the Nudge Objects tool.

Figure 80

More precision is one advantage of the Nudge Objects tool. Dragging an object to the left or right will often result in a small up or down movement from the drag. Using the Nudge Objects tool will give you movement in only one direction. Increasing the number in the middle will nudge the object

faster.

Increasing the value will move or size the object faster.

110

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Resolution Check Tool


This tool will help when you are developing an application on a monitor with a different resolution than that of your customers. It allows you to see how your application will look on different resolution screens.

Note: This is an estimate since not all video cards and drivers follow standards

Figure 81

Data Access Corporation

111

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Object-Order Definition Tool


The next tool is a modal popup. You must use it and close it before continuing.

The tab key will move us to the next entry object in a running application. This tool allows us to change the keyboard navigation of the cursor through the objects in our view. Simply select the object and then use the up/down arrow buttons to reposition the objects. Objects cannot be moved outside their group/container object. When you move a container, all nested objects will move with it.

Tools | Object-Order Definition [ Dept_Dept_Code [ Up Arrow Button until it is the second object from the top

Figure 82

[ OK

112

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Drag Lock
This important feature will protect your view from accidental changes of object movement. Drag Lock will lock the objects in place. This will allow you to double click on the objects without accidentally moving them. You will not be able to drag the objects around with the mouse but you will be able to select them and move them with the arrow keys.

Methods of toggling the Drag Lock


Figure 83

Menu: Hot Key: Status Bar:

Tools | Drag Lock Ctrl+L Clicking the Lock indicator

The drag lock indicator is an Studio control and once set, it affects all components in the Studio. The Studio does not store the setting of this indicator so it must be set each time the Studio is opened.

Press the Ctrl+L until the lock is off in the Status Bar

This location will be blank when lock is off.

Figure 84 Data Access Corporation 113

Lesson 3 Building Views & Components

Discovering Visual DataFlex

The remaining options on the Tools pulldown menu will be covered in other lessons. Items are shadowed (not available) depending on if an application is opened or closed.

Figure 85

114

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Lost Objects in the Studio (recovering objects not visible on screen)


If not already created create a dbTabDialog with two textboxes at the locations shown
[ dbTabDialog (black selection markers) Make the tab page smaller so one of the objects will not show.

Figure 86

/ tab page object will bring up the Code Explorer (Studio editor) [ on the non-visible object in the Code Explorer object tree [ Object Properties dialog Enter 5,5 for the location R

Figure 87

Code Explorer Object Tree

Data Access Corporation

115

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Cutting & Pasting Objects to Different Containers


Objects cannot be dragged from their parent container. To move or copy objects, cut/copy them to the clipboard and paste them into the desired container. If the container being pasted into is smaller, the objects will adjust themselves to remain visible in the new container.
] BoxA [ Copy

Figure 88

] the top Container [ Paste

Try cutting and pasting multiple objects, using the Control key to multiselect objects.
Note: For multiple sequential selection, select the first item and then, , hold the shift key down while selecting the last item. In order to make multiple random selections, hold down the Control key while making additional selections. Data Access Corporation

Figure 89

116

Discovering Visual DataFlex

Lesson 3 Building Views & Components

Save and Close the Test_Studio application Briefly, look over the other pull-down options to see what is available

Figure 90

Data Access Corporation

117

Lesson 3 Building Views & Components

Discovering Visual DataFlex

Anchors & Min/Max Size


Anchors allow automatic resize and location of nested controls when the View or container is resized at runtime.

Here are the basic steps you will need to take Allow the Container to be resized. Set the Containers Border_Style to Border_Thick (otherwise it cannot be resized) Anchor the nested objects within the container. Set with the peAnchor property. Determine the Min and Max size limits that the container should be allowed to grow or shrink to and still be useful. Set with the piMinSize and piMaxSize properties. Test compile button TestView Object
Drag a Button to the bottom right corner [ TestView Object and change the Border_Style to Border_Thick [ Test -Run Button When the program comes up running -- Resize the View (MinSize & MaxSize) and notice how the objects do NOT resize or relocate [ X Close button and return to the Studio

Button
Figure 91

118

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Building Views & Components

[ TestView Object Within the Object Properties dialog change the piMaxSize and piMinSize Plus or Minus 100 the Size property

If Size = 170,300 then make Max = 270, 400 Min = 70, 200

Figure 92

Data Access Corporation

119

Lesson 3 Building Views & Components

Discovering Visual DataFlex


[o oButton Object Within the Object Properties dialog change the peAnchors to anBottomRight [o oDbTabDialog1 Within the Object Properties dialog change the peAnchors to anAll [ Test compile and run component in the debugger button When the program comes up running -- Resize the View (MinSize & MaxSize) and notice how the objects resize & relocate [ X Close button & return to the Studio

Figure 93

120

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Lesson 3 Lab
Description: We start by making required selection lists (lookups) and attaching them to the appropriate field. Then we use the MDI Application Wizard to create an outer container that will contain the menu bar and status bar. The wizard also creates our first view. We will then create the next view manually without the aid of wizards. The third view will use the View Wizard. We will then test our application. Tasks:

Creating Selection Lists


If the Studio is closed restart it, and close all other components.

[ New Standard Lookup Button

Figure 94

Data Access Corporation

121

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Tools | Database Selector [ Add DDO button [ Dept DataDictionary [ Select button [ Yes to Main DDO [ Close button

Figure 95

122

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Automatic Class Selector

/ Dept (to expand list) [ Automatic Class Selector button [ Dept_Code field [ Name Field ; these fields into the grid ; the right side of the Name column wider [ Outer Lookup Object Change the label to Department Lookup

Outer oLookup Object (the dbModelpanel)

Figure 96

Data Access Corporation

123

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Save Button

[ Save button Dept Department Lookup Dept_SL G[ Deferred Object [ Save button Close all the tools File | Close Component

There is a Magic Wand button in the DataDictionary Figure 97 Builder that will speed up connecting a selection list to a field. We will use this button in the next few pages. The Magic Wand button can only default these values, if we follow these naming conventions for both the Filename and Object Name: Suggested Naming Convention FileName Description The root database filename. The filename will have the extension of .SL added but it is not typed into the form when saving. A descriptive word for the file (many times just the filename) and the word Lookup. The word Lookup will flag these components as a Selection List. The root database table name with a _SL added.

Object Name

The deferred view checkbox will make our application faster at startup. Instead of creating all objects in memory at startup, it will not create the object until it is used for the first time.

124

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

[ New Standard Lookup button Repeat the above steps to create a Selection List (Lookup) for the Employee file showing: Code; Last_Name; First_Name fields. Save it Using naming convention listed in the chart above Close all the tools

Figure 98

File | Close Component

Data Access Corporation

125

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Attaching Selection Lists in the DataDictionary


Now that our Selection Lists are created we need to attach them to one or more fields in the DataDictionary. If the Studio is closed restart it

Database | Database Builder (or the 5 button from the end on the button bar)
th

Figure 99

126

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

File | Open [ Empl file [ Open button [ Field Settings [ Code field [ Validation/Lookup Tab [ Magic Wand button (middle button)

Figure 100

Wand Button

If you cannot find the selection list using the Magic Wand use the Find Object & Package (1st) button to locate it. The same Selection List can be attached to multiple fields. Here is a slightly different way to attach a list. The Magic Wand will only work if the filename follows the suggested naming convention.

[ Last_Name field [ Find Object & st Package button (1 button) [ Empl.SL [ Open [ Save button [ OK File | Close

Figure 101

Find Object & Package

Data Access Corporation

127

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

[ File comboform Arrow [ Dept This will Open the Dept file - attach the selection list to Code and Name fields Save and Return to the Studio

Figure 102

128

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Using Application Wizard


The Application Wizard will allow you to quickly generate the code for an application. We will create our first view here and then modify it using Studio tools.

If an existing program is open select File | Close Program File |New Program

Figure 103

[ OK

Figure 104

Data Access Corporation

129

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

CorporationX [ Next

Figure 105

[ Next

Figure 106

130

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

DeptView [ Next

Figure 107

[ Next

Figure 108

Data Access Corporation

131

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

[ Department DataDictionary [ Next

Figure 109

[ Dept_Code field [ Name field [ Number_of_empl [ Budget [ Comments [ Next

Figure 110

132

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

[ Finish

Figure 111

Data Access Corporation

133

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

/ DeptView

Figure 113

Enlarge the Dept_Code Object [ Test compile and run component in the debugger button Notice that you can save new records but you cannot delete records we will correct this in another Lesson

Figure 112 134 Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Creating the Empl View Without Wizards


Close all open views and applications.
[ New Standard View Button

New Standard View

You could also select File | New Component and select the Blank View from the DataEntry View tab page but that would take longer.

Figure 114

Tools | Database Selector [ Add DDO button [ Empl DataDictionary [ Select button [ Yes to make it the Main DDO Notice the parent file (Dept) is also opened. Save operations propagate up so parent files will open automatically

Figure 115 Data Access Corporation 135

Lesson 3 Lab Building Views & Components


[ Close button

Discovering Visual DataFlex

Using the many tools covered in this lesson create the Empl View similar to this screen (do not forget the dbContainer3d object) Use the Object Properties Tool to change the View Label to Employee View Enlarge the Empl.Code & Dept.Dept_Code objects Position the objects in the location shown using the Alignment Tool Use the ObjectOrder Tool to change the navigation

Figure 116

Dont forget the dbContainer3d

Note: Remember what we discussed in the lesson! The related parent field is used in the view, not the child related field. This is because during a save operation DataFlex will do an Attach prior to the save. This operation will move the related field from the parent to the child. If we were to actually use the Empl.Dept field here, then the blank parent record buffer would be moved to the Child Empl.Dept field causing the Empl.Dept field to be blank. The Studio will swap the field for us when it generates the code if we use the wrong one.

The reason we continue to make the Dept Code objects larger is that later we will be setting the field option to CapsLock, which will require a larger object.
136 Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

From the Controls Palette ; a dbTabDialog to the bottom of the view and resize it

Figure 117
] dbTagDialog (for the menu popup) [ Add Tab Page [ Add Tab Page Within the Object Properties dialog: [ each tab page (white selector squares) & set Labels to: Personal Information Work Information Picture ID

Figure 118 Data Access Corporation 137

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Within Database Selector Tool ; fields to Personal Information Tab page

Figure 119

; fields to Work Information Tab page Enlarge the Pay_Type field we will be adding a validation table to it in another lesson.

Figure 120

138

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

] (right click) Pay Type [ Object Properties ] (right click) Prompt_Button_ Mode [ pb_PromptOn This prompt button will not operate until the validation table is added.

Figure 121

[ Automatic Class Selector (Wand) button at the top of the Database Selector Tool ; Picture_ID field to the Picture ID Tab page [ Bitmap button at the top of the Database Selector Tool ; Picture_ID field to the Picture ID Tab page

Figure 122

Data Access Corporation

139

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

[ dbBitmap Object Within Object Properties Tool [ Initial Folder C:\Program Files\Visual DataFlex 9.1\Projects\Class\VDF\ CorporationX\Bitmaps

The Initial Folder property lists the initial directory, which will be displayed by the common file-open dialog. When we run the program, we will see this dialog when we add a bitmap file to an employee record. Figure 123

Note: The Initial_Folder property can be set dynamically to the current workspace \bitmap area. If you dont want to hardcode the Initial_Folder property add this to the Code Explorer: Set Initial_Folder of (CurrentBitMapPath (ghoWorkSpace))

Appendix B has examples of code to solve problems when using multiple directories in your Bitmap path and to limit the bitmap filename to 15 characters. If the end-user selecst a bitmap that is outside the current path, it is suggested that programmably the developer may wish to copy the bitmap to the current Bitmap path.

140

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

[ Save button and save as Empl_View [ Close button

Close

Figure 124

Data Access Corporation

141

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Attaching a New View to the Application


If the main application is closed, reopen it: File | Open program | CorporationX From the Code Editor:
[ Add a Component Button [ Views [ Empl_View.VW [ Add Button [ Close Button

Figure 125

Add a Component

142

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Compiling Code & Testing


The Compile button will automatically save our code first.

[ Compile and debug-run program button (this will compile and run our application) After the program comes up running Open both views by selecting them from the View pull-down

Figure 126

Things to Notice How the tab pages switch. Confirmation Messages during a save. How Selection Lists operate. How multiple Views can be opened simultaneously.
Test the Application noting the items in the chart

Data Access Corporation

143

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

Adding Pictures to Records


Adding pictures to records is accomplished by storing the name of the .BMP file in the database field and storing the physical bitmap file in the \Bitmaps directory of the workspace. We will be using the Empl.Picture field. We already copied both the \data and \bitmaps directories from our training CD to our workspace. If you did not do this please copy the files now.

Run the application and open the Empl View Create a new employee record [ Picture ID tab page / the Bitmap object the popup dialog will allow us to locate our bitmap file. Since our initial folder was set to: C:\Program Files\Visual DataFlex 9.1\Projects\Class\VDF\C orporationX\Bitmaps this is the default directory that the dialog will show Select a .BMP file [ Save Button Close program when done testing

Figure 127

144

Data Access Corporation

Discovering Visual DataFlex

Lesson 3 Lab Building Views & Components

Did You Discover?


1. What happens if you enter a 2-digit year into a date window such as Term Date?

2. What is Epoch and what has it to do with entering dates in a VDF application?

3. Predict and check the results of entering the following dates, with Epoch turned on and set to 30? 01/01/00 06/20/52 12/25/30

4. What would happen to the tab dialogs if the dialog box was not big enough to hold all three tabs? (add more tabs or shorten the tab dialog box to find out)

5. What would happen if you shortened the length of the last name window so that the entire last name entered wouldnt fit in the window?

6. Run the program, and type in a last name of WWWWWWWWWW (type capital Ws until you reach the limit (which is the length of the field). Notice that it had to scroll to the right. Clear with the F5 key, and type in a last name of iiiiiiiiii (all small letters is to the limit). How do you determine what the size of a control should be?

Data Access Corporation

145

Lesson 3 Lab Building Views & Components

Discovering Visual DataFlex

7. When using the Object-Order Definition tool, is it important where Textbox objects are listed?

8. Run our program, and open up the Employee Entry View. Find a Record, then place the cursor on the parent window (Dept) and press Shift+F2 to delete. Wait! What is going to be deleted? The Department or the Employee? Why?

146

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

Lesson 4
Generated Code
We will start to look over all the code that the Studio has generated for us. This will give us a better understanding of how VDF code works. The Studio editor allows manual code to be easily added throughout your application.

Topics in this Chapter:


Editors Full Source Mode The Big Picture Activating Views Creating Templates Manual Code That the Studio Can Read Lab 4: Creating an Invoice Style View Template Adding Manual Code to Objects Creating Dept/Empl View Using View Templates Grid Options Changing Navigation

Data Access Corporation

147

Lesson 4 Generated Code

Discovering Visual DataFlex

Editors Full Source Mode


The Editor has two modes Outline and Full Source mode. Outline will show only the code added to the selected object. Full Source mode will display all the code within the code file.

Within the Studio open the program

] Anywhere within the Code Explorer [ Toggle Full Source Use the code in the editor to follow along the code explanation on the next few pages

Figure 128

148

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

The Big Picture


Lets look at our application with all its modular parts. The Use command will include modular code from separate files into our application. Encapsulation is when our code is broken down into stand-alone modules. This makes it easier to reuse it. Here is our CorporationX.SRC Source code file.
//AB/ Project CorporationX //IDE-FileType=ftMdiFrame //AB/ Object oIde_Project is a MdiFrame_Project //AB/ //AB/ //AB/ Set ProjectName to "CorporationX" Set ProjectFileName to "CorporationX.src" Set GenerateFileName to "CorporationX.src"

//DFAllEnt.PKG
Use Windows
...

//AB-IgnoreStart Use DfAllEnt.pkg #REPLACE CURRENT$WORKSPACE "Class.VDF.CorporationX" // Project Object Structure // Main is a Panel // // Client_Area is a AppClientArea oAbout is a AboutDialog

// Register all objects Register_Object Client_Area Register_Object Main Register_Object oAbout //AB-IgnoreEnd

//AB-StoreTopStart Use cApplication.pkg // Set date attributes as needed Set_Date_Attribute sysdate4_State to (TRUE) Set_Date_Attribute Date4_State Set_Date_Attribute epoch_value to (TRUE) to 30

Ensure all dates are entered as four digits

Object oApplication is a cApplication Set psCompany to "My Company" Set psProduct to "My Product" Set psVersion to "1.0"

These three properties can be customized to your application. Showing your Company; Product; and Version

Data Access Corporation

149

Lesson 4 Generated Code

Discovering Visual DataFlex

//Set psHelpFile To "HelpName.hlp" // Please provide the name of your Windows help file. Procedure OnCreate Send DoOpenWorkspace (CURRENT$WORKSPACE) End_Procedure End_Object // oApplication Use Help_Ids.inc //Developer should provide this file of help context links. Use Std_Help.pkg //AB-StoreTopEnd //AB-IgnoreStart //AB-IgnoreEnd Object Main is a Panel Set Label to "CorporationX" Set Size to 150 300 //AB-MenuAutogen //AB-IgnoreStart DFCreate_Menu Main_Menu #INCLUDE File_PM.inc DFCreate_Menu "&View" ViewPopupMenu is a ViewPopupMenu On_Item "&DeptView \aCtrl+1" On_Item "&Employee View \aCtrl+2" End_Pull_Down Set Status_Help To "Available Views" #INCLUDE Navi_PM.inc #INCLUDE Win_PM.inc #INCLUDE HelpA_PM.inc End_Menu //AB-IgnoreEnd //AB-ToolbarPackage Use DefaultToolbar.pkg // Tool-Bar object. //AB-End Send Activate_DeptView Send Activate_oEmpl_View

Main Panel

Menu Bar and Pulldowns Notice the two views listed

150

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

Object Client_Area is a AppClientArea //AB-ViewStart Use DeptView.vw Use Empl_View.VW //AB-ViewEnd End_Object // Client_Area

//Dept.VW
use Dept.DD use Empl.DD

//Dept.DD //Empl.DD

//Empl.VW
use Empl.DD

//AB-IgnoreStart On_Key Key_Ctrl+Key_1 Send Activate_DeptView To Client_Area On_Key Key_Ctrl+Key_2 Send Activate_oEmpl_View To Client_Area //AB-IgnoreEnd //AB-StatusBarPackage Use DefaultStatusbar.pkg // Status-Bar object. //AB-End //AB-StoreStart Use DfAbout.pkg Object oAbout is an AboutDialog Set ProductName To "CorporationX" Set Copyright To "Copyright: <add code here>" Set Author End_Object Procedure Activate_About Send Popup_Modal of oAbout End_Procedure //AB-StoreEnd End_Object // Main To "Author: <add code here>"

//Use the Standard Status bar and About packages Properties to customize your about dialog

//AB-StoreStart Start_Ui //AB-StoreEnd //AB/ End_Object // oIde_Project

At this point the user interface is started and the activate message is sent to the Main_Menu object, which paints the image on screen making it the top image and gives the focus to this object.

Note: (instructors) This is a good place to point out the corresponding Studio areas from the Program tree that appear whenever a program is opened. Data Access Corporation 151

Lesson 4 Generated Code

Discovering Visual DataFlex

Things to note! The main program is a shell where modular sections of code are included (via the USE Command) The first file brought in by the USE command is the DFAllEnt.PKG. This Package file contains Class definitions (the code to make the tools work). The .PKG files are not always classes; sometimes they are support packages that perform special functions. The View files end with the extension .VW. These View files are the heart and soul of the program. They are modular sections of code that can operate independently. Each can be compiled and run separately within the Studio. Also note that all the views have the same command USE EMPL.DD. This file is needed in each view so it will operate correctly when using the view separately in a test program. When all the views are added together in the main program, the EMPL.DD file is only included into the program once! If a change has to be added to the code in the EMPL.DD file, it only needs to be modified in the one place and after re-compiling will affect all the views. Modular code allows us to use the same code over and over agiain. These modular code sections seem confusing at first. The real benefit is gained when you modify or debug your code. This is similar to the fact that it is harder to troubleshoot a computer that has everything built into the motherboard. If the serial port is a separate card, you can repair it without worrying about breaking the Disk Controller. However, if everything is on the motherboard, fixing one problem can often break other parts.

Note: (for everyone) The USE command assumes a .PKG extension, if no extension is given.

Note: (for DataFlex procedural programmers) The Use command is very similar to the #INCLUDE compiler directive that you may have used in your code. The main difference is that the #INCLUDE would include a file numerous times, but the USE command will only bring in a file once. Note: (for DataFlex procedural programmers) A Menu program with RunProgram wait and Chain wait commands is comparable to what we now call views.

152

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

Activating Views
Views can be activated by the view pulldown menu or by Accelerator keys. The message name MUST be the same in both the .SRC file and the .VW file.

// This is the .SRC file DFCreate_Menu "&View" ViewPopupMenu is a ViewPopupMenu On_Item "&EMPL VIEW\aCtrl+1" Send Activate_EMPL_VIEW // This is the Empl.VW File ... Object Client_Area is a AppClientArea // Include all views Use EMPL_VIEW.vw DEFERRED_VIEW Activate_Empl_View FOR ; ; Object Empl_View is a dbView Set Label to "Employee Entry View"

End_Object // Client_Area On_Key Key_Ctrl+Key_1 Send Activate_EMPL_VIEW of Client_Area

Start_UI

Data Access Corporation

153

Lesson 4 Generated Code

Discovering Visual DataFlex

Creating Templates
Templates save time in the design of components. In this example, we create a template that can be used when needing multiple views of a standard size. Templates can be Local or Global: Local meaning they are only accessible to one workspace; Global meaning will be accessible to all workspaces.
[ New Standard View button from the button bar Enlarge the view to just inside the 640 x 480 grid lines [ File | Save As Template | Local Enter file name of View640x480 [ Save button Close the View

Figure 129

File | New Component Notice the new template listed [ Cancel Button

Figure 130 154 Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

Manual Code That the Studio Can Read


The Studio allows manual edits to the source code and is capable of reading the edits as long as a few rules are followed. Use markers //AB-marker_name to flag the edits (creating edits through the Outline mode of the Studios Code Editor will add these markers for you) Place the markers and the edited code in the correct location (creating these edits through the Studio will ensure they are created in the correct location)

Note: The Visual DataFlex language uses double slashes // to flag comments in your code. Therefore, these markers will be considered as comments by the Compiler, but have special meaning to the Studio.

1. Manual Code in the .SRC file (via the Studio)

Lets look at some code areas in the editor.


Open CorporationX application: [ Outer-Component Code Notice the Start_UI at the bottom and the Date _Attribute commands Enter Your Company; Product; and Version information

OuterComponent
Figure 131

Data Access Corporation

155

Lesson 4 Generated Code

Discovering Visual DataFlex

2. Manual Code in Visual Objects (via the Studio)

Open the EmplView [ oEmpl_Code object Notice that the selected object stays in sync with the shadowed object in the editor

Code added to the top of the Object Code added to the bottom of the Object
Figure 132

Selected object will be highlighted All objects start with an Object command and end with an End_Object. The Studio will add all its code where the Green Line is located. This means you have the ability to add manual code in the Code Explorer above or below where the Studio places all its generated code, such as the properties from the Object Properties dialog and nested objects.

Normally, you can simply add all your custom code below this green line. However, sometimes it is important that the added code is placed at the top of the object. E.g., if you were creating a new property that nested child objects would need, it would have to be created before the nested child objects try to use the new property.

156

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Generated Code

3. Manual Code in the DataDictionary Objects (via the Studio)

Also notice that the Data Dictionary objects are also accessible even though they are not visible objects. We will be adding manual code to many objects later, in the lab [ Close this view

Figure 133

Data Access Corporation

157

Lesson 4 Generated Code

Discovering Visual DataFlex

List of the Studio (AB = Application Builder) markers. Normally you will not need to type these, since the Studio will add these markers for you when you modify within the Studio editor in Outline View mode.
Marker Source Code File Commands for the Studio only Studio generated code for the compiler only Sample //AB/ Project project-name //AB/ command Location First non-blank line in your source code These are various commands that the Studio must understand that must be ignored by the compiler The Studio does not use this area but generates it for the compiler only. Any changes made here will be overwritten by the Studio. Manual Edits No No

//AB-IgnoreStart //AB-IgnoreEnd

No

Data-Dictionary Object Area

//AB-DDOStart //AB-DDOEnd

Only defined and registered Data-Dictionary Objects are allowed Top and bottom edit area of the visual objects Yes

Manual-Code-Area

//AB-StoreTopStart //AB-StoreTopEnd //AB-StoreStart //AB-StoreEnd

Note: The main edit areas are the bottom code areas and do not have the word bottom within the marker name but the Top edit area does contain the word Top just prior to the Start/End.

158

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Lesson 4 Lab
Description Our next view will need manual code additions. The view style will be an invoice style. This style has a parent (order header) record displayed at the top of the view and a grid below filled with the child (order detail) records. Since this style of view is often needed, we will first create a view template that adds the manual code additions to make the view operate correctly. We will then use this template to create our Dept/Empl View. Then in later lessons we will again use our view template. Tasks The order example is a sample application. It may be helpful to run this example to understand how it operates. The order view looks like this:

This step can be skipped if you are familiar with the Order Example.
Windows Start | Programs | Visual DataFlex 9.1 | Sample Applications | Order Entry System Open the Order Entry view & test it

Figure 134

Notice that you cannot enter the grid unless the header is saved Close the example and return to the Studio

Data Access Corporation

159

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

Creating an Invoice Style View Template


We will create a basic invoice style view, adding only the objects that require manual code additions.

[ New Standard View Button Use the Controls Palette to create the 5 objects as shown Use the Object Properties Tool to change the object name & object labels as shown in the chart. Only the required items that need to be renamed are listed.

Figure 135

Object Name Label

Compiler errors will occur if this one is not renamed!

Type of Object dbContainer3d dbForm dbForm dbForm dbGrid

Object Name

Label First Object Parent Related Obj Last Object

oDetail_Grid

160

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

At this point in the manual DO NOT TO TRY TO UNDERSTAND ALL THE MANUAL CODE ADDITIONS! We will cover the syntax of code in other lessons at this point simply concentrate on how the views are working!

Manual code segments that will be added to our Header/Grid (Invoice Style) Template can be cut from a file called Code_Mod.TXT located on the CD that came with this manual.

When manual code is added to a template it is important to make it as generic as possible. This will increase the usefulness of the template to help us create many new views. This also means there may be a few items that may require customization to make our template function in a new workspace with new database tables. You will notice these types of customizations are described in the remark area within the code.

Manual Code Features that will be added are: Custom Save & Delete messages Save_Header procedure (ensures header is saved before entering grid) Switch Procedure for last object in header Append_A_Row (allows entering only at the end of the grid) Child_Entering in the Grid (sends the Save_Header procedure) Auto_Regenerate_State set to false (table will not resort when new records are added) Child_Table_State set to true (to ensure the row is always saved)

Data Access Corporation

161

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

Adding Manual Code to Objects


This step adds the Custom Save & Delete messages, plus the Save_Header procedures to the outer view container. The Code_Mod text file will allow us to cut and paste code instead of manually typing it. We will cover manual code in depth in another lesson.

With our new view still opened.


File | Open File Use the browse button and open the Code_Mod.txt file from the Training CD

Lab dividers will show which lab the code is for. Cut & paste dividers show where to start and end a cut & where to paste it

When cut/pasting be SURE to cut both slashes


Figure 136

Note: In the manual code you will start to see the use of * and + to combine variables and constaints. Ex: Move ("Delete Entire" * (psHeaderName(Self)) + ?") to sDel_String The * will leave a space between and the + will not.

162

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Before adding any code Notice the selected object

/ the oView object (dbView) and Cut & Paste the corresponding code into the bottom area

Figure 137

This is the code to cut & paste. After pasting always compare the code printed in the manual to the code pasted into the object.

//------------------------------------------------------------------// Add to the oView object - below the green line // To customize our template set the defaults of top 2 properties: //------------------------------------------------------------------// Enter the Header descriptive filename // Example: Order --> not OrderHea // The file name will be used to name the view (Order or Transaction) // It will also customize our messages so they will say "Save this Order" // or "Save this Transaction". If the print button is used it will // expect a Crystal report called psHeaderName.RPT --> (Order.RPT) Property String psHeaderName Public "Order"

// Enter the File.Field of the header key field // Example: OrderHea.Order_number for the order example Property String psFileField Public "Order.Order_Number"

Data Access Corporation

163

Lesson 4 Lab Generated Code


Property Integer piKeyFieldnum Public 1 Property String psType_Header_Key Public "I" Procedure Activate Forward Send Activate // Determine the field number of the Header's key field // Then update the default setting for the property piKeyFieldnum String sHold String sFile sField Integer hFile iField iLen iPosDot iType Get psFileField to sHold Move (Length (sHold)) to iLen Move (Pos(".", sHold)) to iPosDot Move (Left(sHold, (iPosDot - 1))) to sFile Move (Append (sFile, ".File_number")) to sFile Move (Eval(sFile)) to hFile Move (Right(sHold, (iLen - iPosDot))) to sField Field_Map hFile sField to iField Set piKeyFieldnum to iField // Determine the type of the Header's key field // Example: "I" = Integer or a "S" = ASCII string

Discovering Visual DataFlex


// 1 is the default for the field number // "I" is the default for the Header Key field type

// This is a small limit to our template but most key fields are either ASCII or Integer // Then update the default setting for the property psType_Header_Key Get_Attribute DF_Field_Type of hFile iField to iType If (iType = DF_ASCII) Set psType_Header_Key to "S" // its default setting is "I" End_Procedure //Activate

//----------------------------------------------------------------------// Change: Create custom confirmation messages for save & delete. // Create the new functions and assign verify messages to them. //----------------------------------------------------------------------Function Confirm_Delete_It Returns Integer Integer iRetVal String sDel_string Move ("Delete Entire" * (psHeaderName(Self)) + "?") to sDel_string Get Confirm sDel_string to iRetVal Function_Return iRetVal End_Function // Only confirm on the saving of new records Function Confirm_Save_It Returns Integer Integer iRetVal iSrvr iRec

164

Data Access Corporation

Discovering Visual DataFlex


String sSav_string Get Server to iSrvr Get Current_Record of iSrvr to iRec If (iRec = 0 ) Begin

Lesson 4 Lab Generated Code

Move ("Save New" * (psHeaderName(Self)) * "record?") to sSav_String Get Confirm sSav_string to iRetVal Function_Return iRetVal End End_Function // Define alternate confirmation Messages Set Verify_Save_MSG Set Verify_Delete_MSG to GET_Confirm_Save_It to GET_Confirm_Delete_It

//------------------------------------------------------------------// Change: Table entry checking - attempt to save header record // // before entering a table (this is called by table. Return a non-zero if the save failed (i.e., don't enter table)

//------------------------------------------------------------------Function Save_Header Returns Integer Integer iRec bChanged iSrvr String sError_String Get Server to iSrvr // The Header DDO. // Are there any current changes? Get Current_Record of iSrvr to iRec // The current header rec#. Get Should_Save to bChanged

// If there is no record and no changes we have an error. If (iRec=0 AND bChanged=0) Begin // no rec Move ("First Create & Save a" * (psHeaderName(Self)) * "Record") to sError_String Error DfErr_Operator sError_String Function_Return 1 // a non-zero return val will stop the save End // Attempt to Save the current Record // Request_Save_No_Clear does a save without clearing. Send Request_Save_No_Clear // The save succeeded if there are now no changes, and we // have a saved record. Should_Save tells us if we've got changes. // We must check the DataDictionary's Current_Record property to see if // we have a record. If it is 0, we had no save. Get Should_Save to bChanged // is a save still needed Get Current_Record of iSrvr to iRec // current record of the DD

Data Access Corporation

165

Lesson 4 Lab Generated Code


// If no record or changes still exist, return an error code of 1 If (iRec=0 OR bChanged) ; Function_Return 1 End_Function

Discovering Visual DataFlex

166

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Note: (Everyone) In an Invoice Style view it is important to restrict the users navigation into the grid without first displaying a Parent/Header record in the top of the view. In our template we will ensure a header parent record is displayed and saved before allowing the user to enter the grid. This will be accomplished by the Save_Header procedure, which safeguards against creating orphan Child/Detail records.

This step will allow entry into the parent field only if it is a new record.

From the Code_Mod.txt file, highlight & cut the appropriate code (shown below) [ Parent object to select it; paste code in the bottom area

Figure 138

//------------------------------------------------------------------// Add to Parent (odbForm) object - below the green line // If Header record exists, disallow entry in Related Parent window. //------------------------------------------------------------------Procedure Refresh Integer iMode Integer iSrvr iCrnt Get Server to iSrvr // get the DataDictionary Get Current_Record of iSrvr to iCrnt // get record in DataDictionary // Set displayonly to true if iCrnt is non-zero Set Enabled_State to (iCrnt = 0) Forward Send Refresh iMode // do normal refresh // don't leave us sitting on a displayonly window If (iCrnt and Focus(Self)=Self) Send Next End_Procedure

Data Access Corporation

167

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

This step modifies (overrides) the behavior of the Switch message (sent when we press the F6 key or click in the grid). Under some view structures if a user is in the last object of the header and presses the F6 key, the Switch message would allow them into the table without a valid parent record. To guard against this we will send the Activate message instead of the normal switch message.

From the Code_Mod.txt file, highlight & cut the appropriate code (shown below) [ Last object to select it; paste code in the bottom area

Figure 139

//------------------------------------------------------------------// Add to the Last (oDbForm3) object - below the green line // Normal switch behavior is to attempt to keep looking for additional // objects to switch to. If we can't switch to the detail table, we // want to stop! So just do a simple activate. This solves the problem // of the Save Header not being called if we press F6 (switch) on the // last object. //------------------------------------------------------------------Procedure Switch Send Activate of oDetail_Grid End_Procedure

168

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

This step will make the grid operate correctly for our application. The Append_A_Row will allow us to add records only to the bottom of the grid. Since we are only adding records to the grid bottom there is no need to sort the table after each save, so we will set the Auto_Regenerate_State off. The Child_Table_State will ensure the row is always saved. The Child_Entering will send our Save_Header procedure.

From the Code_Mod.txt file, highlight & cut the appropriate code (shown below) [ oDetailGrid object to select it; paste code in the bottom area

Figure 140
//------------------------------------------------------------------// Add to oDetail_Grid (dbGrid) object - below the green line // Change: Table entry checking. // // // Set Child_Table_State to True which will cause table to save when exiting and attempt to save header when entering. to TRUE // Saves when exit object

//------------------------------------------------------------------Set Child_Table_State

// Called when entering the table. Check with the header if it // has a valid saved record. If not, disallow entry. //

Data Access Corporation

169

Lesson 4 Lab Generated Code


Function Child_Entering Returns Integer Integer iRetVal

Discovering Visual DataFlex

Delegate Get Save_Header to iRetVal // Check with header to see if it is saved. Function_Return iRetVal End_Function //------------------------------------------------------------------// Change: Assign Add-Mode key to Append_A_Row // // Create new behavior to support Append_A_Row Optimize the table refresh // if non-zero do not enter

//------------------------------------------------------------------On_Key KAdd_Mode Send Append_A_Row // Hot Key for KAdd_Mode= Shift+F10 // prepare to add new record by Jumping to blank row at end of grid. Procedure Append_A_Row Send End_Of_Data Send Down End_Procedure // The way this table is set up, items can never be added out // of order. New items are always added to the end of the table. // By setting Auto_Regenerate_State to False we are telling the // table to never bother reordering after adding records. This is // a minor optimization. Set Auto_Regenerate_State to False // table is always in order // // Q: how would a keyboard do this? down 1 line to empty line // A: Go to end of table and

170

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

File | Save as Template | [ Global Invoice_Style [ Save Button Close this component

Figure 141

Data Access Corporation

171

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

Creating Dept/Empl View Using View Templates

File | New Component [ Invoice_Style [ OK button

Figure 142

172

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

We will not need the Parent related object. Right Click on it (the popup menu will appear) select Delete Tools | Database Selector [ Add DDO [ Empl DataDictionary [ Select button [ No to MainDDO popup question [ Main DDO combo and Select Dept [ Close button

Figure 143

Data Access Corporation

173

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

] Right Click on the first object (the popup menu will appear). Select Properties Use the Object Properties dialog st to label the 1 dbForm to Code [ Database tab page [ browse () button in the Data Source area Select Dept.Dept_Code

Figure 144

[ OK Repeat the above steps on the other dbForm, changing the label to Budget and the source to Dept.budget field

Browse Button

174

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Grid Options
Use the Database Selector tool to add the remaining fields to both the top section and to the grid

] (right click) on the grid (for the popup menu) [ Grid Options

Figure 145

Changing the column size can be done by dragging the line in the grid header

Note: All the things that can be done in Grid Options!

[ Hire_Date [ Down Arrow Key until Hire_Date is listed last Make sure the Main file is Empl file and the index is Index.3 [ OK button

Figure 146 Data Access Corporation 175

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

Changing Navigation

Change the label of the View to Dept/Empl View Change the object names (object name, not label) of the first and last objects to oDept_Code and oDept_Budget Use the Object-Order tool to correct the navigation of the objects, make them match the screen shot [ OK button

Figure 147

176

Data Access Corporation

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Here we have to customize the template by setting the default values of four properties.

/ The outer view container to bring up the editor Change the default values of the two properties as shown in the table below

Outer View Container Object

Figure 148

Property Name psHeaderName psFileField

Change value from: Order OrderHea.Order_Number

Change value to: Department Dept.Dept_Code

Data Access Corporation

177

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

[ Save the view filling in the data as shown [ Test/Run current view button Attach the view to the overall application as shown in the previous lab

Figure 149

Warning: If you get ompiling errors such as Bad Image Errors Look for a single slash /-----//---------

And correct the line in code explorer to have a double slash

Things to Notice Activate the Selection Lists Notice the Scroll bars added to all scrollable areas Confirmation Messages for saves and deletes You should not be able to navigate to the grid until a header record is displayed. Try leaving the header blank and: Press F6 from the header (F6 is the switch key) Click into the grid Press tab from the last object in the header Find a header record and then in the grid pressing Shift+F10 (the Add Mode key) will jump to the bottom of the grid. The grid columns can be resized
178 Data Access Corporation
Test the Application noting the items in the chart

A chart of Accelerator Keys is listed in Appendix C.

Discovering Visual DataFlex

Lesson 4 Lab Generated Code

Did You Discover?


1. What is the normal behavior of the Shift+F10 if the Append_a_Row procedure was not available?

2. In the DataFlex language, how do you continue a command line to the next line?

3. Within the DeptEmpl View, go to the grid and enter some test data, but do not save with the F2 key. . . click on a window in the header . . . can you exit the line item without a save occurring? What if you use the down arrow or up arrow? Does the save occur?

4. When the Studio generates the code for an Object the Green Line in the Code Editor will be replace with what?

5. When you find a Department record (in the header section), only the employees for that Department are found and displayed. How does the program know to show only related records in the dbGrid?

Data Access Corporation

179

Lesson 4 Lab Generated Code

Discovering Visual DataFlex

6. Create a new view with two dbForm controls, one showing the Empl.Code and the other one showing the Empl.Last_Name. Make the dbForm for the Empl.Code control using the Database Selector. Make the dbForm for the Empl.Last_Name using the Controls Palette. When you compile and run your new view did both of your controls show data when you find records? What extra step do you have to do with the Controls Palette when creating data-aware controls?

180

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Lesson 5
Data Dictionarys Part 1
This lesson covers how to use the DataDictionary Builder utility (which is incorporated into Database Builder). This utility will allows you to create and edit the DataDictionary files painlessly. Making selections and setting checkboxes generates most code for you. When reading this lesson, no changes should be made to the files until the Lab at the end of the lesson.

Topics in this Chapter:


DataDictionary Classes Business Rules DataDictionary Class & Object Differences Building Data Dictionarys Field Settings Field_Options Field Validation Modal Objects are Popups Using Validation Tables Field Masking Appearance Tab Other Tab page Checkbox Option Status Help Simple Default Value Entry/Exit/Validation Messages Entry & Exit Messages
Data Access Corporation 181

Auto-Assigning Numbers External Structure Lab 5 Building Data Dictionarys for All Database Files Setting Field_Options Setting Field Validation Validation Tables Setting Field Masking Setting Appearance Tab Setting Status Help Field_Default_Value Auto-Assigning Numbers Changing an Objects Class

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

DataDictionary Classes the .DD File


DataDictionarys are our database interface, performing such operations as finds, clears, saves and deletes. This is where our business rules will be located for such things as extra processing before saves and deletes. One large advantage of the DataDictionary class is that it allows us to place the rules of the database and the individual fields in one central location. Using this class will improve data integrity! Every database table should have a (DataDictionary Class) .DD file created We will be creating a .DD file for each of our database files. If a business rule should always apply throughout the application, it will be added to the DataDictionary class definition in the .DD file, but if a business rule should only apply to one view, then it will be implemented in the DataDictionary object within that view.

Note: (for OOP programmers) The same rules we learned in earlier revisions using DataSets will still apply with DataDictionarys. Our familiar DataSet procedures (creating; update; backout) still apply in the DataDictionary. Your application will work with a mixture of views using DataSets and views using DataDictionarys. Just do not mix DataSets and DataDictionarys in the same view. DataDictionarys are much more powerful. If you have existing applications with DataSets, it is recommended to take the time to convert them to DataDictionarys.

182

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Business Rules
Business Rules are rules that must be followed before changes are allowed to the database.

Examples: Verify important facts before allowing saves and deletes. Do not allow a parent record to be deleted if it has related child records. Auto-assign a number for all new records being saved.

Since these are things that happen during saves and deletes, we subclass the DataDictionary Class and add all these rules in our new class.

Business Rules are built into the subclass so they affect ALL views. If the rule should only affect one view then that rule should NOT be in the class, but in the DataDictionary Object within the view that it should affect.

Data Access Corporation

183

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

DataDictionary Class & DataDictionary Object Differences


The Class will contain all the constant business rules that should apply to all views. Setting the State field to be DD_Capslock in the Class will ensure that the State field will be capitalized no matter in which view the data //Customer.DD File was entered.
Class Customer_DataDictionary is a DataDictionary Procedure Define_Fields Set Field_Options Field Customer.State to DD_Capslock End_Procedure : End_Class

This will affect all views

//CallCust.VW
Object Customer_DataDictionary is a Customer_DataDictionary End_Object

//CustGrid.VW
Object Customer_DD is a Customer_DataDictionary End_Object

//Customer.VW
Object Customer_DD is a Customer_DataDictionary : Set Field_Default Field Customer.State to FL End_Object : Object Customer_State is a dbForm End_Object

This will only affect this one view

Note: (Procedural programmers) If you are having problems with the concepts of Objects and Classes refer to the appropriate section in Appendix C.

184

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Building DataDictionarys for Database Files


When a database file is created, a DataDictionary subclass (.DD file) is automatically created. This DataDictionary file can be read back into the DataDictionary Builder and modified whenever required. It is suggested that you make your modifications via the DataDictionary Builder but you are also allowed to modify the code using a text editor.

In order to know when and how to use the many options in the DataDictionarys, you must know what is available. The rest of the lesson exposes you to the many options that the DataDictionary can contain. Use this lesson as a reference as you complete the lab and when you create future projects.

Note: (everyone) Database Builder is the entire utility. DataDictionary Builder has been incorporated within Database Builder and is the last four tabs. Field Settings Methods Options Structures

Data Access Corporation

185

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Field Settings
The six tab pages under the Field Setting tab page are settings that are made at the field level. Be sure to indicate the correct field before setting these options.

Field Options
Warning! If you wish to see these screens on your computer, open any file in Database Builder Utility. No changes should be made until the lab at the end of the lesson or if you see commands printed in this style font (with the horizontal lines at the top and bottom)!

Figure 150

The KeyField option is normally placed on uniquely indexed fields. When a field is flagged as a KeyField and the Protect_Key_State is True (the default), the user will not be allowed to change the value of the field. Example Code Created:
Procedure Define_Fields Forward Send Define_Fields Set Field_Options Field Empl.Code Set Field_Options Field Empl.Code Set Field_Options Field Empl.Code : to DD_AUTOFIND to DD_KEYFIELD to DD_NOPUT

Note: (Prior database developers) Key fields are similar to the Primary Key concept of other databases

186

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Note: (Prior DataFlex Users) In prior DataFlex versions we placed the entry options within the DEOs. They are now placed in the DataDictionary (DD File). This will assure data consistency in our databases. Entry options Range & Check will be covered later in this lesson.

Within DEOs {option}

Within Data Dictionary Set Field_Options Field

Description

AutoFind AutoFind_GE CapsLock DisplayOnly FindReq ForcePut KeyField NoEnter NoPut Retain RetainAll Required SkipFound Zero_Suppress AutoBack AutoClear AutoReturn Points= n Thousands

DD_AutoFind DD_AutoFind_GE DD_CapsLock DD_DisplayOnly DD_FindReq DD_ForcePut Set Key_Field_State DD_NoEnter DD_NoPut DD_Retain DD_RetainAll DD_Required DD_SkipFound DD_Zero_Suppress Not Windows behavior* Not Windows behavior* Not Windows behavior* done with masking done with masking

Find Equal a record automatically Find Greater or Equal a record automatically Uppercase all data in window No entry and no put to record buffer Found indicator must be true to continue Force data from window to record buffer To protect a field from being changed No navigation to data-entry window allowed No put of data to record buffer Keep data in window (clearable) Keep data in window (not clearable) Requires an entry Skip entry if found indicator is true Blanks display if numeric is zero Back up a window on left arrow Clear the window if new data is entered Advance to next window on a full window Decimal points set to (0 1 2...n) Displays thousands separator in numeric fields

Data Access Corporation

187

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Field Validation
Field Validations are accomplished upon forward navigation from the field and prior to the save (outside of a locked state).

Figure 151

Validation Validation Method

Description & Example Code Created: A validation message that will get called whenever there is forward navigation from this field.
Set Field_Validate_Msg Field Cust.St to Ck_State : Procedure Ck_State // add validation code here End_Procedure

Simple Validation Range From Validation Error

Will check that the data is a sub-string of the checked string, e.g.; M|F.
Set Field_Value_Check Field Cust.Sex to M|F

Will check a Numeric or Date Entry is within a specified range


Set Field_Value_Range Field Customer.Credit_Limit to 500 90000

Error Number/Message that will display if a Simple Validation, Range Validation, Validation Table or an incorrect Checkbox Value Validation fails Number is set by developer
Set Field_Error Field Customer.Credit_Limit to 330 ; The Credit Limit must be between @PARAM to @PARAM2

@PARAM# will reflect Validation Values 188 Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Modal Objects are Popups


Modal Objects are objects that require interaction before processing can continue. A Selection List is an example of a Modal object. The F4 key or prompt button is used to send the popup message. When the Selection list is activated the user is forced to interact with it. They cannot click on the menu bar or any other object outside of the modal object. There are many different names for Modal Objects (Popups; Dialogs; Zooms; Selection Lists; Lookups; Prompts). The terminology can be confusing because many of these names are interchangeable. Many classes can operate as modal objects by setting their Modal_State property to true. The ModalPanel and dbModalPanel are two classes that by default already have their Modal_State property set to true. Therefore, most modal objects are created by using one of these classes. Modal Objects Prompts (i.e.: Selection Lists and Validation Tables) Activated by pressing F4 or clicking on a designated button Prompt_Object or Column_Prompt_Object property is set from the calling object Dialogs (i.e.: About or Login Dialogs) Activated by sending Popup_Modal from the calling object Zooms (i.e.: a popup data entry dialog) Activated by pressing Alt+F9 Zoom_Object or Column_Zoom_Object property is set in the calling object

Data Access Corporation

189

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Using Validation Tables


Validation Tables normally contain a list of Codes and Descriptions used to validate entered data and present to the user a list of suggested or required entries. There are four types of validation class tables that can be used.

The Class Hierarchy chart shows the first Validation Class was built from the Array class and then each seceding class has additional functionality and features included. The main difference among the classes is how the source of the data is being displayed.

Class Hierarchy
Array

|__ValidationTable (built from static data) |__DescriptionValidationTable (built from static data) |__FileValidationTable (built from a database table) |__CodeValidationTable (built from existing database tables)

190

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Visual Display of Validation Tables: All of the validation classes will use either a ComboForm or a ValidationList Class as the visual object to display the data.

This is an example of a Validation Table attached to a field and displayed with a comboform class.

Figure 152

If the validation table is attached to a field built from a dbForm class, the validation table will appear as a popup scrollable list. It will be built from the ValidationList Class.
Figure 153 Note: Creating a parent file and building selection lists (lookups) like those that we created in the last lesson will basically accomplish the same thing as validation tables.

Data Access Corporation

191

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Types of Validation Tables The source of the displayed data will determine which class to use for your validation table.

Type None Dynamic Static

Source of Displayed Data CodeMast & CodeType data files Static Hard Coded Values that will not change Programmers specified database table

Class to be Used Clears Field_Value_Table property. CodeValidationTable DescriptionValidationTable (if Values and Descriptions are loaded) or ValidationTable (if only Values are loaded) One of the Validation table objects created manually.

Custom

Checking Blanks will allow blanks or 0 as a valid response

Figure 154

Checking Validate will require entries to exactly match a value in the list

Note: (Everyone) On-line help is always available. Use it for a more complete explanation of all settings.

192

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

None is to clear the Field_Value_Table.

Figure 155

Note: If you have entered values into the grid for a static type validation table, selecting None will clear the values entered for the Static validation table. This will require you to re-enter the data if the none option was click by mistake.

Data Access Corporation

193

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Dynamic sets the Validation Tables class to CodeValidationTable. By default this class uses the predefined database files CodeMast and CodeType. The Type Value form should be filled in to indicate the code type from the CodeMast file. New Type Value Button allows you to add a CodeType record so it will be available in the Type Value combobox. But normally we create the records first as shown below.

Figure 156

The Maintain Code File dialog is used to create records for the validation table.

This dialog can be reached from the Studio Workspace pull-down and the Code Master Maintenance option. Two empty database files, CodeType and CodeMast are included in the \Data subdirectory. After creating the records in this utility they will be available when you create Dynamic Validation Tables.
Data Access Corporation

Figure 157 194

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Example Code Created:


// The default file used with the CodeValidationTable class is "CodeMast.dat & CodeType.dat" // Therefore, code & description fields and the index is known Object Empl_Pay_Type_VT1 is a CodeValidationTable Set Type_Value To "PAYTYPE" End_Object // Empl_Pay_Type_VT1 : Procedure Define_Fields Forward Send Define_Fields : Set Field_Value_Table Field Empl.Pay_Type To (Empl_Pay_Type_VT1(Self)) // used in conjunction with the Validation Tables above

Note: a useful property is: Static_State Set Static_State to True // Will load its list only once in each session. Set Static_State to False // If application allows editing of the list, //such as a code Maintenance view

Note: Since CodeMast and CodeType files are being opened as file numbers 207 and 208 these file numbers should not be used.

Data Access Corporation

195

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Static Uses static data that is hard coded into the object. It sets the Validation Tables class to Description ValidationTable (if Values and Descriptions are loaded) or ValidationTable (if only Values are loaded)
Figure 158

Example Code Created:


Object Empl_Pay_Type_VT is a DescriptionValidationTable Set Allow_Blank_State To TRUE Set Table_Title Procedure Fill_List Forward Send Fill_List Send Add_Table_Value "H" "Hourly" Send Add_Table_Value "S" "Salary" Send Add_Table_Value "P" "Part-Time" Send Add_Table_Value "C" "Contract" End_Procedure // Fill_List To "Select Pay Type"

End_Object // Empl_Pay_Type_VT:

Procedure Define_Fields Forward Send Define_Fields : Set Field_Value_Table Field Empl.Pay_Type To (Empl_Pay_Type_VT(Self)) // used in conjunction with the Validation Table above :

196

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Custom for any other class that you have used for the Validation Table. Normally a FileValidationTable is used. If you select Custom, then Database Builder will not allow you to configure the Validation Table object and the object will have to be manually built.

Use this class to display/ validate from Database files or DataDictionarys. Normally it is better to use a Selection List because of performance.
Figure 159

Data Access Corporation

197

Lesson 5 Data Dictionarys Part 1


Open Chg_Code //Open the new database that will be used

Discovering Visual DataFlex

Object Charge_Table is a FileValidationTable

// Developer creates the Code File therefore // the fields used for Code & Description must be // indicated along with the correct index to use.

Set Main_File to Chg_Code.File_Number Set Code_field to 3 Set Description_field to 4 Set Ordering to 1 Set Validate_State to True Set Allow_Blank_State to True End_Object // Charge_Table Procedure Define_Fields Forward Send Define_Fields : Set Field_Value_Table Field Empl.Pay_Type To (Charge_Table(Self)) // used in conjunction with the Validation Table above : // field 3 is the charge card code field // field 4 is the charge card description field // index that contain the segments // Chg_Code.Code & Chg_Code.Desc // requires entries to exactly match a value in the list // will allow blanks or 0 as a valid response

198

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Field Masking
This powerful feature enables you to define a data-entry template, or mask, for the values that can be entered into a field. Field masks constrain entries to only those characters, digits and special characters that the masks allow, and only in those specific positions within a field that you predefine. The mask characters are not saved in the database files and are mainly for improving the appearance of the displayed data.

1. Default Masks: Most of the time the default Field_Mask_Type settings are all that is required. There are four Field_Mask_Type settings. Their defaults will be covered in a table in the next section.

Figure 160

Example Code Created:


Set Field_Mask_Type field Customer.Balance to Mask_Currency_Window

// The following Mask_windows are normally not set since they are the default Set Field_Mask_Type field Customer.Name to Mask_Window Set Field_Mask_Type field Customer.Last_Order_Date to Mask_Date_Window Set Field_Mask_Type field Customer.Age to Mask_Numeric_Window

Data Access Corporation

199

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

2. Custom Masks: Sometimes the default masks are not sufficient and customized masks must be created. This is done in two steps. First, set the Field_Mask_Type property to the correct type, then customize a mask with the Field_Mask property. Token characters are shown in the tables on the next few pages.

Figure 161

Example Code:
Set Field_Mask_Type Set Field_Mask

You can also add custom masks to a repository to use later.

Field Empl.Soc_Sec_Number Field Empl.Soc_Sec_Number

To MASK_WINDOW To "###-##-####"

The hyphens in the mask will not be saved to the database. This means that the field length will not need to be increased

200

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Non-token characters (defined for the Field_Mask_Type) will be displayed literally. Token characters can be displayed literally by preceding each with a backslash (\).
Field_ Mask_ Type Defaults Mask_Window Windows default Token Char. # @ ! * Mask_Currency_Windo w & Mask_Numeric_Window "$,*;($,*)" *" , . ; # * 0 Contents of Token Each token occupies one place unless noted 0 - 9 (or blank) any alphabetic character (no numbers) any punctuation character any printable character insert local thousand separator insert local decimal indicator separates positive & negative formats 0 - 9 (or blank) any number of digits including none 0 - 9 (cannot be blank) 1 - 12 01 - 12 Jan - Dec (abbreviated) January - December 1 - 31 01 - 31 Sun - Sat (abbreviated) Sunday - Saturday 00 - 99 1700 - 2900 (diagonal is replaced with the local date separator)

Mask_Date_Window

default should not be changed

m mm mmm mmmm d dd ddd dddd yy yyyy /

Note: Dates will take Microsoft Windows Settings over the mask!

Data Access Corporation

201

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

3. Masks in DEOs: If the mask should only affect one Data Entry Object (DEO) in a view, it can be altered with one of the properties shown
// Set Currency_Mask item_num to integer integer [string] // // // Set Currency_Mask 0 to 8 2 $,*;$,*- : : Set Numeric_Mask 0 to 6 0 *% string is optional second integer is number of digits to right of decimal first integer is number of digits to left of decimal

4. Changing the default masks:

You can change the global defaults of Currency_Mask_Window and Numeric_Mask_Window. This is done by altering the Default_Currency_Mask and Default_Numeric_Mask string(s) within the DFBASE.PKG. When you wish to change the global strings for only one application, you can change the string(s) immediately after the "Use DFAllEnt" statement.

Use DFAllEnt Move ,* to Default_Numeric_Mask

202

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Appearance Tab
This tab allows us to set the default class our visual controls will be built from in the Studio. The Magic Wand button (Automatic Class Selection) on the Database Selector tool defaults dbEdit objects for all TEXT fields; and dbForm objects for all other type fields. Using the Appearance tab page, we can set the type of class that objects will default. Automatic Class Selection

Figure 162

Figure 163

We created a Static Validation type table on the Pay_Type. By our setting the Visual Control to dbComboForm, the Studio will create a dbComboForm (not a dbForm) whenever an object is built from this field. Any objects created by the Studio prior to setting this option are not affected.

Example Code:
Set Field_Class_Name Field Empl.Pay_Type To "dbComboForm"

Data Access Corporation

203

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

The Long and Short Labels will be displayed as the visual label when we create an object from the field in the Studio. The short label will be used in all list type objects (such as dbGrids) and the long label will be used as the label in all other types of objects. This will speed the creation of all our views and will keep our labels constant throughout our application. If the labels are not set, then the Studio will use the field name as the label.

Figure 164

Example Code:
Set Field_Label_Long Set Field_Label_Short Field Empl.Soc_Sec_Number Field Empl.Soc_Sec_Number To "Social Security Number" To "SSN"

Note: The Auto_Label_State property will use the Long Label setting. See the on-line help for a full description of this property.

204

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Other Tab page


This tab page allows us to quickly enter a variety of items for each field in our database. The last item, Short Description allows the programmer to add programming comments for each field.

Checkbox Option
The Checkbox option will make the field into a checkbox. In the Contact sample (a sample provided with VDF) we can see that the Studio will create the visual control for the STATUS field as a checkbox. The values saved to the database will be an A for active (true- checked) or an I for inactive (false- unchecked).

Figure 165

Data Access Corporation

205

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Status Help
Status Help will display at the bottom of the screen whenever the user enters this field.

Figure 166

Example Code:
Set Status_Help Field Empl.Last_Name To "Please enter the employee's last name. "

206

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Simple Default Value


Establishes the default value that will appear after a clear. It is only a default and can be overwritten. Entering values into the Default Value option will add lines into the procedure called Field_Defaults.

Figure 167

Example Code:
Procedure Field_Defaults Forward Send Field_Defaults //DDB-FieldDefaultStart Set Field_Changed_Value Field Empl.St //DDB-FieldDefaultEnd End_Procedure // Field_Defaults To "FL"

Note: (Everyone) This can also be a function such as (MyFunc(Self, parm1 parm2,)). Functions will be covered in a later lesson.

Data Access Corporation

207

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Entry/Exit/Validation Messages
Many times processing must be done as the user enters into or out of a data entry window. The Field Entry, Exit, and Validation messages allow the programmer to send a message to accomplish extra processing.

Data Dictionary Property


Field_Entry_msg

Description
Message sent before entering an item. Returning a non-zero value will stop entry into the item.
Set Field_Entry_msg Field Empl.Hire_Date to Current_Date

Field_Exit_msg

Message sent before exiting an item. Returning a non-zero value will stop exit from the item.
Set Field_Exit_msg Field to Adjust_Ext_Price

Field_Validation_msg From the Validation / Lookup tab page

Message sent before forward navigation from an item, it is called again just prior to the lock of a save operation. Returning a non-zero value will stop forward navigation /save.
Set Field_Validation_msg Field Empl.Hire_Date to Current_Date

Class OrderHea_DataDictionary is a DataDictionary Set Field_Entry_Msg Field Empl.Hire_Date To Current_Date

// This is our newly created procedure // It adds a default date if the field is blank and not changed Procedure Current_Date Integer iField Date dDate Boolean bChanged Get Field_Changed_State iField to bChanged If ( bChanged=0 AND dDate = 0) Begin SysDate4 dDate Set Field_Default_Value iField to dDate End End_Procedure

These messages will pass the Field number and the value of the current DEO.

208

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

Entry & Exit Messages


Entry and Exit Methods are a two-step process.

Step 1 Under the Methods tab create a new procedure.

Figure 168

Step 2 Under the Other tab page list the procedure name to send when entering this field.

Figure 169 Note: You should NOT change the normal navigation during these procedures. If you return a non-zero value it will not allow you to enter/exit. Do not try to have it jump to a new location on screen this should be done by augmenting a message like Refresh or Next. Remember these messages will affect ALL views and should not contain code with features that should only apply to a single view.

Data Access Corporation

209

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Two Arguments are passed with Field_Entry, Field_Exit & Field_Validation messages: Field Number and Field Current Value

Example of each (the fields in this example are not the same as our Empl file):
Set Field_Entry_msg Set Field_Exit_msg Field Empl.Dependents to Default_Dep Field Empl.Birthday to Calc_Age to Check_Age

Set Field_Validation_msg Field Empl.Age

Procedure Default_Dep Integer iField Integer iDependents // Default to one if blank, on entering If (iDependents =0) Set Field_Default_Value Field Empl.Dependent to 1 End_Procedure Procedure Calc_Age Integer iField Date dBirthday Integer iAge Date dToday Sysdate4 dToday Calc ((DateGetYear(dToday)) - (DateGetYear(dBirthday))) to iAge // If you havent had your birthday this year you must decrement iAge If ((DateGetDayofYear(dToday)) < (DateGetDayofYear(dBirthday))) Decrement iAge Set Field_Changed_Value Field Empl.Age to iAge End_Procedure Function Check_Age Integer iField Integer iAge Returns Integer // Validate Age is less then 100 If (iAge > 100) Function_Return 1 Else Function_Return 0 End_Function // would remain in the age window - shift+tab would work // Updates Age when Birthday field exited

210

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

The passing of these arguments (Field_Number and Current_Field_Value) allows us to call the same procedure from multiple fields. This example calls the same procedure from the Customer.First_Order_Date and Customer.Last_Order_Date fields.
Class Customer_DataDictionary is a DataDictionary ... Set Field_Entry_msg Set Field_Entry_msg Procedure Default_Today Integer iFieldnum Date dDate Integer bChanged Get Field_Changed_State iFieldnum to bChanged //has field been changed? 0=not changed If ( bChanged=0 AND dDate = 0) Begin SysDate4 dDate // put system date into dDate // but will not toggle Field_Changed_State End End_Procedure //Default_Today End_Class Set Field_Default_Value iFieldnum to dDate // displays current date to screen Field Customer.First_Order_Date Field Customer.Last_Order_Date To Default_Today To Default_Today

Data Access Corporation

211

Lesson 5 Data Dictionarys Part 1

Discovering Visual DataFlex

Auto-Assigning Numbers
Use this feature when you wish a field in each new record to be automatically assigned the next incremented number. Steps: 1. Select the field that will be autoassigned 2. Assign the File.Field to increment in the Auto Increment form. Step #2 List file.field to increment For ease of use, have these checkboxes checked

Step #1 Select the field

Figure 170

3. If the incrementing file is not part of the DataDictionary structure, list it as an external file from the Structures Tab page. This will only have to be verified if the checkbox above is checked.

Step #3 External Lock if needed


Figure 171 212 Data Access Corporation

Discovering Visual DataFlex

Lesson 5 Data Dictionarys Part 1

External Structure All files that are not part of the DataDictionary structure but will be manually updated must be listed here so they will be locked properly.

The system file must be locked during the save operation so we list it as an Externally Updated File.

Figure 172

For optimization purposes we only lock the system file on new saves and deletes!

Figure 173
Open Empl Open SysFile

Example Code:

// External (System) file structure............. Send Add_System_File Sysfile.File_Number DD_LOCK_ON_NEW_SAVE Define_Auto_Increment Sysfile.Last_Empl_Num To Empl.Code

Note: (Everyone) This DataDictionary method supports only one auto-increment field per file. Data Access Corporation 213

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Lesson 5 Lab
Description: This lab creates and edits the DataDictionary (.DD) files reviewing the many items the lesson covered.

Tasks: In this lab, we will build more features into the .DD files. Modifications that are made require little typing, so these modifications have not been added to the Code_Mod.TXT file.

Building DataDictionarys for All Database Files


If Database Builder is closed reopen it.
File | Open [ Dept [ Empl [ TimeCard [ Wk_Sum [ Open

Figure 174

214

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Setting Field Options


In the Empl File:
[ Field Settings Tab [ Code field [ Options Tab [ AutoFind [ KeyField [ NoPut Enter the other field Options from the chart below

Figure 175

File Empl St Dept

Field Soc_Sec_Number

Entry Option AutoFind CapsLock CapsLock CapsLock CapsLock CapsLock, Required AutoFind, KeyField, CapsLock

Pay_Type Logged TimeCard Dept Reason_Code Dept_Code

Data Access Corporation

215

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Setting Field Validation


This validation will be on the Empl.Pay_Rate field. If Pay_Rate does not fall within 5 and 100,000 the Error #330 Rate must be between $5 and $100,000 will be displayed.

In the Empl File:


[ Validation/Lookup Tab [Pay_Rate field Fill in the Range From/To and the Validation Error forms as shown

Figure 176

216

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Validation Tables
Static Table

[ Validation Table Tab [Pay_Type field [ Static Type Fill in the Value and Description columns as shown

Figure 177

Data Access Corporation

217

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Creating Dynamic Tables is a two step process: 1. Create validate records in the Studio using the Code Maintenance view. 2. Create the Validation table in Database Builder

Step #1 Create records in the Studio using the Code Maintenance view.

Save & Close all files in Database Builder and return to the Studio [ Workspace [ Code-Master Maintenance Fill-in & Save the following reason code records Close the Code Maintenance View

Figure 178

218

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Step #2 Create the Validation table in Database Builder

Return to Database Builder & reopen the files the Reason Code records will not show up if the files are not reopened [ TimeCard file [ Reason_Code field [ Field Settings [ Validation Table Tab [ Dynamic Radio [ Type Value Combo and select Reasons

Figure 179

Data Access Corporation

219

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Setting Field Masking

[ Empl file [ Pay_Rate field [ Field Settings [ Mask Tab [ Mask Type ComboBox [ Currency Complete the mask setting for the Employee & Dept files from the table

Figure 180

File.Field to Mask Empl.Phone Empl.Soc_Sec_Number Dept.Budget

Mask Type Text Text Currency

Custom Mask (###) ###-#### ###-##-####

220

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Setting Appearance Tab


Using the Visual Control, we set the Pay_Type field to dbComboForm. Now whenever we place this field in a view, the Studio will create a dbComboForm object instead of the default of a dbForm. This will also make our static validation table that we just built appear using a dbComboForm. Within the Empl file:
[ Appearance Tab [ Pay_Type field [ Visual Control [ dbComboForm

Figure 181

This will set the label. The default is the field name.
[ Soc_Sec_ Number field Social Security Number Soc Sec Num

Figure 182

Data Access Corporation

221

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Setting Status Help


Status Help will display the help line at the bottom of the screen whenever the user enters this field.

[ Code field [ Other Tab page In Status Help area Type: New employees will be assigned the next available number. Create your own Status Help lines for a few other fields in the files

Figure 183

222

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Field_Default_Value Property
[ St field Enter FL as the Default Value

Figure 184

Alternatively, we could make this a dynamic default by using the Procedure Field_Defaults under the Method tab page. The added code would look like this:

Procedure Field_Defaults Forward Send Field_Defaults //DDB-Generated-Code-Location Set Field_Default_Value Field Empl.St to Sysfile.Local_State End_Procedure // Field_Defaults

Data Access Corporation

223

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Auto-Assigning Numbers
We will auto-assign Empl.Code field by incrementing the Sysfile.last_empl_num field

[ Empl.Code field [ prompt button to the right of Auto Increment [ SysFile [ Last_Empl_Num [ OK

If the SysFile is not listed, open the SysFile and check the System File checkbox on the Parameters tab page. This checkbox will do .step #2 automatically This step checks that the SysFile is listed correctly.
[ Structures Tab Check that the SysFile is listed if not [ 2nd button in the External Structure Area & add it [ Lock Button [ Lock on New Save [ OK Save All Files & return to Studio

Figure 185

Figure 186

224

Data Access Corporation

Discovering Visual DataFlex

Lesson 5 LabData Dictionarys Part 1

Changing an Objects Class


Open the Empl_View in the Studio Open the Object Properties dialog [ Pay_Type Note the class type is dbForm ] Pay_Type [ Change To [ dbComboForm Enlarge the Pay Type object horizontally for the button

Figure 187

Things to Notice Try to delete an Empl record. An error message will appear! We will learn how to solve this problem in the next lesson, when we cover how Saves and Deletes propagate. Create a new Empl record and note the Save validation message. Also, check that the employee code is auto-assigning from the system file. Check the ComboForm Validation Table on the Pay_Type field Check for the Error message when Pay_Rate value is out of range Check the Default Value of the state field Status Help lines appear for the Empl.Code field
Data Access Corporation 225
Compile and Test the Application Open the Empl View and note the items in the chart

Lesson 5 Lab Data Dictionarys Part 1

Discovering Visual DataFlex

Did You Discover?

1. Where in the Studio and Database Builder will a right-mouse-click call up a popup menu?

2. What are the advantages of validation tables over creating a parent related file?

3. What are the advantages of a parent related file over a validation table.

226

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Lesson 6
Data Dictionarys Part 2
This lesson covers the more advanced topics of DataDictionarys.

Topics in this Chapter:


Methods Tab Options Tab Foreign Field Options Error Handling Structures Tab Cascade Delete Database Explorer Lab 6 Methods Tab Structures Tab Initializing Auto-Assign Number

Data Access Corporation

227

Lesson 6 Data Dictionarys Part 2

Discovering Visual DataFlex

Methods Tab
The Methods Tab allows us to add manual code, such as new procedures or modification of existing procedures, to the DataDictionary Class. In the lab, we will be modifying the Update and Backout procedures to send a new message called Adjust_Running_Empl_Total that will increment or decrement the running Employee total for that department. We could simplify this by eliminating the Adjust_Running_Empl_Total procedure and just put the calculation into the Update and Backout procedures but by adding the new procedure, it demonstrates how to accomplish more complex running totals.

Figure 188

The list of Unaugmented Methods allows you to quickly add the most often used procedures and functions. Double clicking on the procedure name will create a blank procedure ready for custom code additions

228

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Options Tab
The Options tab page displays various datadictionary options that apply across all fields in the file.

Foreign Field Options

Figure 189

When entering new records into a database the field options from the Field Setting / Options page are enforced. When the data is not of the main file of a view (but data of the related parent) it is common that additional options are needed. These options are referred to as Foreign Field Options and are separated into three groups: Key Fields, Indexed Fields and Default Fields (which include all other fields).

When entering new records for the Empl file, you would want to be able to enter an Employees Soc_Sec_Number, which is an index field. However, in a Time Card view, (where the Empl file is the parent file and not the main file that is being saved) you might wish to find on this field but you would never wish to change it. This is why you will use the Find Required and NoPut options on the Indexed Foreign Field Options.

Error Handling This is the general error message for all validates that fail and do not have an individual field error message set (Field Setting/Validation Lookup tab page). The error is triggered when one of the following validations fail: Simple Validation, Range Validation, Validation Table, or an incorrect Checkbox Value. These Validation Error Methods should be a function coded at the class level.
Data Access Corporation 229

Lesson 6 Data Dictionarys Part 2

Discovering Visual DataFlex

Structures Tab
Many tasks require the DataDictionarys to communicate among themselves. An example is the save operation that propagates up the structure so all running totals are updated. A delete operation propagates down to delete child records (and then up to update running totals). The DD structure linking is normally always the same as the file structure. Therefore, the Magic Wand buttons will check the file relationships and connect missing parent/child files accordingly. The wand will only add to the list, it will not remove files from the list. Therefore, remove all files before using the magic wand.

The Delete and Save Structure Mode is used to verify the Data Dictionary Structure. It is normally safest to leave these radios to validate once (the first time).
Figure 190
To Empl.File_Number To DD_AUTOFIND DD_NOPUT DD_FINDREQ To DD_DISPLAYONLY

Example Code:
Set Main_File

Set Foreign_Field_Options DD_KEYFIELD Set Foreign_Field_Options DD_DEFAULT // Child (Client) file structure................ Send Add_Client_File Timecard.File_Number Send Add_Client_File Wk_Sum.File_Number // Parent (Server) file structure............... Send Add_Server_File Dept.File_Number // External (System) file structure.............

Set Foreign_Field_Options DD_INDEXFIELD To DD_NOPUT DD_FINDREQ

Send Add_System_File Sysfile.File_Number DD_LOCK_ON_NEW_SAVE

230

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Cascade Delete
Check this option to delete all related child records whenever a delete is performed. Unchecking this option will abort the deletion if any related child records exist.

Uncheck the Cascade Delete option on the Empl database table Save the file

Figure 191

For tax purposes, we should never delete an employee that has child (TimeCard) records.

Example Code:
Set Cascade_Delete_State to False //unchecked

If you try to delete a parent record, which has related child records, this error will be generated: 4140 (Cannot delete-related records exist)

Data Access Corporation

231

Lesson 6 Data Dictionarys Part 2

Discovering Visual DataFlex

Database Explorer
This useful utility can be accessed directly from the Start | Programs | Visual DataFlex menu or from the Studios Database pulldown menu. It will allow you to view and change your raw data stored in your database tables. To allow changes to the database tables you must first change a default configuration setting.

From the Studio


[ Database | Database Explorer [ Tools | Configure Environment [ Open/set datafiles readonly (uncheck it) [ Apply

Figure 192

[ Close Look around at the many features in this

utility

You will find MANY uses for this utility. Here are just a FEW tasks that Database Explorer can do: View and change raw data stored in your database tables Zero the database tables of test data before deploying the application Export data to ASCII or XML format

232

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Lesson 6 Lab
Description: Creating more Business Rules within the DataDictionary.

Tasks:

Methods Tab
First, we will create blank procedures: Within the DBB, open the Empl file:
[ Methods Tab Expand the Unaugmented Methods Tag / Backout / Update

Figure 193

Data Access Corporation

233

Lesson 6 Lab Data Dictionarys Part 2

Discovering Visual DataFlex

If the Code_Mod.txt file is not open Open it in the editor (File | Open File).
Add the new procedure and modify the Update and Backout procedures by cutting & pasting the changes from the Code_Mod.txt file

Figure 194
// this is added to the Methods tab of the Empl DD // Adjust_Running_Empl_Total: Procedure Adjust_Running_Empl_Total Integer iOne_More Calc (Dept.Number_of_Empl + iOne_More) to Dept.Number_of_Empl End_Procedure // Adjust_Running_Empl_Total

// This is added to the Update Procedure of the Empl DD Send Adjust_Running_Empl_Total 1 // This is added to the Backout Procedure of the Empl DD Send Adjust_Running_Empl_Total -1

234

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Another business rule is in the TimeCard file. Whenever a TimeCard record is created, we need to update the status of the employee to Logged In or Logged Out.

Open the Timecard file [ Methods Tab Expand the Unaugmented Methods Tag / Creating Modify the procedure as shown Save & Close file

Figure 195

// This is added to the Creating Procedure of the TimeCard DD Move TimeCard.In_or_Out to Empl.Logged

Data Access Corporation

235

Lesson 6 Lab Data Dictionarys Part 2

Discovering Visual DataFlex

Structures Tab
The Required Child and Required Parent list should match our file relationship structure.
This step was accomplished in Lab 2 and can be skipped if done in that lab If there are any files listed in the Required Child/Parent file areas delete them using the delete button. [ Magic Wand in the Required Child files [ Magic Wand in the Required Parent files Repeat this step for all files Save and Close all the files

Figure 196

236

Data Access Corporation

Discovering Visual DataFlex

Lesson 6 Lab Data Dictionarys Part 2

Initializing Auto-Assign Number


Database Explorer is a separate utility that enables us to view and modify database table contents. We will use it here to quickly adjust the raw data in our SysFile table. This lab has just added an auto increment feature that will increment the current number in the SysFile.Last_Empl_Num field and assign it to the Emp.Code field of the next newly saved record. We have existing records in the Employee file that could create a problem. If the SysFile.Last_Empl_Num is set to 10 it would try to assign 11 to the next saved record. If there was already a record 11 in our database, it would give a Duplicate records not allowed in file error. To avoid duplicating an Empl number we will set the Sysfile.Last_Empl_Num field to a number larger than any saved record in the Empl file.
Return to the Studio Database | DBExplorer [ Empl File Note the largest Empl Code number [ SysFile Enter a Company Name and Local State then in the Last_Empl_Num enter a number larger than any saved Empl.Code record

Figure 197

This is a system file so it should only have one record created! Save and Exit

Data Access Corporation

237

Lesson 6 Lab Data Dictionarys Part 2

Discovering Visual DataFlex

Did You Discover?

1. When using the magic wand button in the Structures tab page of Database Builder will it remove unneeded files from the required Child/Parent list?

2. What is the difference between the Validation Error No. & Text on the Field Setting | Validation/Lookup Tab and Validation Error No. & Text on the Options tab?

3. In Database Builder under the METHODS tab if you select a method from the Unaugmented list what happens to the Unaugmented and Implemented lists?

238

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

Lesson 7
Connecting Parts
Music will never be heard from a multi-unit stereo system if the cables between units are connected incorrectly. This lesson talks about DataDictionarys (DDs) and DataDictionary Objects (DDOs) and the connections they have. Proper connections of the DDs and DDOs in your application are crucial to it operating correctly.

Topics in this Chapter:


Differences between the DD Class files and the DDOs Connecting DDs to DDs within the DataDictionary Class Connecting DDOs to DDOs within the View Connecting DEOs to DDOs within the View Object Nesting Encapsulation of DDO Structure Lab 7 Completing the DDO structure of our Views

Data Access Corporation

239

Lesson 7 Connecting Parts

Discovering Visual DataFlex

Differences between the DD Class Files and DDOs


1.) DataDictionary Classes (.DD files) - Classes are tools: Using Database Builder, we create a .DD file for every database file. These are Subclasses of the DataDictionary Class. Additions in these .DD files will affect all views

// Wk_Sum.DD File Class Wk_Sum_DataDictionary is a DataDictionary // TimeCard.DD File Class TimeCard_DataDictionary is a DataDictionary End Class // Empl.DD File End Class

Class Empl_DataDictionary is a DataDictionary End Class // Dept.DD File Class Dept_DataDictionary is a DataDictionary End Class

We build the business rules in these files created in Database Builder utility.

Figure 198 240 Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

2.) DataDictionary Objects in the Views: In our View, we have DDOs that are built from the DataDictionary Class that we create in Database Builder Utility.
// Empl_View.VW ACTIVATE_VIEW Activate_Empl_View FOR Empl_View

Additions here only affect this single view

Object Empl_View is a dbView Set Label to "Empl_View" Set Size to 210 410 Set Location to 6 7 Object Dept_View is a dbView Object Dept_DD is a Dept_DataDictionary Set Status_Help Field Dept.Code to ; "F7 & F8 will find all dept records End_Object // Dept_DD //AB-DDOStart Object Empl_DD is a Empl_DataDictionary Set DDO_Server to Dept_DD End_Object // Empl_DD Object Dept_DD is a Dept_DataDictionary End_Object // Dept_DD Set Label to "Dept View" Set Size to 170 354 Set Location to 6 6 // Dept_View.VW ACTIVATE_VIEW Activate_Dept_View FOR Dept_View

Set Main_DD to Empl_DD Set Server to Empl_DD

Set Main_DD to Dept_DD Set Server to Dept_DD

Object Container1 is a dbContainer3d Set Size to 60 393 Set Location to 5 5

Object Container1 is a dbContainer3d Set Size to 145 335 Set Location to 5 5 Object Dept_Code is a dbForm Entry_Item Dept.Dept_Code

Data Access Corporation

241

Lesson 7 Connecting Parts

Discovering Visual DataFlex

We move the business rules into our view by adding DDOs through the database Selector tool:

Figure 199

242

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

Connecting DDs to DDs within the DataDictionary Class


Related files need their DataDictionarys connected. To properly function, there must be a two-way communication between the DataDictionarys.

File Relationships: The connection between child-to-parent file relationship is only one way. DataDictionary Structure: The connecting of DD to DD is bi-directional and done with the Send Add_Client_File and Send Add_Server_File messages.
Dept.DD

Empl.DD

TimeCard.DD

Wk Sum.DD

//Sample code showing these methods: Class Empl_DataDictionary is a DataDictionary Procedure Define_Fields // Child (Client) file structure................ Send Add_Client_File Timecard.File_Number Send Add_Client_File Wk_Sum.File_Number // Parent (Server) file structure............... Send Add_Server_File Dept.File_Number

Data Access Corporation

243

Lesson 7 Connecting Parts

Discovering Visual DataFlex

This is where we make the DataDictionary to DataDictionary connection.

Figure 200

Code generated in the Empl.DD file will look like this:


: // Child (Client) file structure................ Send Add_Client_File Timecard.File_Number Send Add_Client_File Wk_Sum.File_Number // Parent (Server) file structure............... Send Add_Server_File Dept.File

244

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

Connecting DDOs to DDOs within the View


Related files need their DDOs connected. In order for our database operations to perform correctly, we link our DDOs together much like our file relationship structure. Save operations propagate up and Deletes propagate down. Therefore, both connections are normally made.

The connecting of DDO to DDO is done by setting the DDO_Server property. We connect DDOs when they should act in a coordinated manner. As a general rule, the child-to-parent file updating links will match the child-to-parent relationships.

Dept

Empl

TimeCard

Wk_Sum

Data Access Corporation

245

Lesson 7 Connecting Parts

Discovering Visual DataFlex

DataDictionary Object Structure: Once an updating dependency is established, the DDOs "know" about each other and can communicate directly among one another.

DEFERRED_VIEW Activate_Order_Entry FOR ; Object Order_Entry is a dbView Object Dept_DD is a Dept_DataDictionary End_Object // Dept_DD Object Empl_DD is a Empl_DataDictionary Set DDO_Server to Dept_DD End_Object // Empl_DD Object TimeCard_DD is a TimeCard_DataDictionary Set DDO_Server to Empl_DD End_Object // TimeCard_DD Object Wk_Sum_DD is a Wk_Sum_DataDictionary Set DDO_Server to Empl_DD End_Object // Wk_Sum_DD

246

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

Manual Steps to create a DataDictionary Object Structure in the Order Sample: Step 1 Code an object for each file. Start at the top of the file structure, and work from left to right and from top to bottom. Listing the DDOs in this order will eliminate forward reference problems of referencing a DDO in a Server property before the object declaration. Add the required DDO_Server properties. Each child file will have a Server property for each of their parents Add a constraint block in the child DDO if needed! Not all child files should be constrained. Think about your application and add the constraints where they are required.

Step 2 Step 3

Connecting DDOs within the Studio is done from the Database Selector Tool and pressing the DDO Tree button.

Since the Main DDO is OrderHea, all children files will be constrained

Figure 201

Data Access Corporation

247

Lesson 7 Connecting Parts

Discovering Visual DataFlex

Connecting DEOs to DDOs within the View


In order for our views to operate correctly, each DEO should have a DDO that services it, during Finds, Clears, Saves, and Deletes. The DEO to DDO connection is made on the Database tab in the Object Properties Tool.

If a direct server is not set, then the parent objects server (Indirect server) is used. A parent object is just the object in which the current object is contained.

Figure 202

248

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Connecting Parts

The Server property is what links the DEOs to their DDO Server.

Object Customer_DD is a Customer_DataDictionary End_Object // Customer_DD Object Cust_Name is a dbForm Set Server to Customer_DD End_Object // Cust_Name Object Cust_Address is a dbForm Set Server to Customer_DD End_Object //Cust_Address Object Cust_City is a dbForm Set Server to Customer_DD End_Object // Cust_City

DataDictionary Objects (DDOs) are objects that act as an interface between the database file and the Data Entry Objects. They are objects built from the filename_DataDictionary class that we created using Database Builder. Therefore, they will know about all the business rules we created. Data Entry Objects, (DEOs) are objects that allow data entry, such as dbForms, dbGrids, and dbEdits.

Data Access Corporation

249

Lesson 7 Connecting Parts

Discovering Visual DataFlex

Object Nesting
Nesting of Objects is the actual physical positioning of one object inside another object in the source code. The Studio tool Controls Palette has data containers that are useful in grouping data aware objects. Direct Server specifically Object Customer_DD is a Customer_DataDictionary set in this object
End_Object // Customer_DD Object Customer_Info is a dbContainer3d Set Server to Customer_DD Object Customer_Name is a dbForm End_Object // Cust_Name Object Customer_Address is a dbForm End_Object // Cust_Address Object Customer_City is a dbForm End_Object // Cust_City End_Object // Customer_Info

Notice here that by setting the server in the parent data container object we do not need to set it in the individual data aware objects

DDOs should never contain DEOs. Since these objects do not specifically set the Server property (Direct Server), they will use their parent objects server (Indirect Server)

Reasons for nesting DEOs: Navigation / Visual Design Changing the cursor navigation through the objects by adding container objects. Organizing related fields inside a container will allow the use of the F6 key (the switch accelerator key) to jump to the next container and back. Delegation of Messages (i.e.; the setting of the server in the data container indirectly sets the server of the nested dbForms)

250

Data Access Corporation

Discovering Visual DataFlex

Lesson 7

Encapsulation of DDO Structures


In the prior examples, we saw each View having DDOs and DEOs that connect by way of the SERVER property. Data Entry Objects in each view are served by DataDictionary Objects within their own view. This is what makes each view operate independently of all other views!

Views should be independent separate units!

Different Customer record displaying in each view. This is what we want!

Figure 203

If the objects are using different DDOs, then each will work independently of the other.

Data Access Corporation

251

Lesson 7 Lab Connecting Parts

Discovering Visual DataFlex

Lesson 7 Lab
Description: Checking the DDO structure of our views so they operate correctly.

Tasks:

Completing the DDO Structure of Our Views


In previous lessons, we discovered that we could add records to our views but we could not delete records. In this lesson we covered how important the connections between DDOs are for the operation of the view. We also learned that Saves propagate up and Deletes propagate down.

Open our three views and from the Database Selector tool click the DDO tree button Check to be sure that the DataDictionarys are all listed (except for SysFile) and that the main DDO is correct Main DDO of Dept View is Dept Main DDO of Empl View is Empl Main DDO of Dept/Empl is Dept Correct anything that may be incorrect. Compile a view and check that you are able to delete records.

Figure 204

252

Data Access Corporation

Discovering Visual DataFlex

Lesson 7 Lab Constraints

Did You Discover?


1. If you want two views to always display the same records from the database tables, you should?

Data Access Corporation

253

Lesson 7 Lab Connecting Parts

Discovering Visual DataFlex

254

Data Access Corporation

Discovering Visual DataFlex

Lesson 8 Constraints

Lesson 8
Constraints
Constraining the DataDictionarys will limit the displaying of the records to meet the criteria of the constraint.

Topics in this Chapter:


Constraining Records Constrain_File Property OnConstrain Procedure Lab 8 Building Constraints in Selection Lists Building Constraints that Change

Data Access Corporation

255

Lesson 8 Constraints

Discovering Visual DataFlex

Constraining Records
Constraining DataDictionary Objects will filter the records that they display. There are two basic types of Constraints: Constrain_File Property for Relational Constraints OnConstrain Procedure

Constrain_File Property
When is a relational constraint needed? We constrain the view so only related child records of the parent can be seen. This constraint is needed in some views and not desired in others.

256

Data Access Corporation

Discovering Visual DataFlex

Lesson 8 Constraints

Needs a Constraint

In this view, we want the table to fill only with Employees (child records) that are related to the Dept. (parent record).

Figure 205

The Studio will set this constraint for you, based on the Main DataDictionary of the View.

The figure shows how to set & view this constraint in the Studio.

Figure 206

Data Access Corporation

257

Lesson 8 Constraints

Discovering Visual DataFlex

Does Not need a Constraint Here we do not wish to limit the viewing of child records (Empl) to only the children of the found parent record (Dept).

If we did constrain the Employee file, after finding this record all other finds on any employee indexes would only find Tech Employee records.

Figure 207

Notice here there is no constraint.

Figure 208 258 Data Access Corporation

Discovering Visual DataFlex

Lesson 8 Constraints

Constraining is most commonly done on a child file to show only the related records of the parent record currently shown. This type of relational constraint can be accomplished by a property setting or by an OnConstrain procedure.
Object Empl_DD is a Empl_DataDictionary Set Constrain_File to Dept.File_Number // or replacing the above property with the following procedure will do the same thing // // // Procedure OnConstrain Constrain Empl Relates to Dept End_Procedure // Empl_DD

End_Object

Data Access Corporation

259

Lesson 8 Constraints

Discovering Visual DataFlex

OnConstrain Procedure
We can use constraints to restrict the database viewing in many ways. Here we limit the view to only TimeCard records with a date greater than 01/01/2000
Procedure OnConstrain Constrain TimeCard.Date GE 01/01/2000 End_Procedure

Multiple Constrain Commands: Here we limit the view to only TimeCard records with dates greater than 01/01/2000 and Empl_Code that are greater than 250. If possible, the constraint listed first should be the primary segment of an index in order to increase performance. It also should be the most limiting constraint.
Procedure OnConstrain Constrain TimeCard.Date GE 01/01/2000 Constrain TimeCard.Empl_Code GE 250 End_Procedure

Avoid Expressions: The above example can also be written like this, but because of the use of expressions it would not be optimized. For this reason avoid using the AS syntax whenever possible.
Procedure OnConstrain Constrain TimeCard as ((TimeCard.Date >= 01/01/2000) and ; (TimeCard.Date <= 06/30/2000)) End_Procedure

Procedure OnConstrain Constrain Timecard as ((Empl.Dept = TECH) or ; (Empl.Dept = PROD)) End_Procedure

260

Data Access Corporation

Discovering Visual DataFlex

Lesson 8

Steps to Changing Constraints on the Fly! (While the program runs) 1. Create a property. A property will keep its value as long as the object persists. Properties will be covered in detail in a later lesson. 2. Create an interface that will allow the user to alter the value of the property. 3. Send the message Rebuild_Constraints to the DataDictionary every time the value of the property changes.
Property Boolean pbLimitView False ... Procedure OnConstrain If (pbLimitView(Self)) Constrain Customer.State EQ "FL" End_Procedure // An interface (such as a button that would pop up a form) would be needed to // change the value of the property and Rebuild_Constraints would have to be // sent whenever the property was altered. If the DEO was a dbGrid then // Beginning_of_Data may be required.

A field in a System File could also be used, but since this field could change it is not a very good method, unless you have a method of sending Rebuild_Constraints whenever the field is changed.
... Procedure OnConstrain Constrain Customer.State EQ SysFile.Local_State End_Procedure

Data Access Corporation

261

Lesson 8 Lab Constraints

Discovering Visual DataFlex

Lesson 8 Lab
Description: Modifying the Employee Selection List to constrain the viewing of the records to only active employees. Tasks: Constrain the selection list so only active Employees (employees that have their Termination_Date field blank) will be shown. This can be accomplished in the Studio by opening the Empl.SL file and modifying the DDO.

262

Data Access Corporation

Discovering Visual DataFlex

Lesson 8 Lab Constraints

Building Constraints in Selection Lists


Within the Studio
File | Open Component [ Lookups from the comboform [ Employee Lookup [ OK button Add the State & Term_Date fields [ Code Explorer [ Empl_DD Cut & paste code modifications from Code_Mod.txt Save & close this lookup

Add the State and Term_Date fields

Figure 209

File | Open Component [ Views from the comboform [ Employee View [ OK button Compile & Test Enter a Termination Date for an Employee & Save test that it does not show in the Selection List

The selection list will no longer show terminated employees.


//------------------------------------------------------------------// Only show Employees that are not terminated //------------------------------------------------------------------// Add to the Empl_DD in the Employee Lookup Procedure OnConstrain Constrain Empl.Term_Date EQ 0 End_Procedure

Data Access Corporation

263

Lesson 8 Lab Constraints

Discovering Visual DataFlex

Building Constraints that Change


Open the Employee View [ Empl_DD Cut & paste code modifications from Code_Mod.txt Compile & Test Use F7 & F8 keys to view records making sure only employees with the local state appear

Empl DD

Change a State Field to something other than the local state & save You should no longer be able to find the record using the F7&F8 keys

Figure 210

Use Database Explorer to check the Empl.St field to ensure that the constraints are only showing the correct data.
//--------------------------------------------------------------------------------------// Only show Employees that match the default state in the SysFile //------------------------------------------------------------------------------------// Add to the Empl_DD in the Empl_View Procedure OnConstrain Constrain Empl.St EQ SysFile.Local_State End_Procedure

Thus if this application were deployed in Florida, the value of the Local_State field would be FL, however in California it would be CA.

264

Data Access Corporation

Discovering Visual DataFlex

Lesson 8 Lab Constraints

Did You Discover?


1. Open any Lookup List (Selection List - SL file) in an editor. The code begins with CD_Popup_Object. What does the CD stand for? Example Code:
CD_Popup_Object Empl_SL is a dbModalPanel

2. If you look in the properties of the selection list, the Ordering property (which index to use) is set to zero. Why is that?

3. After the constraint in the Employee View is added, can you save an employee that has a termination date greater than zero?

4. How could you make the Selection List use the same DataDictionary constraints as the invoking view? (without copying or moving the OnConstrain code from one to the other)

Data Access Corporation

265

Lesson 8 Lab Constraints

Discovering Visual DataFlex

266

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Lesson 9
All about Messages
Love may make the world go round but it is Messages that make Object Oriented Programs go round. The cascade of messages being sent is what makes everything happen in an OOP program. Developers must be able to understand and send messages in order to make their programs operate.

Topics in this Chapter:


Link Between Messages Triggering Messages Focus Object & Current_Object Sending a Message Access Methods Local Variables Forwarding & Delegating Self Access Method Relaying a Message Neighborhoods Broadcast Command Delegate Send Documentation - Commands Changing Behavior of Messages Augmenting / Canceling /Overriding / Adding Messages Documentation - Procedures Documentation-Class Hierarchy On_Key Commands
Data Access Corporation 267

Properties (creating) Properties (Set Get Commands) Object Properties Itme Properties Procedures Functions Functions as Expressions Categories of Messages Delegation & Container Objects On Procedures (Events) Using OnClick / OnActivate App / OnMaxText Events Creating Buttons Creating Checkboxes & Radios Lab 9 Checking the Servers Properties Highlighting a Grid Row

Lesson 9 All about Message

Discovering Visual DataFlex

The Link Between Messages and Procedures/Functions


Object Oriented programs send messages to accomplish tasks. These messages correspond to procedures or functions with the same name.

OBJECT ORIENTED EXAMPLE: Matching message name and called Sound_Alarm Send Sound_Alarm // Jumps to a procedureProcedure name

Procedure Sound_Alarm Send Bell Send Bell Send Bell End_Procedure

268

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Triggering Messages (Event Driven)


Object oriented programming is ideally suited for supporting Event Driven environments. An event has to occur in order for anything to happen.

Event

Message Sent

triggers other messages

Pressing F2 key

Sends Request_Save message

Procedure Request_Save Which Sends Many other messages

Data Access Corporation

269

Lesson 9 All about Message

Discovering Visual DataFlex

Focus Object & Self


Current Object and Focus Object are often confused, mainly because they are often the same.

Focus Object is the object interacting with the current user.

Self is the object where the processing is taking place at that instant. There is a property Self that returns the Object ID of the current object (a synonym for Self is Current_Object).

If the users cursor were sitting in the Customer_State dbForm, both Current and Focus Objects would be this Customer_State dbForm. If the user presses the Save Key, the Focus Object remains the same and the Current Object changes according to which object is processing the many messages that cascade from the Request_Save message. You can reference Self in order to get the Object_ID of the current object.
Move Self to hoCurrentObj

270

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Sending a Message
Defaulting to the Current_Object Sending the message my_routine without referencing an object will cause the message to be sent to the current object (the object currently in control).
Send My_Routine

Directing a message to a specific object In order to send a message to a specific object, we need the objects ID. Here we wish to send the My_Routine message to the oEmplView object. It will find an object named oEmplView, return the object ID, and then send the My_Routine message to that object ID.
Send My_Routine of oEmplView

You may see old code that uses the syntax Send MessageName to ObjectID instead of Send MessageName of ObjectID. For consistency, the of syntax works better since it is the same for properties and procedures and functions. Set MyProperty of oObjectName to XYZ Send MyMessage of oObjectName Get MyFunction of oObjectName to iVal
Note: Code Editor Hint: After you type Send MessageName of the editor will popup a list of object names of all objects in the current component.

Data Access Corporation

271

Lesson 9 All about Message

Discovering Visual DataFlex

Access Methods
Access methods are used to direct a message to a particular object. Access methods are functions, which return the object ID.

Types of Access Method: Object Referencing Current_Object / Self Access Method Full Access Method

Object Referencing This is the simplest and recommended method. You simply list the object name and it will determine the object ID and send the message to the correct object.
Send Change_Label of oCustomer_Phone

Self or Current_Object Access Method: This is an older method that required you to add the current_object or Self keywords.
Send Change_Label of (oCustomer_Phone(Self)) // Or Send Change_Label of (oCustomer_Phone(current_object))

Full Access Method: This method involves listing the full nesting structure of the objects. Using this method is lengthy and to be avoided if possible.
Send Change_Label of (oCustomer_Phone(oCustomer_View(oClient_Area(oMain(Desktop)))))

This command is read: Send Change_Label to oCustomer_Phone child of oCustomer_View child of oClient_Area child of oMain child of the Desktop

Note: If you are maintaining old code you may run into the Name_Object access method. This is an obsolete command and should not be used.

272

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Forwarding & Delegating (location of methods)


Forward and Delegate are prefixes that can be added to the Send, Get, or Set commands. Simply sending a message will starts with the current object. If we Forward Send the message it will start looking for the message in the parent class. If we Deligate Send the message it will start looking for the message in the parent object.

When a message is sent to an object, it does not stop there if the object does not have a corresponding method (procedure or function). It loops through a three-step cycle trying to find the method. The message cycles through the three steps repeatedly, trying to find a method with the same name as the message being sent. When it finds the method, the method is executed. These three steps are:

1. Look within the current object

2. Forward the message (forward the message up the inheritance path, through classes)

3. Delegate the message (pass the message through to the parent object). Delegation does not happen automatically in other OOP languages. DataFlexs default is to automatically delegate.

The next page will demonstrate what will happen if we send a message that does not exist. We will get an error at the desktop but the next page shows all the steps.

Data Access Corporation

273

Lesson 9 All about Message

Discovering Visual DataFlex


Final Step Runtime Error!

Read from the bottom boxes up.


Use DFAllEnt.pkg Use CUSTOMER.DD DEFERRED_VIEW Activate_Customer FOR ; Object oCustomer_View is a dbView Object oCustomer_DD is a Customer_DataDictionary End_Object // oCustomer_DD

Invalid message MSG_Print_Label Status <<98>> on line #25119 Step D1: Check Current_Object Step D2: Forward dbView Up Class Hierarchy

Step D3: Delegate to Parent Object

Object oCustomer_Number is a dbForm Entry_Item Customer.Number End_Object // oCustomer_Number

Object oCustomer_Name is a dbForm Entry_Item Customer.Name End_Object // oCustomer_Name

Step C1: Check Current_Object Step C2: Forwarding dbTabDialog Up Class Hierarchy

Object oCustomer_TD is a dbTabDialog Object oAddress_TP is a dbTab page

Step C3: Delegate to Parent Object

Step B1: Check Current_Object


Object oCustomer_Address is a dbForm Entry_Item Customer.Address End_Object End_Object // oAddress_TP // oCustomer_Address

Step B2: Forwarding DbTab page Up Class Hierarchy

Step B3: Delegate to Parent Object

Object oComments_TP is a dbTab page Set Label to "Comments" Object oCustomer_Comments is a dbEdit Entry_Item Customer.Comments

Step A1: Check Current Object Step A2: Forwarding dbEdit Up Class Hierarchy

On_Key Key_Alt+Key_P send Print_Label Step A3: Delegate to Parent Object End_Object End_Object End_Object CD_End_Object // oCustomer_Comments // oComments_TP

Pressing Alt-P Sends the Print_Label message

// oCustomer_TD // oCustomer_View

274

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Self Access Method Works by Delegation


In the above example if the oCustomer_Comments object wanted to send a message to the oCustomer_DD DataDictionary this is what would happen.
Send Clear of oCustomer_DD // Object Referencing Access Method

Steps: 1. The oCustomer_DD is first evaluated to find the Object_ID. These are the steps to find the object ID of oCustomer_DD. oCustomer_Comments do you have a child object called oCustomer_DD? No, then forward & delegate oComments_TP, do you have a child object called oCustomer_DD? No, then forward & delegate oCustomer_TD, do you have a child object called oCustomer_DD? No, then forward & delegate oCustomer_View, do you have a child object called oCustomer_DD? Yes, then return the Object ID. This will be something like 97.

2. Send Clear of 97 // (97 = the returned Object ID number)

Optimizing your code: If many messages are to be sent to the same Object it is more efficient to place the object ID into a local variable and send the messages to that variable.
Procedure DoIt Integer hoObjID // Object ID hanble Move oCustomer_DD to hoObjID Send Clear of hoObjID Send Find of hoObjID First_Record End_Procedure

Data Access Corporation

275

Lesson 9 All about Message

Discovering Visual DataFlex

Relaying a Message (Breaking Encapsulation sort of)


As noted above, Self is a recommended access method. It will allow us to send messages to sibling objects, child objects or any object in our delegation path. It however will not allow us to send a message to nested objects of a sibling object or to a grandchild object. This may sound like a bad thing at first, but in reality, it is enforcing encapsulation. That is a good thing! We should not be sending messages to these encapsulated objects (only to sibling objects, our children objects, or objects in our delegation path).

Object oParent Messages should NOT flow directly in these paths Object oChild Object oGrandchild

Object oSibling

276

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

In our example, the grandchild is an edit object displaying a large text field. If the parent object wanted the grandchild to jump to the top of the text field, the Beginning_of_Data message would be sent to the grandchild.

To correctly send a message without breaking encapsulation we relay the message down to the inner object.
Object oParent ... Send Update_Your_Child of oChild ... Object oChild ... Procedure Update_Your_Child Send Beginning_of_Data of oGrandchild End_Procedure Object oGrandchild is an Edit .... (Beginning_of_Data is received and the Cursor is sent to the top of the Data in this object) End_Object End_Object Object oSibling End_Object End_Object

Sending messages will be made easier when we use neighborhoods!

Data Access Corporation

277

Lesson 9 All about Message

Discovering Visual DataFlex

Neighborhoods
As you can see from the above topics sending a message can sometimes become difficult. Neighborhoods are used in a limited (almost exclusively by visual objects) but very useful way. Their main purpose is to hide visual containers. This will make sending messages MUCH easier. Neighborhoods will find the objects that you previously could not find by flatting out the visual container objects.

Everything we have covered so far in this lesson still applies. The only difference is the FIRST neighborhood found if it were a public neighborhood, it would check its list of neighborhood objects.

Each object has a peNeighborhood property that is set to one of three settings. This property is available through the Studios Object Properties dialog. nhPublic: This will flag the object (views, tab-views, modal dialogs) as a public neighborhood, and will maintain a list of neighborhood objects. nhPrivate: This will flag the object (controls, arrays, reports, etc.) as a private neighborhood and will not maintain a neighborhood list. This is the default for most objects and is the standard black box theory of OOP. This theory states that objects are encapsulated by their parents black box (will not be accessible to outer objects). Private neighborhood objects will register themselves in their parents neighborhood but will STOP their child objects from registering themselves in a neighborhood (which will make the children hidden). nhNo: This setting is used for visual containers. They will register themselves in their parents neighborhood and allow their child objects to also register themselves in the neighborhood.

278

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

How objects become part of a neighborhood list: When child objects are created, they will find the first parent object that is a neighborhood (public or private, but only the first neighborhood). If it is a public neighborhood, it will register itSelf in the neighborhood list.

Note: Neighborhoods do not support duplicate object names (only one duplicate name will appear in the neighborhood list).

Public Neighborhood Object oView is a dbView Object oContainer1 is a dbContainer Neighborhood set to nhNo Object oForm1 is a dbForm Member List: oContainer1 oForm1 oContainer2

Object oContainer2 is a dbContainer Object oArray Object oForm2

Neighborhood set to nhPrivate Notice its children are not listed in the public neighborhood

Data Access Corporation

279

Lesson 9 All about Message

Discovering Visual DataFlex

Broadcast Command
The broadcast command allows you to quickly send messages to a group of nested objects.
Broadcast Send Do_It //Will send the message to all immediate child objects. Broadcast turns the normal delegation off. Broadcast Recursive Send Do_It //Will send a message to all descendents of an object. //The message will be sent to a child, then to all of that child's children before proceeding to the next child Broadcast Recursive Send Do_It of Desktop //Will send the message to all objects in the program. Broadcast Recursive_Up Send Do_It //Will send the message to the most inner child object then upward to itSelf (excluding itSelf). //This mode is well suited for deactivating child objects or left-right tree navigation, where every //node on the tree is an object. Broadcast No_Stop Get IsSomeoneCelebrating to iAnswer //The No_Stop option allows a Broadcast Get command to continue broadcasting even after an object //returns a non-zero value for a Get message. When the broadcast finishes, the return value will be that of //the last object to process the message. Normally used when you know several child objects do have a //common method which you want to execute but when youre not interested in the return value.

A The command Broadcast Recursive Send Do_it sent from object A would be sent to all objects. Sent from Y would only be sent to object Z. B C D E F

Y Z

280

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Delegate Send
Delegate Send is used to send the message directly to the parent object. Using it will optimize performance and will make your intentions clear.

// Both lines accomplish the same thing: Send DoIt of MyParent Delegate Send DoIt // here the Parent ID is evaluated // here the message is directly sent to the parent

Data Access Corporation

281

Lesson 9 All about Message

Discovering Visual DataFlex

Using Online Documentation Commands


This is a good time to look at the On-Line Help files. Currently there are two versions of the online help files as we update the old Windows help files to the new HTML Help files. You can access the help directly from Start | Programs | Visual DataFlex 9.1 | Visual DataFlex Help.

[ Start [ Programs [ Visual DataFlex 9.1 [ Visual DataFlex Help [ Index Tab type bro [ Display Button Read the help for the two broadcast pages Look up the Delegate command

Figure 211

You can also double click on the Broadcast Command instead of the Display button.

282

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Changing Behavior of Existing Messages


The topics below are methods for creating or changing procedures. Normally these procedures should be created in the object that you wish to affect.

Augmenting a Message Augmenting adds additional functionality to the normal operation of a pre-existing procedure. Forward Sending the message accomplishes this. Augment whenever you wish the normal procedure behavior, but need something extra to happen.

Augmenting a Procedure:
Procedure Request_Save Forward Send Request_Save Send Bell End_Procedure // do normal save behavior // then ring computer bell

If you Send instead of Forward Send the message you will get a recursive or Stack fault error.

Augmenting a Function:
Function Validate_Save Returns Integer Integer iRetVal If (Invt.Qty < 0) Begin Error DFErr_Operator "Insufficient Inventory on hand" // error message will occur after the unlock Function_Return 1 End Forward Get Validate_Save to iRetVal Function_Return iRetVal End_Function

Data Access Corporation

283

Lesson 9 All about Message

Discovering Visual DataFlex

Canceling a Message Canceling is done to stop an object from performing a procedure. Since your procedure is found before the predefined procedure (in the class or within a parent object), it will look no further and never find the other procedure.
Procedure Request_Clear End_Procedure

Overriding a Message Overriding a procedure is changing the normal behavior We do not forward send the original message so the normal behavior is not done. We position the procedure so it is found before the pre-existing procedure is found (normally in the current object).
Procedure Request_Delete Send Bell Send Info_Box NO DELETIONS ALLOWED! End_Procedure

Adding (creating) a Message The above methods alter pre-existing procedures. Adding a message is creating a completely new procedure. Notice when we create a new procedure we also must create a way of triggering the message. In this case, we use the On_Key command.
.... On_Key Key_Alt+Key_C Send Check_Range .... Procedure Check_Range Date dStart dEnd Get Value of oStart_Date to dStart Get Value of oEnd_Date to dEnd If (dStart > dEnd) Error DFErr_Operator The ending date must be greater than the starting date End_Procedure

284

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Using Online Documentation Procedures


Looking up Predefined Procedures: Notice that the Request_Save procedure is defined in many classes. Polymorphism refers to defining a procedure in multiple places. Via forwarding and delegation (as we learned earlier) the runtime will execute the first one that it finds.

Within the on-line WinHelp:


[ Start | Programs | Visual DataFlex 9.1 | Visual DataFlex Help [ Index Tab type request_s Notice all the defining classes for this message!

Figure 212

Scroll to the dbGrid Class [ Display Button

Remember if the message is not found in the current object it will forward up the class hierarchy path. In this case, it should find it in one of these defining classes.

Data Access Corporation

285

Lesson 9 All about Message

Discovering Visual DataFlex

Using Online Documentation Class Hierarchy


Question: If we had an object built from the dbSpinForm class, which defining class would resolve the Request_Save message?

Within the online help:


[ Contents Tab [ Class Reference [ dbSpinForm

Figure 213

Notice the dbSpinForm is a subclass of the dbForm class. The dbForm is a defining class for the Request_Save message. When the message is forwarded up the class hierarchy path, it will find the Request_Save message in the dbForm class.

286

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Local Variables
Local variables are declared in procedures or functions and only exist within the procedure or function. Variables declared outside procedures or functions are global variables.

Local Variables: Used only in Procedures or Functions Most common types are: String; Number; Date; Integer, or Real. Others are: Boolean, Time, TimeSpan, DateTime, Handle, plus advanced data types. Are Dynamic: They will grow as needed no length is indicated. Destroyed & memory released when the Procedure/Function is terminated Since they are destroyed their names can be duplicated in other procedures or functions

Note: In prior versions, local variables were always preceded with the word Local. This is no longer needed or suggested.

Note: Try never to use Global variables! They consume memory, cause undesired dependencies, and cause naming conflicts, since Global variable names cannot be used as a Local variable name!

Data Access Corporation

287

Lesson 9 All about Message

Discovering Visual DataFlex

On_Key Commands
These are used to send a message from a key combination or from one of the predefined accelerator key functions. Adding an accelerator key can act as a shortcut to options from the menu bar or button.

On_Key key_name send message {of object} {private} Stops child objects from inheriting Name of the Message

Accelerator key function name or a physical key combination Accelerator Key Functions: (cannot change the hot key associated with them)
On_Key KCancel Send Exit_Application On_Key KUpArrow Send Previous

Physical Keys: (three Prefixes Key_Alt+ Key_Ctrl+ Key_Shift+)


On_Key Key_Ctrl+Key_P Send Print_it On_Key Key_Alt+Key_Z Send Update_Records Private

Note: Child objects will inherit accelerator keys (just like messages) through normal delegation unless the Private option is used.

288

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Properties (creating)
Syntax
Property type property_name initial_value

Often we need to store a value from one object and have access to the value from another object. Procedural programmers have a tendency to want to create a global variable but creating a new property is the correct way to code this. The solution is to: 1. Create a property in an outer parent object 2. Use the Set command to store the data 3. Use the Get command to retrieve the stored data Sample of creating a property:
Object oMy_View is a dbView Property integer piClick_Counter 0 // new property created and available to all objects in the dbView Object oMy_Button is a Button Procedure OnClick Integer iClicks Get piClick_Counter to iClicks Increment iClicks Set piClick_Counter to iClicks Set Label to iClicks End_Procedure End_Object // oMy_Button End_Object // oMy_View // Set the property value // Get the current property value

Note: Instead of procedures or functions that pass many arguments it may be better to create a new class that has new properties. With the Set and Get commands, these properties can be easily stored and altered, eliminating the need of argument passing.

Data Access Corporation

289

Lesson 9 All about Message

Discovering Visual DataFlex

Properties (Set & Get Commands)


Properties are attributes of an Object or Item that can be set or retrieved. You can think of a property as a variable that contains a value of an object or item.
// Set the property with the Set command Set Application_Name to Ledger // Retrieve the property with the Get command Get Application_Name to app_name

The Studio sets properties for you such as Location, and Application_Name.

Object Properties These are properties at the object level. Syntax:


Set property_name {of object} to value {value 2 ...} Get property_name {of object} to return_value

If we leave off the {of object }, it will default to the current object.

Get Border_Style to iVal Set Label to sLabel

// gets the objects Border_Style property // sets the objects Label

290

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Item Properties These are properties at the item level. Items are zero-based, so the second item is referenced as item 1. Syntax:
Set property_name {of object} {item_number} to value {value 2 ...} Get property_name {of object} {item_number} to return_value

Object DtlGrid is a dbGrid Set location to 5 10 Begin_Row Entry_Item Invt.Item_id Entry_Item Invt.Description Entry_Item Invt.Unit_price Entry_Item Orderdtl.Price Entry_Item Orderdtl.Qty_ordered Entry_Item Orderdtl.Extended_price End_Row Set Form_Width item 0 to 55 // this column will be shadowed

The word item is no longer required and can be left off on all these command lines.

Set Header_Label item 0 to "Item Id" Set Form_Width item 1 to 116

Set Header_Label item 1 to "Description" Set Form_Width item 2 to 55

Set Header_Label item 2 to "Unit Price" Set Form_Width Set Column_Shadow_State item 2 to true End_Object item 3 to 43

Set Header_Label item 3 to "Price"

Data Access Corporation

291

Lesson 9 All about Message

Discovering Visual DataFlex

Procedures
Procedures and Functions are very similar. The main difference is that a Function will always return a value. A procedure can return a value but this is reserved for legacy procedures. Newly created procedures should not return values.

Syntax:
Procedure procedure_name {type1 arg1 ... ... typeN argN} variable_type name ... {forward send procedure_name arg1 ... argN} // statements to perform when this procedure is executed End_Procedure

Send procedure_name {of object_name } arg1 ... argN to value //

Note: There is also a procedure {set} option, which is an advanced concept. A full example of this can be found in Appendix B.

Example: When the message Authorize is sent it also passes a string argument. This argument is placed into a local variable called sUser_Rights.
Object oMyOKButton is a Button Procedure OnClick Send Authorize SUPERVISOR End_Procedure End_Object Procedure Authorize String sUser_Rights If (sUser_Rights = "SUPERVISOR") Send Activate of oMain_View End_Procedure ...

292

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Functions
Functions always return a value. Therefore, instead of using the Send command we use the Get command. This is similar to retrieving the setting of a property. Syntax:
Function function_name {type1 arg1 ... ... typeN argN} returns return_type variable_type name ... {forward get function_name arg1 ... argN to value} : // statements to perform when this function is called Function_Return value End_Function

Get function_name {of object_name } arg1 ... argN to value // functions can also be written as an expression Move (function_name (Self, arg1)) to value

Sample:
Function Wage_Increase Number nWage Returns Number Number nAfter_Raise Calc ( nWage * 1.10 ) to nAfter_Raise Function_Return nAfter_Raise End_Function

Here we pass the value of Empl.Wage to the local variable called nWage. The function returns the value nAfter_Raise into the variable nWage_Incr.

... Get Wage_Increase Empl.Wage to nWage_Incr ...

Note: (prior DataFlex Users) Many of your Macro commands can be easily converted into Functions. In fact, many DataFlex commands have been replaced with functions, e.g., Append and Length.

Data Access Corporation

293

Lesson 9 All about Message

Discovering Visual DataFlex

Functions as Expressions
A Function can be used as an expression, while procedures cannot. This example uses an expression for an Entry_Item. (the database in this example is not the one in our labs)
Object oCustomer_Grid is a dbGrid //AB-StoreTopStart Function DaysSinceOrder Returns Integer DateTime dHireDate dToday TimeSpan tsDiff Integer iDays Move Customer.Last_Order_Date to dHireDate Move (CurrentDateTime ()) To dToday Move (dToday - dHireDate) To tsDiff Move (SpanTotalDays (tsDiff)) To iDays Function_Return iDays End_Function // DaysSinceOrder //AB-StoreTopEnd Set Main_File to Customer.File_Number Set Size to 105 239 Set Location to 12 24 Set Wrap_State to TRUE Begin_Row Entry_Item Customer.Last_Order_number Entry_Item Customer.Last_Order_date Entry_Item (CurrentDateTime()) Entry_Item (DaysSinceOrder (Self)) End_Row

The Self keyword is left off on Global Functions The Self keyword on other functions is used as the location. Only use the Self keyword as a parameter on Global functions.

If the function has arguments, they are passed just before the closing parentheses. Here Empl.wage is passed as an argument. Ex: Move (Wage_Increase(Self, Empl.wage)) to nWage_Incr

294

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Categories of Messages
Properties, procedures, and functions fall under three categories.

Public messages are the most commonly used messages and are intended to be sent or altered in typical programs.

Protected messages are available for special uses, but not likely to be sent or altered in typical programs.

Private messages are used by the class internally to accomplish a goal. They should not be sent or intercepted! Private messages could be removed when a class is modified.

Data Access Corporation

295

Lesson 9 All about Message

Discovering Visual DataFlex

Delegation & the Importance of Container Objects


The augmenting of common messages such as the Request_XX messages (Request_Save; Request_Delete, etc.) would be difficult if we had to augment them in all objects for all fields in an Empl View. Therefore, these common Request_XX messages can be augmented in the parent object for the child objects to use.

The example on the next page will show how the Parent Server is used if the nested objects do not explicitly set the server.

Figure 214

296

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Visual DataFlex Code: Here the container is setting the server. The nested objects will use the same server, since they are not setting the server for themselves.
Object oContainer1 is a dbContainer Set Server to oCustomer_DD

Object oID_Form is a dbForm Entry_Item to Customer.ID End_Object // oID_Form Object oName_Form is a dbForm Entry_Item to Customer.Name End_Object // oName_Form Object oPhone_Form is a dbForm Entry_Item to Customer.Phone End_Object // oPhone_Form Procedure Request_Delete Forward Send Request_Delete Send Bell End_Procedure End_Object // oContainer1

We would not wish to repeat the Request_Delete message for all three dbForms. Therefore, we send the Attach_Server in the container (not in the dbForms) and request_xx messages sent by child objects are delegated to the parent container/object with the Attach_Server set.

Data Access Corporation

297

Lesson 9 All about Message

Discovering Visual DataFlex

On Procedures (Events)
Programmers often desire to add functionality to certain events. ON procedures are triggered (sent) during certain events and allow the programmer easy access to add additional functionality at the time these events occur. All Visual DataFlex event names begin with the On prefix (some older ones are missing the On prefix). It would be beneficial to look in the online help files and see what is available. Do not try to learn all the On procedures. Simply browse the list to see what is available. Some events may behave differently depending on the Defining Class.

Within online Help [ Index tab Type OnAct R this will bring you to the first On-event procedure. Browse the list to see what is available

Figure 215

298

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Using OnClick Event Add this procedure inside a button to exit the application.
Object oExit_Button is a Button : Procedure OnClick Send Close_Panel End_Procedure End_Object

Using OnActivateApp Event This procedure is added to the Views main Panel object. The event will fire when the application is first activated and every time you switch to the application. This example will play a wave file upon activating our application.
Use Wave : Object oMain is a Panel Set Label To "New Program1" //AB-StoreStart Procedure OnActivateApp Playwave "c:\windows\msremind.wav" SND_ASYNC End_Procedure //AB-StoreEnd

Using OnMaxText Event Add this procedure to an Edit Object to notify that the size limit has been reached.
Object oComments is an Edit : Procedure OnMaxText Send Bell End_Procedure End_Object

Data Access Corporation

299

Lesson 9 All about Message

Discovering Visual DataFlex

Creating Buttons
Buttons are another method of triggering a message. Through the OnClick event it gives the user visual clues to available options.

Object oMy_Button is a Button Set Label to Cancel Set Size to 14 50 Set location to 115 36 Procedure OnClick Send Request_Cancel End_Procedure End_Object

300

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 All about Messages

Creating Checkboxes & Radios


Checkbox and Radio Classes are selection devices. Used as a group, Checkboxes can be used for multi-selection and Radios for single selection. The Notify_Select_State procedure is called whenever there is a change to them. Example of a Radio group:
Object oRadioGroup1 is a RadioGroup Set Label to "Output Report:" Set Size to 39 56 Set Location to 3 7 Set Current_Radio to 0 Object oRadio1 is a Radio Set Label to "Screen" Set Size to 10 39 Set Location to 11 5 End_Object // oRadio1

Object oRadio2 is a Radio Set Label to "Printer" Set Size to 10 37 Set Location to 24 5 End_Object // oRadio2

Procedure Notify_Select_State Integer iToItem integer iFromItem Forward Send Notify_Select_State iToItem iFromItem If (iToItem = 0) Set Output_Device_Mode to Print_To_Window Else Set Output_Device_mode to Print_To_Printer End_Procedure End_Object // oRadioGroup1

Data Access Corporation

301

Lesson 9 All about Message

Discovering Visual DataFlex

Example of a single Checkbox that toggles the state of a form:


Object oFileName_Form is a Form Set Location to 25 65 Set Size to 13 100 Set Label to File name: End_Object //oFileName Object oCheck is a CheckBox Set Location to 40 5 Set Label Print to File Set Checked_State to true // Shadow file name form if print to file is false Procedure OnChange Integer iState Get Checked_State to iState Set Enabled_State of oFileName_Form to iState End_Procedure End_Object // oCheck

302

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Lesson 9 Lab
Description A new view will be created to log employees in, generating a timecard record. We will also be creating a Property called psInOut that will be used to set the label of four objects. Tasks The TimeCard Log-In view will contain a number of manual code additions. We will use this same view again as the Log-Out view in another lesson. This is why we will make many of the labels within the view dynamic. We will do this by creating a property called In_Out. Then procedure Activating will correctly set the label property from the In_Out property. By using this property to dynamically set these labels, we will later be able to use this same code for the logging out of employees. By simply setting the property to Out all the labels will also change. Creating new TC_In View:
[ New View button From the Database Selector tool, select the DDO tree button Check to be sure that the DataDictionarys are all listed and that the main DDO is correctly set to TimeCard_DD

Figure 216

Data Access Corporation

303

Lesson 9 Lab All about Message

Discovering Visual DataFlex

Objects to Build dbView Textbox

File.Field to Display

Object name oTC_In

Label Logging Employees Employees listed in the grid are logged

dbGrid Empl.Code oEmpl_Grid Grid Options: Empl.Last_Name Main File=Empl Empl.First_Name Index =#2 dbGroup Process Button Log dbForm * Empl.First_Name First Name: TextBox At dbForm * TimeCard.Hours Hours: dbForm * TimeCard.Minutes Minutes: dbForm * TimeCard.Reason_Code Reason Code: dbEdit TimeCard.Memo Memo: * Set Label_Column_offset to 0 and Label_Justification to JMode_Top

The table on this page lists the fields and other items to modify. Use the Database Selector and the Controls Palette tools to make all the objects. Use the Object Properties dialog to name the objects and set their labels (some labels are set to jMode_Top & 0 offset). Use the Object-Order Definition Tool to correct navigation

Figure 217 304 Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Checking the Servers:


Select the Process object (dbGroup) From the Object Properties dialog, select the Database Tab Check that the indirect server is correctly set to TimeCard -- if not then in the Database Selector (DDO button) check that the main DDO is set to Time_Card

Figure 218

[ on the Grid [ Grid options Verify all options

Figure 219 Data Access Corporation 305

Lesson 9 Lab All about Message

Discovering Visual DataFlex

It is important that the view is correct up to this point before adding manual code.
Classroom Environments: Verify your classmates work and have them verify yours. Make sure that all objects are created and are the correct type Self Study: Verify your work with the chart and screen shot (on the prior pages) Dont forget to save the view as TC_In

306

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Properties (the global variables)


Here the psInOut property is created. TC_In
Open the Code Editor & the Code_Mod.txt file Add the manual code from the Code_Mod.TXT file to the TOP of the TC_In object

Code added to the oTC_In object

Here we retrieve the value of the InOut property to use in our labels Green Line
Figure 220

Warning: Add code above the green line.


//---------------------------------------------------------// Add to oTC_In object // The property psInOut must be created before it is used by // the other objects. Therefore, this code has to be place // before the other objects reference the psInOut property // TC_In view set to "IN" TC_Out view set to "OUT" //---------------------------------------------------------Property String psInOut "IN" //---------------------------------------------------------// Dynamically set the Label from the psInOut property //----------------------------------------------------------

Data Access Corporation

307

Lesson 9 Lab All about Message


Procedure Activating String sIO Forward Send Activating Get psInOut to sIO Set Label to ("Logging Employees" * sIO * ":") // "*" will trim & add a space between the strings End_Procedure //---------------------------------------------------------// Updates the Grid whenever the view takes the focus //---------------------------------------------------------Procedure Activate Integer iRetVal Forward Send Activate iRetVal Send Beginning_of_Data of oEmpl_Grid End_Procedure

Discovering Visual DataFlex

308

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Empl_DD:
Add the manual code from the Code_Mod.TXT file to the Empl_DD object

Figure 221
//---------------------------------------------------------// Add to the Empl_DD in the TC_In view // Only display In or Out Employees depending on first // character of the psInOut property //---------------------------------------------------------Procedure OnConstrain String sVal Get psInOut to sVal Move (Uppercase(sVal)) to sVal Move (Left(sVal,1)) to sVal Constrain Empl.logged NE sVal End_Procedure

Data Access Corporation

309

Lesson 9 Lab All about Message

Discovering Visual DataFlex

TimeCard_DD:
Add the manual code from the Code_Mod.TXT file to the TimeCard_DD object

Figure 222

//---------------------------------------------------------// Add to the Timecard_DD in the TC_In view // Remember the DD also has a procedure Creating that moves // the TimeCard.In_or_Out to the Empl.Logged field. This is // one of the times that it is very important that we do not // Forward Send first. //---------------------------------------------------------Procedure Creating // Since the TimeCard.In_or_Out is only one character long // the psInOut property value will be truncated Move (Uppercase(psInOut(Self))) to TimeCard.In_or_Out Forward Send Creating End_Procedure

Return to Figure 195 to review this procedure.

310

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Textbox Object:
Add the manual code from the Code_Mod.TXT file to the oTextbox1 object

Figure 223

//---------------------------------------------------------// Add to the oTextBox1 in the TC_In view // Dynamically set the Label property (opposite to the // value of the psInOut property //---------------------------------------------------------Procedure Activating String sIO Forward Send Activating Get psInOut to sIO Move (uppercase(sIO)) to sIO If (sIO = "IN") move "Out" to sIO // this will toggle the status from In to Out Else move "In" to sIO // this will toggle the status from Out to In Set Label to ("The Following Employees are logged" * sIO * ":") End_Procedure

Data Access Corporation

311

Lesson 9 Lab All about Message

Discovering Visual DataFlex

Empl_Grid Object:
Add the manual code from the Code_Mod.TXT file to the appropriate object

Figure 224

//---------------------------------------------------------// Add to the oEmpl_Grid // Do not allow any changes in the grid //---------------------------------------------------------Set Allow_Bottom_Add_State to False Function Row_Save Returns integer Error DFErr_Operator "No Saves allowed to this grid!" Send Refresh Mode_Find_or_Clear_Set Function_Return 1 End_Function Procedure Request_Delete Error DFErr_Operator "No Deletes allowed to this grid!" End_Procedure

312

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Process Object:
Add the manual code from the Code_Mod.TXT file to the dbGroup appropriate object

Figure 225

//---------------------------------------------------------// Add to oDbGroup1 in the TC_In view // Dynamically set the Label from the psInOut property //---------------------------------------------------------Procedure Activating String sIO Forward Send Activating Get psInOut to sIO Set Label to ("Process" * sIO * ":") End_Procedure

Data Access Corporation

313

Lesson 9 Lab All about Message

Discovering Visual DataFlex

Button Object:
Add the manual code from the Code_Mod.TXT file to the Button object Paste over the existing OnClick procedure

Figure 226
//---------------------------------------------------------// Add to oButton1 // Dynamically set the Label from the psInOut property //---------------------------------------------------------Procedure Activating String sIO Forward Send Activating Get psInOut to sIO Set Label to ("Log" * sIO * ":") End_Procedure //---------------------------------------------------------// Process the selected employee saving & refreshing list //---------------------------------------------------------Procedure OnClick Delegate Send Request_Save // delegate will start the message in the parent object Send Beginning_of_Data of oEmpl_Grid // move to top of grid & remove logged employee from list End_Procedure

314

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

Highlighting a Grid Row


We will change the color of the entire row in the grid to make it clear which employee is being logged in.

] Grid object [ Properties

] CurrentCellColor [ Standard Color [ clGreen ] CurrentRowColor [ Standard Color [ clLime

Figure 227

Data Access Corporation

315

Lesson 9 Lab All about Message

Discovering Visual DataFlex

You should have already saved this view but to change the description or defer the object you can call up the component property dialog.
Component | Properties Verify the data in the dialog [ OK

Figure 228

316

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

[ Test compile and run component in the debugger button Check that: It compiles without errors 4 labels displayed correctly Grid has row highlighted Lower name object matches grid Grid disallows saves & deletes

Warning:
The view is not complete yet, so do not add any records!

Figure 229

Exit back to the Studio

Note: (everyone) To fully understand code requires time to study it. As time permits, follow through the manual code segments at your own pace.

Data Access Corporation

317

Lesson 9 Lab All about Message

Discovering Visual DataFlex

Did You Discover?


1. Do properties forward and delegate like procedures and functions?

2. If you cancel the Request_Clear procedure in a container object that contains many dbForm objects will it affect the Request_Save?

3. What would happened if Forward Send Creating was listed before the Move command in TimeCard DD objects Creating procedure we just added in the lab? Here is the code:
Procedure Creating // Since the TimeCard.In_or_Out is only one character long // the psInOut property value will be truncated Move (Uppercase(psInOut(Self))) to TimeCard.In_or_Out Forward send Creating End_Procedure

4. Look in the help to find the names of the other Accelerator-Keys.

318

Data Access Corporation

Discovering Visual DataFlex

Lesson 9 Lab All about Message

5. Name as many ways as you can to make a procedure execute.

6. Create a new view with a grid displaying the Empl.Code; Empl.Last_Name and Empl.Term_Date fields. Use the RadioGroup Class to set up a dynamic constraint to show: All Employees Terminated Employees Active Employees

Data Access Corporation

319

Lesson 9 Lab All about Message

Discovering Visual DataFlex

320

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Items & Predefined Classes

Lesson 10
Items & Predefined Classes
This lesson covers topics such as images and special On events that trigger messages to be sent whenever these events occur.

Topics in this Chapter:


Items - Zero-Based Referencing Items Outside the Current Object Grid - Column Properties Lab 10 Creating Timers

Data Access Corporation

321

Lesson 10 Items & Predefined Classes

Discovering Visual DataFlex

Items - Zero-Based
Most Windows classes only have one item so the item will default to item 0. For Example, in the case of a dbEdit class, you may have a need to reference each item (line) separately. Items are zero based, meaning that the first item is item 0. The property current_item is the item that the user is currently interacting with.

Object Copyright is an Edit Set Size to 100 200 Set Location to 10 10 Procedure Activating Forward Send Activating

The word item can be left off

Set Read_Only_State to True //This will stop the user from making changes to the text

Set Value 0 to "Copyright 2004 Data Access Corporation" Set Value 1 to " Set Value 2 to " Set Value 3 to " End_Procedure End_Object Data Access Corporation" 14000 S.W. 119 Avenue" Miami, Florida 33186"

Other multi-item classes are grid, list, edit, menu, dbList, dbGrid, array, and set.

322

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Items & Predefined Classes

Referencing Items Outside the Current Object


Both item reference and current object can be left blank and it will default to the current item and current object. There are times in which we must reference an item outside the current object.
Object oCopyright_Object is an Edit Set size to 100 200 Set location to 10 10 Set Read_Only_State to True //This will stop the user from making changes to the text Procedure Activating Forward Send Activating Set Value 0 to "Copyright 2004 Data Access Worldwide" Set Value 1 to " Set Value 2 to " Set Value 3 to " End_Procedure End_Object Data Access Worldwide" 14000 S.W. 119 Avenue" Miami, Florida 33186"

Object oPhone is a dbForm

These are item references or in the case of an Edit object, the line number

On_Key Key_Alt+Key_U Send Add_Phone Procedure Add_Phone String sCurrentVal Integer iLineCount Get Value to sCurrentVal //move the value from this dbForm into sCurrentVal variable Get LineCount of oCopyright_Object to iLineCount // find the max line count of the edit object Set Value of oCopyright_Object iLineCount to sCurrentVal End_Procedure End_Object

Data Access Corporation

323

Lesson 10 Items & Predefined Classes

Discovering Visual DataFlex

Grid - Column Properties


Check the on-line help to see the many column properties available. Column properties, like item properties, are also zero-based. Example:
// Shadowing a column affects both its appearance and its functionality. A shadowed column will be // displayed in the shadowed color (defined by the desktop or its palette). If a user places the selection // cursor on a shadowed column, the column will not respond to the Enter key or any mouse action. Set Column_Shadow_State 4 to True // this will shadow the 5th column

// Adding parentheses around it can also return a property value If (Column_Shadow_State(Self,4)) send Extra_Processing

Column properties may be set dynamically, although such usage would be unusual. If the property is changed when the object is active, you will not see a change in the objects appearance until you redisplay the object. The following sample would toggle a columns checkbox state and update the dbGrid as required.

Procedure Toggle_CheckBox Boolean bState Get Column_Checkbox_State 4 to bState Set Column_Checkbox_State 4 to (not(bState)) // If the object is active, we must redisplay it to see changes If (Active_State(Self)) Send Display End_Procedure

Note: Column_xxx states must be set after the Entry_Items, in order for it to take effect. (e.g. in the bottom code section below the comment line in the editor).

324

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Lab Items & Predefined Classes

Lesson 10 Lab
Description: Practice using the dfTimer class, by adding all the parts to make this timer a functional part of our view. This lesson also duplicates the view and shows how to register an external component so the Studio will recognize it. It then adds the new views to the overall application. Tasks:

Creating Timers
(This is an outline; the detail instructions will follow) Add a timer event that will default the time into the TimeCard record. We use the Field_Default_Value so we do not trigger the Data Loss message when we close the view.

We will be using the dfTimer class from the Studios Controls Palette Tool (NonVisible tab page).

The properties of the dfTimer object will set the frequency that the timer will fire and list which object should be sent what message.

The Timecard DataDictionary Object will contain the Update_Time message that will default the current time into the TimeCard record.

The Log In/Out button will send the Request_Save message. It will also send Beginning_of_Data so the selected record in the grid will be removed and our cursor will be returned to the top of the list.

Data Access Corporation

325

Lesson 10 Lab Items & Predefined Classes

Discovering Visual DataFlex

Timer object Within the TC_In view:


Tools | Controls Palette [ Non-Visible tab page ; dfTimer to the top corner In the Object Properties Set: Time_out to 400 Timer_Message to msg_Update_Time Timer_Object to TimeCard_DD

Figure 230

326

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Lab Items & Predefined Classes

[ TimeCard_DD Add the new code segment below the code already there.

Figure 231

//---------------------------------------------------------// Add to the TimeCard_DD object // This procedure triggers the timer. // It sets the date & time values in the TimeCard record. //---------------------------------------------------------Procedure Update_Time Integer iHr iMin Date dToday SysDate4 dToday iHr iMin Set Field_Default_Value Field TimeCard.Date to dToday Set Field_Default_Value Field TimeCard.Hours to iHr Set Field_Default_Value Field TimeCard.Minutes to iMin End_Procedure

Data Access Corporation

327

Lesson 10 Lab Items & Predefined Classes

Discovering Visual DataFlex

[ Test compile and run component in the debugger button Check that the timer is updating time Log someone in: Select a Reason code from the comboform and then press the Log In Button Were they removed from the list? Exit back to the Studio

Figure 232

Warning! The Reason code is a Validated field. An error will be generated if you leave it blank!

We will need two views one for processing the employees in and one to process them out. Therefore, we will save this view under two names.
File | Save As Enter the data as shown [ Save Button Close this view and

Figure 233

File | Open | View | Time Card Out View

328

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Lab Items & Predefined Classes

Data Access Corporation

329

Lesson 10 Lab Items & Predefined Classes

Discovering Visual DataFlex

The closing and reopening of the views will refresh the code explorer.

The psInOut property that we created affects the labels and the constraining of the view. Therefore, the only change that we will have to make to our new view is changing its default property value from In to Out. Default setting Within TC_Out view:
[ oTC_Out Change the default property setting from IN to OUT Compile the View and make sure the In & Out labels are correct

Figure 234

Warning! You might have to close the component view and reopen the view in order for the tree view to show the object name change from oTC_In to oTC_Out.

330

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Lab Items & Predefined Classes

Add the new views to the application.

If the application is closed, open it


[ Add a Component button [ Views [ TC_In ] TC_Out [ Add button [ Close button [ Compile and debug-run program Button Test that the new views operate correctly

Figure 235

Data Access Corporation

331

Lesson 10 Lab Items & Predefined Classes

Discovering Visual DataFlex

Did You Discover?


1. The lesson mentioned dbEdit as a multi-item class. Name other classes that are multi-item.

2. What information can you get by clicking on "Help/About..." of a running VDF application?

Note: (everyone) To fully understand the manual code requires time to just study it. If time permits, follow through the manual code segments at your own pace.

332

Data Access Corporation

Discovering Visual DataFlex

Lesson 10 Lab Items & Predefined Classes

Data Access Corporation

333

Discovering Visual DataFlex

Lesson 11 Troubleshooting

Lesson 11
Troubleshooting
This lesson covers Troubleshooting techniques.

Topics in this Chapter:


Studio Databases Troubleshooting Hints Compile Each View Separately Check File Relationships Check for Unique Index on the Parent Related Field. Rebuild the DDO tree within the View Checking the Data Debug Compiler Errors & Use a .PRN file Create a Small Test Program Use the Debugger Lab 11 Debugger Breakpoints Debugger Watches

Data Access Corporation

335

Lesson 11 Troubleshooting

Discovering Visual DataFlex

Studio Databases
The Studio uses two databases, ddData and abData files. The Studios Workspace pulldown menu has the Maintain and Reindex options. These options allow you to update or reindex the databases. ddData file contains a record for each DataDictionary created. abData contains a record for all the subcomponents of the Studio. Knowing about these files and how to reindex them can sometimes solve your problems.

Workspace | Reindex Studio databases (it will quickly reindex the files) Workspace | Maintain Studio databases

Figure 236

Press F7 & F8 to view the records Close the dialog

Figure 237 336 Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

Troubleshooting Hints
Here is a list of troubleshooting hints that solve many program problems.

1. Compiling each View separately 2. Checking File Relationships Matching length/type of related fields Matching DataDictionary Required Parent/Child structure

3. Checking for unique index on the parent related field: 4. Rebuilding the DDO Tree within the View 5. Checking the Data 6. Debugging Compiling Errors & using a .PRN file 7. Creating a Small Test Program 8. Debugging Runtime errors

Data Access Corporation

337

Lesson 11 Troubleshooting

Discovering Visual DataFlex

1. Compile Each View Separately Each view should be tested and compiled separately before it is added to the complete program. The ability to conduct stand-alone tests is one of the benefits of OOP. This will make tracking down problems less painful and time consuming. If multiple views are not compiling, it may be a DataDictionary error. An error in the DataDictionary will affect all views that use the common DataDictionary. To compile a single view, open the view and then click the Test compile and run component in the debugger button.

Test compile button

Figure 238

338

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

2. Checking File Relationships Valid file relationships are critical to the correct operation in Visual DataFlex. Checking your relationships has been made easier in Database Builder.

From Database Builder:


[ Report [ Check Relationships

Figure 239

U[ Select All [ (uncheck) the DataFlex error file [ Start checking

Figure 240

Data Access Corporation

339

Lesson 11 Troubleshooting

Discovering Visual DataFlex

From this screen, we can print the report out. However, just reading it on screen will normally point us to any incorrect relationship.

Ensure the reports have no errors

Figure 241

The following tests are made and all mismatches reported: The length & type of each relating child field to the related parent field The parent related field is uniquely indexed The Required Child and Parent File Structure is correct

340

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

Another way to check that the required Child and Parent DataDictionary structure is correct is to remove the references and then use the magic wand to re-add them.

Figure 242

Use the delete buttons to remove all files and then use the top (magic wand ) buttons to add back only the files that have a relationship created.

Data Access Corporation

341

Lesson 11 Troubleshooting

Discovering Visual DataFlex

3. Checking for Unique Index on the Parent Related Field

The employee file relates to the Dept file on the Dept_Code field here we see that the Main index for this field is index 1
Figure 243

Figure 244

#2. Check that the Dept_Code field is the only field listed

342

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

4. Rebuilding the DDO Tree Within the View

This dialog is in the Studio. Open the Empl View, then press the DDO Tree button from the Database Selector tool.

Figure 245

If the Studio encounters file relationships in your DDO Tree Structure that are not represented in the DD classes, a warning message will appear.

Main_DDO Changing the Main_DDO will affect how the Constrain File commands will be added. All Child DDOs to Main DDO will have a Constrain_File property. Notice how both Timecard and Wk_Sum are constrained to Empl, which is the Main_DDO.

Data Access Corporation

343

Lesson 11 Troubleshooting

Discovering Visual DataFlex

Steps to Rebuild a DDO structure: Rebuilding the DDO tree can solve many oddball behaviors that are caused by an incorrect DDO structure.

Use the Studio Editor to check for any manual code additions in the DataDictionarys. If there are any edits, cut and paste them somewhere safe. Otherwise, we will lose these additions when we complete the next step. Use the Remove button to remove all DDOs. Use the Add DDO button to add in the Main_DDO file. This will add the main DD and all ancestors (parent, grandparent, etc.) DDOs to the structure. If you disallow saves in your view, the ancestor DD files will not be necessary, unless the files are needed elsewhere in the view. Next, use the Add DDO button and add all descendent (child, grandchild, etc.) DDOs. If deletes are disallowed, these descendent DDOs will not be needed unless the files are required elsewhere in the view.

Figure 246

344

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

5. Checking the Data During development of an application, as file structures and relationships change, invalid data can be added to the database. This bad data can be responsible for the application not operating correctly. Use Database Explorer to check for these problems: Check that System Files only has one record. Check that validated fields have valid data. Even if a field is not visible on screen, when the record is saved, all fields will be validated. If a validation on a field is added, the existing data must be validated against the new business rule.

Use Database Builder to check for these problems: Check Max Records against Records Used. Max Records should be set to about 20% above the estimated maximum size of the database. This estimate should be sufficiently large enough to accommodate the expected file, but be aware that making it too large will slow down index performance. Check for orphan records (from the Report pull-down)

Figure 247 Data Access Corporation 345

Lesson 11 Troubleshooting

Discovering Visual DataFlex

6. Debugging Compiler Errors & using a .PRN file The new editor in the Studio makes using the PRN files almost obsolete, but it is still worthwhile to know about this file.

Test compile button

Always compile each view separately. Compiling smaller sections makes it easier to locate the problem.

Even when compiling a single view, an error can still come from included files (i.e.; .DD; .SL; .PKG files).

Figure 248

346

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

Often the errors will direct you to the last addition that you made to the program, so finding the cause of the error is not that hard. Other times you have no idea which section of code contains the error. When this is the case, you may need to look at a .PRN file.

Tools | Configure Environment [ General Tab page Click in the Compiler Switches and press F1 for help

Switches

From the help screen, scroll down until you find the words Figure 249 Compiler Switches printed in green. Clicking on this link will jump you to the full explanation of the switches. The F option will generate the .PRN file.

Data Access Corporation

347

Lesson 11 Troubleshooting

Discovering Visual DataFlex

This .PRN file can then be loaded into any editor. If we were compiling the entire Order application example, then the .PRN would be called Order.PRN. If you are compiling a single view, the .PRN file will be named IDETestRun_X.PRN in the \AppSrc directory. After loading the PRN file, you search for the word ERROR:. Your code will be listed here along with the error messages. The error normally will be located within the two lines of code above where the error message is printed.

Our error here is cause by the incorrect spelling of integer.

We cannot Figure 250 correct the error in the .PRN file, but we can see that the code is located in the button object, so we return to the Studio and double click on the button to open the editor.
Note (Everyone): With the Studio Editor it is very seldom that looking at a .PRN file is needed. The Studio will open the correct file that contains the error just by double clicking on the error.

348

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

7. Create a Small Test Program Whenever you use a new class or try to accomplish something for the first time, create a small test program. Creating a test program will allow you to experiment with the new properties, procedures and functions. This will give you a better understanding of the code and how to use it before including it into a large program.

To do this, look up the new feature in online help. Often there will be sample code that you can cut and paste to test.

Bring up the DataFlex on-line Help


] F1 ] Index tab For_All Look through both entries on this topic

Notice the sample code that is provided can be cut and pasted directly into the Studio.

Figure 251

Data Access Corporation

349

Lesson 11 Troubleshooting

Discovering Visual DataFlex

8. The Debugger Runtime problems:

Some of the Debugger features: tracking down runtime errors setting watches message tracing

Open the CorporationX Application ] Compile and debug-run program button View | Empl View Resize the dialogs as shown

Figure 252

This will compile your application with all the debugging packages added and load & run both the debugger and your application.

350

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Troubleshooting

Within the Debugger:


Data | Watches Data | Local Variables Data | Global Variables Data | Call stack Tracing | View Message Trace Window | Tile

Figure 253

When starting to learn the debugger, you normally want to have all the components open.

The next step is normally setting breakpoints, which we will do in the lab.

Data Access Corporation

351

Lesson 11 Lab Troubleshooting

Discovering Visual DataFlex

Lesson 11 Lab
Description: Using the debugger. We will continue using the above example in the lab. If you have closed everything, simply refer back a few pages and set up the debugger again.

Tasks:

Debugger Breakpoints
First step is to set breakpoints. All files (views, components, .SL and packages) that make up the view will be available from the debugger comboform.
Select the Empl.dd from the comboform Scroll down until you find the Update & Backout properties [ the dots at the left (of the Forward Send statements) to create breakpoints where indicated

You cannot break on the actual Procedure line, so we break on the first line of code in the procedure. Will turn to red showing a breakpoint
Figure 254

352

Data Access Corporation

Discovering Visual DataFlex

Lesson 11 Lab Troubleshooting

Debugger Watches
Start Program Execution Button
Within the debugger, highlight Dept.Number_of_Empl and then right click on it

Step into
Select Evaluate from the floating menu [ Watch button [ Close Within the running program,

Watch on Dept.Number_of _Empl

find an existing record and change the Dept code F2 to save [ OK & then continue to press the Step into button and watch the Dept.Number_of_Empl field change as it steps through the Backout and Update procedures. List the values in the chart.

Value of Dept.Number_of_Empl Before the Backout After the Backout Before the Update After the Update Your results should show Backout subtracting one from the old department count and Update adding one to the new department count.

Data Access Corporation

353

Lesson 11 Lab Troubleshooting

Discovering Visual DataFlex

Did You Discover?

1. What does the Z compiler option do?

2. What does the S compiler option do?

3. If your users launch 3-4 copies of this program at the same time, how much memory will it use up?

354

Data Access Corporation

Discovering Visual DataFlex

Lesson 12 Waves and Bitmaps

Lesson 12
Waves and Bitmaps
This is a fun lesson that covers sounds and bitmaps and a few other GUI features of Visual DataFlex. We will add a wave file and bitmap file, adding sound and color to our application.

Topics in this Chapter:


Displaying Bitmaps from a Database File Displaying Bitmaps as a Backdrop Wave Files - Applications with Sound Creating a Wave File Embedded Resources Lab 12

Data Access Corporation

355

Lesson 12 Waves and Bitmaps

Discovering Visual DataFlex

Displaying Bitmaps from a Database File


This method was demonstrated in the Quick Start manual (and in our application). The ASCII field, Country.Flag Object oCountry_Flag is a dbBitmap holds the names Entry_Item Country.Flag // only the name of the bitmap file is stored of the bitmap Set Border_Style to Border_Dialog // Raised border files. The bitmap Set Bitmap_Style to Bitmap_Stretch // Auto-resize bitmap to fit object files are normally Set Size to 83 149 stored in the Set Location to 12 54 \bitmap End_Object subdirectory.

Objects of the dbBitmap class display the bitmap file named in a database field. Upon receiving the Entry_Display message from the data dictionary, the bitmap is displayed. These bitmap files store such data as personnel ID photos or inventory pictures.

Steps for Creating a dbBitmap Object All bitmaps must be created and assembled together in the bitmap directory. Create a dbBitmap from the database selector tool dragging the ASCII field into the view.

356

Data Access Corporation

Discovering Visual DataFlex

Lesson 12 Waves and Bitmaps

Displaying Bitmaps as a Backdrop


In Visual DataFlex, you can set the Bitmap property for any visible object. When the object is painted on screen, the bitmap file is displayed in the upper left corner of the object.

You may design your own bitmaps, or use any Object Print_Button is a Button *.BMP-format files legally Set Size to 10 10 available to you from any Set location to 20 20 source (*.BMP, or *.RLE Set BitMap to printer.bmp for the compressed bitmap Procedure OnClick format). Typically, you Send Print Report would design a bitmap to End_Procedure fit on, and completely cover, a control. If you End_Object want a panel or dialog to contain a bitmap, however, the chances are that you want its size and aspect ratio retained. Therefore, Visual DataFlex resizes bitmaps to fit controls, but does not resize bitmaps displayed on panels and dialogs. If you want the exact appearance of a bitmap you are putting on a control to be retained, make sure the ratio between the vertical and horizontal dimensions are the same for the bitmap as for the control.

Many VDF properties can be set to a .bmp file. Always check the help documentation for graphical file requirements. Some properties require a 24x24-pixel file.

Data Access Corporation

357

Lesson 12 Waves and Bitmaps

Discovering Visual DataFlex

Some common properties and functions are: Properties / Functions bitmap string filename bitmap_style integer BITMAP_ACTUAL| BITMAP_STRETCH| BITMAP_CENTER| BITMAP_TILE bitmap_height returns integer function bitmap_width returns integer function Description This property identifies the file containing the bitmap image for this object. This property specifies the position, size, or shape in which the bitmap image for this object is to be displayed. BITMAP_STRETCH fills the object with the image. This function returns the height of the image contained in the file named by bitmap. This function returns the width of the image contained in the file named by bitmap

Note: Bitmaps can also be used as Icons. They can also be captured to and from the Windows clipboard a complete explanation of this is in the Language Guide

358

Data Access Corporation

Discovering Visual DataFlex

Lesson 12 Waves and Bitmaps

Wave Files - Applications with Sound


Adding sound to your application is easy and fun. All you need is a sound card and a wave file.

Syntax:

PLAYWAVE WaveFilename PlayOption

The WaveFilename is the name of a wavefile (.WAV).

Use Wave Procedure OnChange

// include the Wave.PKG

PlayWave c:\windows\media\Chimes.wav" SND_ASYNC End_Procedure

//issue the Playwave command

PlayOptions SND_SYNC SND_ASYNC SND_NODEFAULT

Description Play synchronous. Plays from beginning to end. Will not interrupt (default setting) Play asynchronous. Interrupt playing by pressing a key. Does not play system default sound in the case that the specified file is not found. This must be Or'ed with either SND_SYNC or SND_ASYNC. Play in a loop Play non-stop

SND_LOOP SND_NOSTOP

Data Access Corporation

359

Lesson 12 Waves and Bitmaps

Discovering Visual DataFlex

Creating a Wave File


This section is for reference only. It requires sound cards, microphones, and speakers. Its purpose is to show how to use and create wave files. Windows sound recorder allows you to record your own . Wav files that you may then use in your application.
[ Start button [ Programs [ Accessories In Window 98, ME 2000 & XP: [ Entertainment [ Sound Recorder In Windows NT

Figure 256

[ MultiMedia [ Sound Recorder

The sound recorder buttons work very much like the buttons on a real recorder.
File | New [ Record Button and record a message File | Save As Give this file a name and save it under our\Bitmaps directory

Figure 257

360

Data Access Corporation

Discovering Visual DataFlex

Lesson 12 Waves and Bitmaps

Embedded Bitmaps
DataFlex can include bitmap files and icons into the Exe as native resources as it compiles your source code. This will increase speed of loading bitmaps and eliminate the need of copying these as separate files during deployment.

The Compiler uses the Programname.cfg file to determine what items to embed. This file can be directly edited but it also can be modified via the Studio from the Program | Properties Dialog.

Programs | Properties [ Bitmaps tab page [ Scan for images [ Yes Button [ Yes Button [ OK Button Close the Dialog

Figure 258

Data Access Corporation

361

Lesson 12 Waves and Bitmaps

Discovering Visual DataFlex

Within the Studio:


File | Open file Browse to the \AppSrc directory [ CorporationX.cfg Close the file after you look over the contents

Figure 259

362

Data Access Corporation

Discovering Visual DataFlex

Lesson 12 Lab Waves and Bitmaps

Lesson 12 Lab
Description: This lab uses one of the event procedures to add a picture as a background.

Tasks:

Open the application in the Studio [ Client_Area Cut & past the code modification from the Code_Mod.txt file Compile & Test

Figure 260

The CorpLogo.BMP file is located in the workspace \Bitmap directory, which was copied earlier from the training CD.

// Add to the bottom of the Client_Area object Set Bitmap to "CorpLogo.BMP"

Data Access Corporation

363

Lesson 12 Lab Waves and Bitmaps

Discovering Visual DataFlex

Did You Discover?


1. How can you make the TC_In view automatically display when the program is executed?

2. How can you create an icon on the desktop to automatically run this application?

3. After completing this lab, will you have to move the CorpLogo.BMP when deploying your application? What would you suggest be done?

364

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Lesson 13
DDs Local Buffers & Procedures
This lesson covers some of the most commonly used DataDictionary procedures and how the DataDictionarys Local Buffers operate.

Topics in this Chapter:


Changing Field Values DD Local Buffers Optimizing Field_Exit_msg Important DataDictionary Procedures Procedure Creating Procedure Update & Backout Functions Validate_Save & Validate_Delete Procedures Save_Main_File & Delete_Main_File Lab 13

Data Access Corporation

365

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

Changing Field Values - DataDictionarys Local Buffers


The DataDictionarys keep a local buffer that is synchronized with the data on the screen. Developers will find that the DataDictionarys local buffers are easier to access.

Without Data Dictionarys: there are three work areas Screen Buffer Area /DEO items
Set Changed_Value 0 to sVal

Record Buffer Area


// in a locked state to file.field Move sVal to Customer.St

Hard Disk
Save Customer

With Data Dictionarys: The Screen buffer and DD Local Buffer areas are always synchronized. Change one and the other one automatically updates.

Screen Buffer Area /DEO items


Set Changed_Value 0 to sVal

Record Buffer Area These are always synchronized. DD Local Buffer Area
Set Field_Changed_Value ; field Customer.St to sVal // in a locked state to file.field Move sVal to Customer.St

Hard Disk
Save Customer

366

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Setting data entry object values vs. setting DataDictionary buffers: Within the DEO
Set Value to FL

Within the DD
Set Field_Current_Value; field Customer.State to FL This only sets the value. Without the Field_Changed_State set to true, the data will not be moved into the database during the save! Flags the field as changed, so it will saved to the database during a save operation. A short-cut. It is a combination of the two properties above

Set Item_Changed_State to True Set Changed_Value to FL

Set Field_Changed_State; field Customer.State to True Set Field_Changed_Value; field Customer.State to FL

The Set establishes the property value. To retrieve property values use the Get command.

Get Value to sVar Get Field_Current_Value field Customer.State to sVar

Note: Many field properties are also available in the format file_field. These will set/get the value from a parent file:

Get File_Field_Current_Value File_Field Customer.Name to sVar

Data Access Corporation

367

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

Optimizing Field_Exit_Msg
The prior page covered the differences between Field_Current_Value and Field_Changed_State. Field_Current_Value changes only the value on screen. If a save occurred, the data would not be moved to the database. This may lead one to believe that using Field_Changed_Value all the time would be correct, but this is not always the case. The following two examples will both result in updating the extended_price. However, in grids, the Field_Current_Value is more efficient. The following pages will show you why.

Using Field_Current_Value procedure:


Set Field_Exit_msg Field Orderdtl.Qty_Ordered To Adjust_Display_Total

Procedure Adjust_Display_Total Integer iQty Number nAmnt Get Field_Current_Value Field Orderdtl.Qty_Ordered Get Field_Current_Value Field Orderdtl.Price to iQty to nAmnt

Set Field_Current_Value Field Orderdtl.Extended_Price to (nAmnt * iQty) // Note we set Current_Value, but not Changed_State! // Since Changed_State is not true, a save will not move the new value to the database // To update the field value we recalc it in procedure Update of the DataDictionary End_Procedure

Using Field_Changed_Value procedure:


Set Field_Exit_msg Field Orderdtl.Qty_Ordered

Note that the field is again updated in the Update procedure.


To Adjust_Display_Total

Procedure Adjust_Display_Total Integer iQty Number nAmnt Get Field_Current_Value Field Orderdtl.Qty_Ordered Get Field_Current_Value Field Orderdtl.Price to iQty to nAmnt

Set Field_Changed_Value Field Orderdtl.Extended_Price to (nAmnt * iQty) // note Field_Changed_State will set the Current_Value and the Changed_State End_Procedure

368

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Negative side effects of using Field_Changed_Value in Grids: When using a dbForm there is no big benefit of one procedure over the other. The big difference is when we are using a dbGrid. Accessing a blank row will create a record with only the Orderdtl.Extended_Price field filled in. Because the Field_Changed_Value sets Field_Changed_State to true, a save will take place EVERY time you navigate up or down the Quantity column, even though no user input took place. Using this property forcing saves, a LOT of unnecessary I/O traffic can be generated if the user scrolls in the Qty column.
Change the Studios workspace to Order Entry Sample Application Open OrderDtl in Database Builder and click on the methods tab page Scroll down to the Adjust_Display_Total procedure and change Field_Current_Value to Field_Changed_Value

Figure 261

// This updates the extended price field, which will update any // display balances. This is only done for display purposes. The actual // amount is updated to the field during the save. Procedure Adjust_Display_Total Integer iQty Number nAmnt Get Field_Current_Value Field Orderdtl.Qty_Ordered Get Field_Current_Value Field Orderdtl.Price // note we set value, but not changed state! End_Procedure to iQty to nAmnt

Set Field_Changed_Value Field Orderdtl.Extended_Price to (nAmnt * iQty)

Data Access Corporation

369

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

Save and return to the Studio File | Open | View | Order Entry Double click on the dbGrid and add the Row_Save function from Code_Mod.txt file Save and Compile the view

Figure 262

// Add to the top of the OrderDtl_Grid Function Row_Save Returns integer Integer iRetVal Send Info_Box "Save Operation being Called" Forward Get Row_Save to iRetVal Function_Return iRetVal End_Function

370

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Click F8 (to find the first record) Click on the first row of the Qty Column Move down the Qty Column without changing any values Note that a save is being triggered because of the Field_Changed_Value property. Continue down the Qty Column until you come to the first blank row

Figure 263

When you try to leave this blank row, a save is again attempted; but this time it will generate a Status 90 error because other columns are required fields in the DataDictionary. Click OK in the error dialog & Close the running application. Open Database Builder and return Field_Changed_Value to Field_Current_Value. Leave the other changes in place, recompile and run the application. Move down the Qty Column, without changing any values. Note that no saves are being triggered. This is because the change to the Field_Current_Value property alone did not cause the line to save. The Field_Changed_State remains false and therefore no save is triggered. This time the blank line problem we experienced earlier does not happen.

Data Access Corporation

371

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

We now see the benefits of using Field_Current_Value in dbGrids. However, since Field_Current_Value only sets the value, if we make a change to the Qty, how is the Qty field and the Extended price being saved to the database?

Open OrderDtl in Database Builder and click on the methods tab page Scroll down to the Update Procedure Note that Update will recalculate the Extended_Price field every time a save occurs

Figure 264

372

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Important DataDictionary Procedures


DataDictionarys handle the reread and unlocking of the file during the save and delete operations. It is imparitive to allow the developer to add custom code at numerious points throughout these operations. Many DataDictionary procedures have been created for the developer to use as hooks. These hooks allow the developer to code at key points during the Save or Delete operations. There are many common procedures and functions listed in the Methods tab of Database Builder. We will cover the four basic procedures that are used most often. These procedures are always called in a locked state, thus it is safe to access the record buffers. New Save Sends Edit Save Sends Delete Sends

Procedure Creating

Procedure Update

Procedure Backout Normally

Procedure Deleting

Mirror Images of each other

Note: When you are outside of a locked state, reference item windows or the DD local buffers. Inside a locked state, reference file.fields (record buffers). Never add code in a locked state that would wait for user intervention.

Data Access Corporation

373

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

Procedure Creating
This procedure is only called when saving a New Record. Here we are adding the users ID to the newly created record so we can track who created the record.
Procedure Creating Forward Send Creating Move (UserID(Self)) to Empl.Created_By End_Procedure // Creating

The Creating procedure (and other procedures covered here) is an empty hook (empty procedure) within the basic class package. When the procedure is an empty hook in the Class, it is not required to Forward Send. Although it is a good practice to always Forward Send, since we may someday add new subclass layers that would then require the Forward Send.

Note: (DataFlex 3.1 Object Oriented Programmers) The Destroying procedure is obsolete, given the new transaction processing feature.

374

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Procedure Update & Backout


Update is called during a new save and Backout is called during a delete. Both procedures are called during an edit save. These procedures can be used to maintain running totals. Typically, the procedures will be mirror images of one another, Update adding to the running total and Backout subtracting from the total.

Procedure Update Forward Send Update Add TimeCard.Pay to Empl.YTD_Pay End_Procedure Procedure Backout Forward Send Backout Subtract Timecard.Pay from Empl.YTD_Pay End_Procedure

To fully understand how these two procedures work so harmoniously together during an edit save, we must remember that both are called during the same locked state and that Entry_Update (which moves the data from the image to the record buffer) is called between these two procedures.

STEPS: ReRead Backout Locks files and refreshes the record buffer Subtracts the original timecard amount from the running total (this is like deleting out the original record) Entry_Update Update Save Moves new data values from the screen to the record buffer Adds new timecard amount to the running total Moves data from record buffer to disk

Data Access Corporation

375

Lesson 13 DDs Local Buffers & Procedures

Discovering Visual DataFlex

Functions Validate_Save & Validate_Delete


These functions are intended to check for such things as possible data-integrity violations or other checks just prior to the writing of the record to the disk. If the function returns a zero, the save/delete is allowed. Returning a non-zero will prevent the operation.

// Will give an error if the inventory is not sufficient to cover the order. // This function would normally go inside the Order detail DataDictionary Function Validate_Save Returns Integer Integer iRetVal If (Invt.Qty < 0) Begin Error DFErr_Operator "Insufficient Inventory on hand" // error message will occur after the unlock Function_Return 1 End Forward Get Validate_Save to iRetVal Function_Return iRetVal End_Function

// before deleting Customer record, check if needed for end of year taxes via an active field Function Validate_Delete Returns Integer Integer iRetVal Forward Get Validate_Delete to iRetVal If (iRetVal <> 0) Function_Return iRetVal // the delete has failed, no need to continue If (Customer.Status = "Y") Begin Error DFErr_Operator "Cannot delete an Active Customer" // error will not show until unlock occurs Move 1 to iRetVal End Function_Return iRetVal End_Function // to stop the delete

Validate_Delete is called from a locked state. The error message will not appear until the operation is completed and the file is unlocked.

376

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 DDs Local Buffers & Procedures

Procedures Save_Main_File & Delete_Main_File


These procedures by default perform a save/delete operation on the main_file. They are intended to be augmented or overridden.

In both of these examples, the extra Hist file is not part of the DataDictionary structure. To have the file locked and reread with the other files, we would add it to the External Structure in the DataDictionary.

// Purpose: To collect a record of all save operations made to the main file into a history file. Procedure Save_Main_File // clear, move the fields into the history file & save Clear Hist Move Employ.ID to Hist.ID Move Employ.Name to Hist.Name ... SaveRecord Hist Forward Send Save_Main_File End_Procedure // Save_Main_File

// Purpose: Before deleting an employee record, save the data to a history file Procedure Delete_Main_File // clear, move the fields into the history file & save Clear Hist Move Employ.ID to Hist.ID Move Employ.Name to Hist.Name ... SaveRecord Hist Forward Send Delete_Main_File End_Procedure // Delete_Main__File

Data Access Corporation

377

Lesson 13 Lab DDs Local Buffers & Procedures

Discovering Visual DataFlex

Lesson 13 Lab
Description: This lab will not list all keystrokes. It lists general instructions. It is a good review of many of the topics covered so far in the manual. It uses the procedures that we have learned in this lesson. It also adds an additional Company file. When an additional file is added to the File/DataDictionary structure, many steps need to be taken to make sure all existing files are updated correctly. Tasks: Open the Empl file in Database Builder and review how we maintained the running totals for the Number of Employees in the Dept file.

Review the Update and Backout Procedures

Figure 265

378

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 Lab DDs Local Buffers & Procedures

Using Database Builder, create a new Company file (file number = 1). Then create the needed index so this can be used as a parent file. (For help, review the rules of file relationships located in Appendix C). Company; Filenumber = 1 Fields Company_Code Type ASCII Length 4 Field Settings AutoFind CapsLock Name Total_Budget ASCII Numeric 25 8.2 Key Field AutoFind Currency Mask

Index #1 = Company_Code Index #2 = Name

Open the Dept file: Add a field in the Dept file called Company_Code (this field must be called Company_Code for a future Lab to work!). Relate the Dept.Company_Code field to the Company.Company_Code field (both fields must be the same size and type to relate them!). Create a new Index #3 with the new Company Code field and the Dept Code fields as the index segments. Both uppercase checkboxes should be checked. (Did you remember to verify the structures tab on both Company & Dept DataDictionarys?)

Data Access Corporation

379

Lesson 13 Lab DDs Local Buffers & Procedures

Discovering Visual DataFlex

Select File | New Component and use the Invoice Style template that was created in a prior lesson. Create a small view called CoDept that will show the Company data at the top and all the related Dept records in a dbGrid below. You may wish to review the prior Lab where we used the Invoice_Style template to create the DeptEmpl view. The steps below will walk you through all the steps. Update the two default properties within the template. Company Company.Company_Code Set the Main_DDO to Company in this new view. Delete the Parent Related Object Attach the Company.Code and Company.Total_Budget fields to the first and last dbForms Add labels to these objects Add the Company.Name field Adjust the Object-Order to correct navigation among these three objects. Add Dept fields to the dbGrid. Hint: comment (text) fields cannot be placed in dbGrids. Align objects Compile and Test the view. Create a company record with the company code of DAW. Before you create this record, first press Ctrl+F5 to clear the grid. The department records already created will be showing up in the grid as orphan records. This is because their Company_Code field is blank in all these records. Do not correct this now. We will correct this in a batch process in another lesson.

380

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 Lab DDs Local Buffers & Procedures

The Dept DataDictionary file will need Update and Backout procedures to collect the running total in the Company.Total_Budget field. Review the Update and Backout procedures just covered in this lesson and the one just reviewed at the start of this lab as a model. The OrderDtl.DD in the Order sample is an excellent example to study. If you need more help, see the completed DataDictionarys in the Finished Example workspace.

Add the new view to the CorporationX Application.

What did we learn about which DataDictionarys are required in a view? (Both parent and child DataDictionarys are needed to save and delete records in the main DDO). What will happen when we go to save a record in the other views? (They will not be able to save, unless all parent DataDictionarys are present. This is because Save operations propagate up so all parent DataDictionarys are required in all views.). Make the needed changes in all views to add the Company DataDictionary using the DDO button on the Database Selector tool. Close the Database Selector tool every time you switch between views.

Update the DeptView by adding the Company.Company_Code field to the view.

Update Dept/Empl View by adding the Company.Company_Code field to the view. This object should be the related parent object that was created in the Invoice_Style template but we already deleted it in the prior lab. The code is listed below and in Code_Mod.txt under lesson 13. Cut and paste it into this object. This code will shadow the parent object when you find an existing record.

Save, Compile & Test you may need to review the Troubleshooting lesson.

//------------------------------------------------------------------// Add to Parent (dbForm) object - below the green line // If Header record exists, disallow entry in Related Parent window. //------------------------------------------------------------------Procedure Refresh Integer iMode

Data Access Corporation

381

Lesson 13 Lab DDs Local Buffers & Procedures


Integer iSrvr iCrnt Get Server to iSrvr // get the DataDictionary Get Current_Record of iSrvr to iCrnt // get record in DataDictionary // Set displayonly to true if iCrnt is non-zero Set Enabled_State to (iCrn = 0) Forward Send Refresh iMode // do normal refresh // don't leave us sitting on a displayonly window If (iCrnt and Focus(Self)=Current_Object) Send Next End_Procedure

Discovering Visual DataFlex

382

Data Access Corporation

Discovering Visual DataFlex

Lesson 13 Lab DDs Local Buffers & Procedures

Did You Discover?


1. In the lab, we sent the Adjust_Running_Empl_Total message from the Update and Backout procedures. We are only adding one or/and subtracting one employee to the Dept.Number_of_Empl field. Creating is only called on a New save and Deleting is only called on a Deletion of the Empl Record. Could Creating and Deleting procedures been used instead?

2. Can you write a business rule so that a company must have a "NAME" (must not be blank?)

3. Can you write a business rule so that a company record can never be deleted?

4. In the Dept Backout and Update, we do not explicitly say "Save Company". When you delete or save a Dept record, is the Company total budget updated and saved? Why?

Data Access Corporation

383

Lesson 13 Lab DDs Local Buffers & Procedures

Discovering Visual DataFlex

384

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Lesson 14
Classes Within the Studio
This lesson covers the creating of new classes. These classes are then made accessible via the Studio.

Topics in this Chapter:


Building New Subclasses Switching Classes the Studio Uses Creating SubClass Layering Templates DFS Files DFO Files Using Subclasses in the Studio Local & Global directories Lab 14 Steps to Add a New Class to the Controls Palette

Data Access Corporation

385

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Building New Subclasses


Building a new class is like building a new tool that you can then use to build objects. You start with an existing class and build your subclass from it.

Lets look at the DataDictionary class. The DataDictionay Class is the most common subclassed. This was done within Database Builder when we created each file. The DD file contains this subclass. This allows us to have one centralized file that holds all the rules for an individual database. If all our views use this new subclass, then we will have consistent behavior throughout our application. A new business rule added to the class will affect all views!

The DataDictionary class is not the only class that we can subclass. If we continually have to modify an object it is a good indication that we should subclass.

Syntax for creating a Class:


Class subclass is a Super_Class Procedure Construct_Object Forward Send Construct_Object // declare new properties // initialize properties (with the SET command) // define child objects // define accelerator keys / or modify them End_Procedure // Procedure & Functions are added here End_Class

386

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Here we create a new subclass. In addition to the behaviors already present in the AppClientArea Class, it sets the corporate logo as a background and creates a new property called pRestrict_Rights. Objects built from this new class will have the corporate logo displayed and can SET or GET the value of the pRestrict_Rights property.

// Stored in cCorp_AppClientArea.pkg file in the \PKG (global) or AppSrc (local) directory: Class cCorp_AppClientArea is a AppClientArea Procedure Construct_Object Forward Send Construct_Object Set Bitmap to CorpLogo.bmp Property Integer pRestrict_Rights 0 End_Procedure End_Class

Note: The DataDictionary class uses a special constructor procedure called Define_Fields. Other subclasses use the Construct_Object syntax.

Data Access Corporation

387

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Switching Classes the Studio Uses


This dialog allows you to change the default class that the Studio uses when building objects. In turn, this affects the objects built from the Controls Palette and other tools.

Within the Studio:


Tools | Configure Environment [ Classes tab page [ Close the dialog

Figure 266

388

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Creating SubClass Layering


When developing your applications, it is a wise decision not to use Data Accesss supplied classes directly but, instead, to use your own subclasses of them. The Studio will create two basic layers of subclasses, a Global layer that affects all work areas and an individual Workspace layer for each workspace. This means you can fine tune each workspace for the individual customer, but if a feature should affect all workspaces, it would be added to the Global layer. VDF Packages Global Layer Workspace Layer Workspace Layer Workspace Layer

. . .

As a development strategy, you will create a Global layer of subclasses, descended directly from the supplied classes. Then, for each Workspace that you create, you will subclass the Global layer to create a Workspace layer. This diagram outlines the hierarchy of classes that will then exist: Take the Button class as an example and using the supplied defaults, this is how the hierarchy would look:

Button (Visual DataFlex Supplied base class) +-cMyButton (Global subclass here the size could be globally changed) +-cWsButton (Workspace subclass the color could be changed for each customer)

In your applications, you would not create objects from the Button or cMyButton classes: you would use only the cWsButton. You would never make changes to the Button class (as Data Access would do that), but you would make changes to the global cMyButton class that you wanted all your Workspaces to include. These changes would include setting defaults different from those supplied that are appropriate for your work (changing colors, fonts, etc.), and they could even include bug fixes to those supplied classes, or new features. You would change the Workspace cWsButton to include changes specific to a Workspace. As these classes are derived from the Global subclasses, they will automatically have all the changes of the Global subclasses.
Data Access Corporation 389

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

When creating a subclass layer, you merely need to provide a few details and the Studio will automatically create all files that are needed to support the subclass layer. In a working development area, it is highly suggested that you create both Global and workspace layers. Creating Global Layer:
Tools | Create Global subclass layer

Warning! If you do not wish to create a global area (because you already have one created or for other reasons) then press Cancel button and do not complete the step below. On the next page, make sure you check the Original DAW installed classes.

Figure 267

[ Preview [ OK [ OK This will take a little time to complete

Note that it will replace all c prefix with cMy


Figure 268 390 Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Creating Workspace Layer:

Workspace | Create subclass layer

Figure 269

[ Preview [ OK [ OK

Note that it will replace all cMy prefix with cWs check this radio ONLY if you did NOT create a global layer
Figure 270

Data Access Corporation

391

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Templates (Speeding Development)


Manual code additions are often required to enforce business rules and to ensure the view operates correctly. Creating Templates will eliminate the repeating of custom additions that we want standardized within all our objects, views and/or applications. There is no reason to re-create the wheel each time we create a similar section of code.

The Studio will support templates at global and local levels: 1 Sub-component templates (a group of objects that can be saved & reloaded) 2 DFS DF Sub Components

Component templates (Lesson 4 created a View640x480 and Invoice_Style View templates) TPV TPR TPL TPD Template View files Template Report files Template List files Template Dialog files

Sub-component templates: A sub-component is any group of objects that can be saved to a file and reused in a component. What we are really doing is sort of a cut and paste into the component code.

Component templates: Any component (View, Report, Lookup list, Dialogs) can be saved as a template.

392

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

DFS files
A .DFS file is a DF Sub-component template. DFS files can be saved as Global or Local workspace files, stored in the \Visual DataFlex 9.1\Usr\Global\IdeSrc or local workspace \IdeSrc directory.
Create a view & drag a RadioGroup from the Base Containers tab Change the Group label to Send Report to: Change the Radios labels to Screen; Printer & File Cut & paste the manual code from the Code_Mod.txt file to the Radio Group within the Notify_Select_State procedure

We now have a component template that could be used for Crystal report views.
//----------------------------------------------------------------------// Add to the Notify_Select_State procedure of the Radio_Group //----------------------------------------------------------------------Case Begin Case (iToItem =0) Set Output_Device_Mode To PRINT_TO_WINDOW Case Break Case (iToItem =1) Set Output_Device_Mode To PRINT_TO_PRINTER Case Break Case (iToItem =2) Set Output_Device_Mode To PRINT_TO_FILE Case Break Case End

Data Access Corporation

393

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Saving a DFS:

[ RadioGroup Component | Save object Sub-Component | Local Enter Crystal_Print_Radio [ Save Close the VIEW without saving

Figure 272

394

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Inserting a DFS

New Standard ReportView


[ the New Standard ReportView button Component | Insert object SubComponent | Local [ Crystal_Print_Radio. dfs [ Open Save this new report as RptRadio then close the view and reopen it Notice our RadioGroup has the labels and the added code in the editor

Figure 273

Data Access Corporation

395

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

DFO Files
A .DFO file is also known as an object preference file. This file can be used to set properties, add custom source code, or to create additional child objects. When a new object is created by the Studio, the object's preference file is processed and added to the object. DFO files can be saved as Global or local workspace files, stored in the \Visual DataFlex 9.1\Usr\Global\IdeSrc or local workspace \IdeSrc directory.

Close all other components [ New Standard View button Drag a cWSDbForm from Data tab Change the object name to oName1 and the Label Name1

Figure 274

396

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

We will be changing the Form_Border.

File | New File Cut the following code from Code_Mod.txt and paste it into this new file. Save the file as cWsDbForm.dfo in the workspace \IdeSrc directory

Figure 275
//AB/ OBJECTDEF Object Set Form_Border to Border_None //AB-StoreStart //Procedure //End_Procedure //AB-StoreEnd End_Object

Anything between the //ABStoreStart&End markers will be added to the object and accessible in the Code Explorer.

Data Access Corporation

397

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Drag another cWsDbForm into the view Change the object name to oName2 and the Label Name2 / Name2 to bring up the Code Explorer (the comments from the DFO should show) Save as TestNewDFO then close the view

Figure 276

398

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Using Subclasses in the Studio


Subclasses are new tools that are built from existing classes adding or changing the features of the superclass.

Basic Steps to Create a Subclass to be used in the Studio:


Step #1 Create a new subclass. Create a new subclass and save it as a .PKG file

Step #2 Create .DFC file The .DFC file informs the Studio how to handle your new class. Include the line Set ClassPackage To "Classname.pkg" OR add Use ClassName.pkg line to your DFAllEnt.pkg and pre-compile it. Creating .DFC file will be demonstrated in the lab.

The Studio can now display simple comments for each property in the Property Window. This is accomplished by changing the property declarations in a class's DFC file. The general syntax is to add the comment at the end of the property declaration after a "//". For example: Property Complex Size 150 300 // Object Size (Complex: height, width) Several special comment markers are allowed. Marker // Description This means delete any comment that might exist from the super class. Comment will be blank. Note required space between // and -. Only the single - is allowed // + xxxxxxx Append text following the + to any existing superclass comment. Old and new comment will be separated by a space. Note required space between // and + No comment or Use super class comment. Normally, just leave the comment // // xxxxxxxx Replace existing comment

Data Access Corporation

399

Lesson 14 Classes Within the Studio

Discovering Visual DataFlex

Step #3 Updating the Studios Controls Palette Tool (required only if class should be visible on the Controls Palette tool) Copy the required 24X24 bitmap (to be used on the button in the Controls Palette) to the \IdeSrc area. Add your new subclass information to Maintain Class-List (located on the Tools pull-down of the Studio).

Note: Naming Convention - Use the same name for the class, the package file, the description file(dfc) and the bitmap file. The Maintain Class-List dialog is optimized for this notation. Ex: BigButton 1. Class BigButton is a Button . . . Save the DataFlex class in a file called BigButton.pkg 2. 3. Create the Studio class file as BigButton.dfc Create a bitmap to be displayed on the Controls Palette, called BigButton.bmp

400

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Classes Within the Studio

Local & Global directories


Most of the files discussed in this lesson are stored in the IdeSrc directory. Local files are used only by the local workspace. Global files are used by all workspace. Files Sub Components & Component Templates File extensions .DFS .TPV .TPR .TPL .TPD Object Preference Sub Classes .DFO .DFC .PKG \IdeSrc \IdeSrc \AppSrc \Usr\Global\IdeSrc \Usr\Global\IdeSrc Local Workspace \IdeSrc Global \Usr\Global\IdeSrc

Data Access Corporation

401

Lesson 14 Lab Lesson 14 Lab

Discovering Visual DataFlex

Lesson 14 Lab
Description: This lab creates a new class and adds it to the Controls Palette for use within the Studio.

Tasks:

Steps to Add a New Class to the Controls Palette


Step #1. Create the new subclass Our example is a large print button with a printer.bmp displayed on it.
Create a new file File | Open New Cut the following code from Code_Mod.txt and paste it into a new file in the Code Editor. Save it as cWsPrint_Button.PKG in the workspace \AppSrc directory

Figure 277
// Add to the new file called cWSPrint_Button.PKG // cWsPrint_Button class is a print button // that has a printer bitmap displayed on it. Class cWsPrint_Button is a Button Procedure Construct_Object Forward Send Construct_Object Set Bitmap to "cWsPrint_Button.bmp" Set Size To 28 30 End_Procedure End_Class

402

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Lab Lesson 14 Lab

Step #2a Create .DFC file The .DFC file tells the Studio how to use the new class
FFile | New File
Cut the following code from Code_Mod.txt and paste it into the Code Editor Save it as cWsPrint_Button.DFC in the workspace \IdeSrc directory

//AB/ CLASSDEF // Add to the new file called cWSPrint_Button.DFC Class cWsPrint_Button is a Button Set ClassPackage to cWsPrint_Button.pkg Inherit Property No_Visible No_Generate String Bitmap cWsPrint_Button.bmp Property Complex Size 28 30 End_Class

Step #2b Create .DFO file (this is not require) The .DFO file tells the Studio how to use the new class
FFile | New File
//AB/ OBJECTDEF Object //AB-StoreStart Procedure OnClick End_Procedure // OnClick //AB-StoreEnd End_Object

Cut the following code from Code_Mod.txt and paste it into the Code Editor Save it as cWsPrint_Button.DFO in the workspace \IdeSrc directory

Data Access Corporation

403

Lesson 14 Lab Lesson 14 Lab

Discovering Visual DataFlex

The class .PKG file would have to be added and pre-compiled in your DFAllEnt.PKG, if the Set ClassPackage line is removed from the .DFC.

The DFC options are fully described in the on-line help. Quickly look over this section
Open the WinHelp File [ Studio [ Advanced Topics [ Using Your Own Subclasses [ Anatomy of Studio Subclasses [ Introduction Look up Inherit and the other lines that were used in our .DFC

**
Figure 278

404

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Lab Lesson 14 Lab

Step #3 Updating the Studios Controls Palette Tool

Close programs and components in the Studio [ Tools [ Configure Class-List [ Workspace tab [ Add button Enter the data for the new class [ Add button [ OK From Windows explorer copy the cWsPrint_Button.bmp from the training CD to the workspace \Bitmaps directory

Figure 279

The order of our tab pages and controls are in the same order shown in this list. The Global list is created first and then the workspace ones. Therefore, our new tab page should be created last.

Data Access Corporation

405

Lesson 14 Lab Lesson 14 Lab

Discovering Visual DataFlex

Create a new view using your new control Save view as Testbutton Compile and test your new control remember the OnClick will not work since it is empty.

Figure 280

Notice that the bitmap property is no longer displayed in the Object Properties dialog and the button size is larger

406

Data Access Corporation

Discovering Visual DataFlex

Lesson 14 Lab Lesson 14 Lab

Did You Discover?


1. Why create Subclasses?

2. A few classes listed in the Configure Class-List have the Image and Page columns empty. Why?

3. In many lessons, we have discussed ways that make developing faster and easier. Can you name the files extensions that are created to speed development?

4. In an earlier lesson, an Invoice_Style template was created in the Global area. What would have to be done to remove this global template?

Data Access Corporation

407

Lesson 14 Lab Lesson 14 Lab

Discovering Visual DataFlex

408

Data Access Corporation

Discovering Visual DataFlex

Lesson 15 Batch Processing

Lesson 15
Batch Processing
This lesson covers Business Process Objects (BPOs). They are used whenever batch processing of records is required.

Topics in this Chapter:


Business Processing Objects (BPO) Batch Process using DDOs Lab 15 BPO to Update Company Fields in Dept Records BPO to Log Employees Out at End of Day

Data Access Corporation

409

Lesson 15 Batch Processing

Discovering Visual DataFlex

Business Process Objects (BPO)


When we added the Company File in the prior lab, we created orphan records in the Dept file. We need to update these Dept Records so they contain valid data in the Company field. We use Business Process Objects (BPO) for batch processing of records. Here is a code segment that will read all Dept records and save them with the DAW company code in them.
Object oUpdateRecords_BP is a BusinessProcess Set Location to 15 51 Set Process_Caption to "Update_Records" //AB-StoreStart Open Dept // use these to keep track of process Property Integer piChanged_Count 0 Property Boolean pbProcess_Completed_State False Set Allow_Cancel_State to True // We will not use a DDO structure. // This is because we are updating orphan records. // The datadictionary would try to do an "Attach" during the save. // Create the process. Procedure OnProcess Boolean bExit Repeat // scan records. Clear Dept Find GT Dept.Company_Code // Will not have to seed the Index since we are // looking for blank Dept.Company_Code If (Dept.Company_Code <> "") Break // Jump out of index - all blanks have been updated Send Update_Status ("Updating data" * String(Dept.RecNum)) ReRead Dept Move "DAW" to Dept.Company_Code SaveRecord Dept Unlock Set piChanged_Count to (piChanged_Count(Self)+1) // count items changed Get Cancel_Check to bExit // check for cancel of status panel Until (bExit)

410

Data Access Corporation

Discovering Visual DataFlex


// if the process was canceled roll back If bExit ; Send Log_Status Else Begin Set pbProcess_Completed_State to True End End_Procedure // This message runs the process. // We augment this to print a status dialog when finished Procedure DoProcess Boolean bDone String sChgCount Set piChanged_Count to 0 Set pbProcess_Completed_State to False Forward Send DoProcess Get piChanged_Count to sChgCount Get pbProcess_Completed_State to bDone "Process was Canceled"

Lesson 15 Batch Processing

Send Info_Box (If(bDone,"Process Completed", "Process was canceled") + ; "\n\n Logged " * sChgCount * "Dept Records Changed!") // the "\n\n" will start a new line End_Procedure //AB-StoreEnd End_Object // oUpdateRecords_BP

Data Access Corporation

411

Lesson 15 Batch Processing

Discovering Visual DataFlex

Batch Process using DDOs


The following BusinessProcess object will be used to log all the employees out at the end of the day. The process will start from the OnClick event of a Button sending the DoProcess message.
Object oEveryoneGone_BP is a BusinessProcess Set Location to 62 22 Set Process_Caption to "Update Records" //AB-StoreStart //Use these to keep track of process Property Integer piChanged_Count 0 Property Boolean pbProcess_Completed_State False Set Allow_Cancel_State to True // we need a complete DDO structure // If deleting records all child DDOs - Deletes propagate down // If saving records all Parent DDO End_Object // Company_DD - Saves propagate up Object Company_DD is a Company_DataDictionary

Object Dept_DD is a Dept_DataDictionary Set DDO_Server to Company_DD End_Object // Dept_DD

Object Empl_DD is a Empl_DataDictionary Set DDO_Server to Dept_DD Procedure Update Forward Send Update Move "O" to Empl.logged End_Procedure End_Object // Empl_DD

// Create the process. Procedure OnProcess Handle hoDD Boolean bExit Move Empl_DD to hoDD // object id of empl dd Repeat // scan all records.

412

Data Access Corporation

Discovering Visual DataFlex


Send Clear to hoDD

Lesson 15 Batch Processing

Send Find to hoDD GT Index.4 // Will not have to seed the Index // Empl.logged field should only contain "I" or "O" If (Empl.logged = "O") Break // Jump out of index Send Update_Status ("Updating data" * Empl.Last_name) Send Request_Save to hoDD Set piChanged_Count to (piChanged_Count(Self)+1) // count items Get Cancel_Check to bExit // check for cancel of status panel Until (bExit) If bExit ; Send Log_Status Else Begin Set pbProcess_Completed_State to True End End_Procedure // This message runs the process. // We augment this to print a status dialog when finished Procedure DoProcess Boolean bDone String sChgCount Set piChanged_Count to 0 Set pbProcess_Completed_State to False Forward Send DoProcess Get piChanged_Count to sChgCount // use counter to report records changed Get pbProcess_Completed_State to bDone Send Info_Box (If(bDone,"Process Completed","Process was canceled") + ; "\n\n Logged " * sChgCount * "Employees Out!") // the "\n\n" will start a new line End_Procedure //AB-StoreEnd End_Object // oEveryoneGone_BP "Process was Canceled"

Data Access Corporation

413

Lesson 15 Lab Batch Processing

Discovering Visual DataFlex

Lesson 15 Lab
Description: The two BPOs covered in the lesson will be used in this lab. Both will be attached to buttons that will start the processes. When we created the new Company file and added the new Company_Code field in the Dept file, this created a problem that this field was blank. This lab will correct the problem by inserting a company code into all blank Dept.Company_Code fields. Tasks:

BPO to Update Company Fields in Dept Records


Create a new view Drag a BPO (Business Process) and a button object to the view Set the button object name to oStart_Process and the label to Start Process Cut and paste the code from Code_Mod.txt to the Buttons OnClick procedure

Figure 281

// add this code to Start_Process button Send DoProcess of oUpdateRecords_BP

414

Data Access Corporation

Discovering Visual DataFlex

Lesson 15 Lab Batch Processing

Set the BP object name oUpdateRecords_BP Set the Process_Caption to Update_Records Cut and paste the code from Code_Mod.txt to the BP Replacing all existing code and comments (EXCEPT for green line) Save as UpdateCo Compile & Test Verify all records are updated with Database Explorer

Figure 282

//---------------------------------------------------------// Add to the oUpdateRecords_BP Open Dept // use these to keep track of process Property Integer piChanged_Count 0 Property Boolean pbProcess_Completed_State False Set Allow_Cancel_State to True // We will not use a DDO structure. // This is because we are updating orphan records. // The datadictionary would try to do an Attach during the save. // Create the process. Procedure OnProcess Boolean bExit Repeat // scan records. Clear Dept Find GT Dept.Company_Code // Will not have to seed the Index since we are

Data Access Corporation

415

Lesson 15 Lab Batch Processing


// looking for blank Dept.Company_Code

Discovering Visual DataFlex

If (Dept.Company_Code <> "") Break // Jump out of index - all blanks have been updated Send Update_Status ("Updating data" * String(Dept.RecNum)) ReRead Dept Move "DAW" to Dept.Company_Code SaveRecord Dept Unlock Set piChanged_Count to (piChanged_Count(Self)+1) // count items changed Get Cancel_Check to bExit // check for cancel of status panel Until (bExit) // if the process was canceled roll back If bExit ; Send Log_Status Else Begin Set pbProcess_Completed_State to True End End_Procedure // This message runs the process. // We augment this to print a status dialog when finished Procedure DoProcess Boolean bDone String sChgCount Set piChanged_Count to 0 Set pbProcess_Completed_State to False Forward Send DoProcess Get piChanged_Count to sChgCount Get pbProcess_Completed_State to bDone Send Info_Box (If(bDone,"Process Completed", "Process was canceled") + ; "\n\n Logged " * sChgCount * "Dept Records Changed!") // the "\n\n" will start a new line End_Procedure "Process was Canceled"

416

Data Access Corporation

Discovering Visual DataFlex

Lesson 15 Lab Batch Processing

BPO to Log Employees Out at End of Day


This new button will allow us to quickly log all remaining employees out at the end of the day.

Open TC_Out view Add a Button and BP object Set the button Label to Everyone Gone and the object name to oGoneButton Cut and Paste code to the button

Figure 283
// add this code to the Everyone Gone button Send DoProcess of oEveryoneGone_BP Send Beginning_of_Data of oEmpl_Grid

Data Access Corporation

417

Lesson 15 Lab Batch Processing

Discovering Visual DataFlex

Label the BP object oEveryoneGone_BP Set these properties: Process_Caption to Update_Records Cut and Paste code to the BP replacing code already there (EXCEPT for green line) Compile & Test view

Figure 284

If you do not have any employees that are logged in, you may have to compile the entire program and log in some employees first.

// Add to oEveryoneGone_BP // use these to keep track of process Property Integer piChanged_Count 0 Property Boolean pbProcess_Completed_State False Set Allow_Cancel_State to True // we need a complete DDO structure // If deleting records all child DDOs - Deletes propagate down // If saving records all Parent DDO End_Object // Company_DD - Saves propagate up Object Company_DD is a Company_DataDictionary

Object Dept_DD is a Dept_DataDictionary Set DDO_Server to Company_DD End_Object // Dept_DD

418

Data Access Corporation

Discovering Visual DataFlex

Lesson 15 Lab Batch Processing

Object Empl_DD is a Empl_DataDictionary Set DDO_Server to Dept_DD Procedure Update Forward Send Update Move "O" to Empl.logged End_Procedure End_Object // Empl_DD

// Create the process. Procedure OnProcess Handle hoDD Boolean bExit Move Empl_DD to hoDD // object id of empl dd Repeat // scan all records. Send Clear to hoDD Send Find to hoDD GT Index.4 // Will not have to seed the Index // Empl.logged field should only contain "I" or "O" If (Empl.logged = "O") Break // Jump out of index Send Update_Status ("Updating data" * Empl.Last_name) Send Request_Save to hoDD Set piChanged_Count to (piChanged_Count(Self)+1) // count items Get Cancel_Check to bExit // check for cancel of status panel Until (bExit) If bExit ; Send Log_Status Else Begin Set pbProcess_Completed_State to True End End_Procedure // This message runs the process. // We augment this to print a status dialog when finished Procedure DoProcess Boolean bDone String sChgCount Set piChanged_Count to 0 Set pbProcess_Completed_State to False Forward Send DoProcess Get piChanged_Count to sChgCount // use counter to report records changed Get pbProcess_Completed_State to bDone "Process was Canceled"

Data Access Corporation

419

Lesson 15 Lab Batch Processing

Discovering Visual DataFlex

Send Info_Box (If(bDone,"Process Completed","Process was canceled") + ; "\n\n Logged " * sChgCount * "Employees Out!") // the "\n\n" will start a new line End_Procedure

420

Data Access Corporation

Discovering Visual DataFlex

Lesson 15 Lab Batch Processing

Did You Discover?

1. Will the Business Process still work if you remove the DoProcess Procedure?

2. Can you still use procedural code instead of BPO to process records?

Data Access Corporation

421

Lesson 15 Lab Batch Processing

Discovering Visual DataFlex

422

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Reporting

Lesson 16
Reporting
This lesson covers the creating of reports via the report wizards and adding report views to your VDF application. Crystal is a powerful report writer that allows you to quickly create .RPT files that can be called from a VDF program. You will need Crystal Reports installed to complete some of the features covered in this lesson.

Topics in this Chapter:


o o o o o Comparing the Reporting Methods BasicReport Class WinReport (WinPrint) CrystalReport Class Lab 16 Using WinPrint Report Wizard Using Crysal Report Wizard Adding a Print Button to an Entry View

Data Access Corporation

423

Lesson 16 Reporting

Discovering Visual DataFlex

Comparing the Reporting Methods


BasicReport Class This class will produce a report that is similar to the procedural Report macro. It is limited in its capabilities (formatting and fonts). It is useful to produce reports that will be printed to dot matrix printers. Since the output is limited it will not be covered in this manual, see the on-line help and the Developing Visual DataFlex Applications manual for a full description of this class.

WinReport (WinPrint) WinReport is a subclass of the BasicReport so there are many similarities to their structure. WinPrint is capable of font changes and record selection. The WinPrint Report Wizard will use this class when generating code.

CrystalReport Class CrystalReport is a class that will use a .RPT file that was created using the Crystal Report Writer software. This report writer will generate great looking reports in minimal time. Crystal is full of features such as adding bitmaps, changing fonts and color, record selection and sort order. The Crystal Report Wizard will use this class when generating code. The Crystal product can be purchased separately. Combined with the DataFlex Connectivity Kit for Crystal Reports, it can access DataFlex databases. After installation, you will be able to produce the .RPT files that the CrystalReport Class will run. Your customers will not be required to purchase the Crystal product. The .RPT files will be launched from your VDF application.

424

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

Lesson 16 Lab
Description: Creating a WinPrint and Crystal report using the report wizards.

Tasks:

Using WinPrint Report Wizard

File | New | Report [ WinPrint Report Wizard [ OK button

Figure 285

Data Access Corporation

425

Lesson 16 Lab Reporting

Discovering Visual DataFlex

Dept_Budget [ Next

Figure 286

[ Next

Figure 287

426

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

[ DEPT [ Next

Figure 288

[ Next

Figure 289

Data Access Corporation

427

Lesson 16 Lab Reporting

Discovering Visual DataFlex

[ Name [ Budget [ Company_Code [ Next

Figure 290

428

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

[ Dept.Company_Code [ Next

Figure 291

[ Index 3 [ Next

Figure 292

Data Access Corporation

429

Lesson 16 Lab Reporting

Discovering Visual DataFlex

[ Finish Button

Figure 293

Be sure your application is opened. (File | Open Program)


[ Code Explorer [ Add Component [ Reports (to expand) [ Dept_Budget.rv [ Add [ Close

Figure 294

Code Explorers Add Componet button


430 Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

Compile and run your new report

Leaving the selection criteria blank will print all records. You may wish to add more records so your report has more to print.
Figure 295

Open the report component and look over the generated code. If you look at the above Screen shot of the report You may notice a small problem with the header of Company_Code. It is missing the last e To correct this lookup the command DFWritePos and enlarge the MaxLength to 2.50

Figure 296

Data Access Corporation

431

Lesson 16 Lab Reporting

Discovering Visual DataFlex

Using Crystal Report Wizard


The wizards make creating the reports very easy. Study the code after it is generated to learn valuable coding skills. Review the reports that are available in the examples. The Order sample program has many good reports.

File | New | Report [ Crystal Report Wizard [ OK

Figure 297

[ Next button

Figure 298

432

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

[ browse () button From the workspace \data directory select the Department.RPT file [ Open [ Next button

Figure 299

enter Department Report (Crystal) [ Next button

Figure 300

Data Access Corporation

433

Lesson 16 Lab Reporting

Discovering Visual DataFlex

[ Next button

Figure 301

[ Dept [ Dept_Code [ Add button [ Next button

A user selection is not always needed. This screen can be left blank.

Figure 302

434

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

[ Next button

Figure 303

Indexed fields have a red mark on the icon. This report is grouped by Dept. Therefore, it is limited to what fields can be used to sort. The best way to determine this is to see if Crystal would allow the field as the Sort order. This is true on many of the options of the wizard.

Check all the output destinations [ Next button

Figure 304

Data Access Corporation

435

Lesson 16 Lab Reporting

Discovering Visual DataFlex

[ Finish button

Figure 305

Note: Crystal does not have to be installed on the end users machine in order to run the Crystal reports (just needed .dll files). It is necessary to have Crystal installed in order to create the reports.

436

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

Attach the report to the application. Open the application


[ Add Component button [ Reports [ Department ReportCrystal.rv [ Add Button [ Close Button Compile and Test Open the Report Component & Study the code that was generated.

Figure 306

Data Access Corporation

437

Lesson 16 Lab Reporting

Discovering Visual DataFlex

Adding a Print Button to an Entry View


This step adds a print button and procedure for the print button that will print the current record.

Open the DeptEmpl.vw Add the Print button from the Custom tab page Set the object name to oPrintButton

Figure 307

438

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

Before adding any code Notice the selected object


Open the Code_Mod.txt file in the Studio Code Explorer / the View object (dbView) to bring up the editor Cut & Paste the corresponding code into the top area Cut & Paste the corresponding code into the bottom area (below the code that is already there)

Figure 308

//------------------------------------------------------------------// Add to the top of the DeptEmpl object // This package will be needed to run the Crystal report //------------------------------------------------------------------Use CrystalReport.pkg

// Add to the bottom of the DeptEmpl object // Create Crystal report to print the current header record. // Object's access method is: Send Print_It iHeaNumber Object Single_Record_Report is a CrystalReport Property Integer piHeaderNumber 0 Property String psHeaderNumber // need two properties (ASCII & integer) Procedure onInitializeReport

Data Access Corporation

439

Lesson 16 Lab Reporting

Discovering Visual DataFlex

// set the Report titles and selection formula -- toggle the string/integer properties If ((psType_Header_Key(Self)) = "I") Begin Set ReportTitle to ("Print " * (psFileField(Self)) * (piHeaderNumber(Self))) Set SelectionFormula to ("{" + (psFileField(Self)) + "} = " + (piHeaderNumber(Self))) End Else Begin Set ReportTitle to ("Print " * (psFileField(Self)) * (psHeaderNumber(Self))) Set SelectionFormula To ("{" + (psFileField(Self)) + "} = '" + (psHeaderNumber(Self)) + "'") End End_Procedure // pass Header to print Procedure Print_It string sNum Integer iNum If ((psType_Header_Key(Self)) = "I") Begin Move sNum to iNum Set piHeaderNumber to iNum End Else Set psHeaderNumber to sNum Send Run_Report End_Procedure End_Object // print the current order. This message will be sent // by the print button Procedure PrintCurrentRecord Handle hDD Integer iNum iFieldNum String sNum sRepFileName sFileField Get Server to hDD // this will be the header_file DD If (Current_Record(hDD)) Begin // only do this if record exists Move ((psHeaderName(Self)) + ".Rpt") to sRepFileName Set Report_Name of Single_Record_Report to sRepFileName Get psFileField to sFileField Get piKeyFieldnum to iFieldNum // There is a limit here since we expect the psType_Header_Key to be an "I" or "S" (Integer/ String) If ((psType_Header_key(Self)) = "I") begin Get Field_Current_Value of hDD iFieldNum to iNum Move iNum to sNum Send Print_It to Single_Record_Report sNum End Else Begin

440

Data Access Corporation

Discovering Visual DataFlex


Get Field_Current_Value of hDD iFieldNum to sNum Send Print_It to Single_Record_Report sNum End End End_Procedure // Dynamically set the label Procedure Activating String sLabel_it Move ((psHeaderName(Self)) + " Entry View") to sLabel_it Set Label to sLabel_it End_Procedure

Lesson 16 Lab Reporting

Data Access Corporation

441

Lesson 16 Lab Reporting

Discovering Visual DataFlex

This step will shadow the Print button so it will not be available if there is no record to print.

From the Code_Mod.txt file, Highlight & Cut the appropriate code (shown below) / the First Object to bring up the editor Paste code in the bottom area

//------------------------------------------------------------------// Add to the bottom area of the Dept.Dept_Code dbForm // We want to disable the print button if there is no current record. // The DD notifies all DEOs of any record change. // We can augment any DEO's refresh message to see if a current // record exists and set the Enabled_State of print button accordingly. //------------------------------------------------------------------Procedure Refresh Integer iMode Integer iRec Forward Send Refresh iMode // if record exists, enable the print button. Get Current_Record of (Server(Self)) to iRec Set Enabled_State of oPrintButton to (iRec>0) //(iRec>0)evaluates to True/False End_Procedure

442

Data Access Corporation

Discovering Visual DataFlex

Lesson 16 Lab Reporting

This step will add the OnClick procedure to the print button.

From the Code_Mod.txt file, Highlight & Cut the appropriate code (shown below) / the button object to bring up the editor Paste code in the bottom area. Paste over the existing procedure Compile and Test (Remember the button will be shadowed until a record is found)

Fi

310

// Added to the bottom of the oPrintButton Procedure OnClick Delegate Send PrintCurrentRecord // defined in view object End_Procedure

Data Access Corporation

443

Lesson 16 Lab Reporting

Discovering Visual DataFlex

Did You Discover?

1. Can you print the selection range in the header of a Crystal report?

Workshop Project: If time permits and you need a challenge - add the code that would create a Wk_Sum record whenever a TimeCard record is saved/deleted.

444

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Appendix A
Did you Discover Answers

Data Access Corporation

445

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 1 - Discover Answers


1. Which Appendix in this manual has more basic information on the DataFlex language?

Answer: Appendix C. New DataFlex Users Procedural Programmers Appendix C DataFlex Core Information Appendix C OOP Core Information

DOS Object Oriented Programmers Appendix C OOP Core Information Prior VDF Users Appendix C Prior VDF Users

2. Create names for the following items:

Sample Name A Local Boolean Variable A Local Integer Variable A Global Integer Variable A Global String Variable A Class An Object An Integer Property A String Property A Variant Property A Constant A Local Integer Variable (used to hold an object ID) bVar iVar giVar gsVar cMyEdit oMyEdit piMyProperty psMyProperty pvMyProperty C_MyCounter hoObjID

446

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 2 - Discover Answers


1. Printed in this lesson was a DEF for the TimeCard file that shows its file structure. Without modifications to the TimeCard file can it have a child file attached to it? Why or Why not? (look in the Appendix C for relationship rules for help)

Answer No. One of the rules for relationships is that the parent file must be uniquely indexed. Since there are no unique indexes this file cannot be a parent file, with a child file relating to it.

2. The lock in the upper right corner must be green to make changes to the first three tab pages. When opening a file it always comes up in red - Is there a way to default it to green?

Answer: Yes, within DDB the File menu, Configure option and Database Builder tab page there is a checkbox for Open tables in normal mode. Normal mode is when the lock is red (non-exclusive rights to the database). Uncheck the option for Exclusive (exclusive lock on the database) showing a green light for database changes.

3. When adding a new field in Database Builder, are the Add and Insert buttons required to add a new field?

Answer: No, you can simply type directly into a blank field row. The Insert button will allow you to insert a field between existing fields and the Add button will jump you to bottom of the grid on the first blank row.

4. When loading a complete file structure (with many relationships) into a new Filelist.CFG, is it important to load the .DEF files in any special file number position? Why?
Data Access Corporation 447

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Answer: Yes, This is because of file relationships if the child is pointing to file 4 and you change the parents position in filelist to 9 the file relationship will not be loaded correctly. Therefore you will have to load the files in the same file number position. It is also recommended to add parent files before child files so the parent file number is created before the child attempts to relate to the file number.

5. Write down 3 different ways to open a database file in DDB. (open, not create) Answer: From the menu, select File|Open From the combo box Open As

6. What is End User Mode and how do you set up Database Builder in End User Mode? (hint look this up in the on-line help under the index tab)

Answer: In this mode, Database Builder cannot modify any file structures, indexes, or Data Dictionarys. You can only print file status reports and access the file-maintenance options. End User Mode allows your application users to access functions such as re-indexing, repair data, and other maintenance functions. Users will be locked out of all other functions. To place Database Builder in End User Mode, set the windows registry setting of VDF Default tag dbAdminMode variable as follows: dbAdminMode = OFF

448

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 3 - Discover Answers


1. What happens if you enter a 2-digit year into a date window such as Term Date?

Answer: The year will automatically change to a 4-digit year!

2. What is Epoch and what has it to do with entering dates in a VDF application? Answer: EPOCH_VALUE sets the two-digit year value equal or above which dates are considered to be in the 1900s and below which dates are considered to be in the 2000s. The Set_Date_Attribute and Epoch_Value determines if it will add 1900 or 2000 to a year that was entered as two digit. This setting can be changed easily in the code created in the Studio. Open a program, and look at the code in the Program Code area. The default setting can be changed from the Tools | Configure Environment menu in the General tab page.

3. Predict and check the results of entering the following dates, with Epoch turned on and set to 30? 01/01/00 06/20/52 12/25/30

Answer: They are automatically converted based on the epoch setting selected. 01/01/2000 06/20/1952 12/25/1930

Data Access Corporation

449

Appendix A Did you Discover Answers

Discovering Visual DataFlex

4. What would happen to the tab dialogs if the dialog box was not big enough to hold all three tabs? (add more tabs or shorten the tab dialog box to find out)

Answer: The tab pages will wrap. There are properties (like Tabwidth_Mode and Mutliline_State) that can alter tabs.

5. What would happen if you shortened the length of the last name window so that the entire last name entered wouldnt fit in the window?

Answer: It will scroll to fit as many characters as the length of the data field.

6. Run the program, and type in a last name of WWWWWWWWWW (type capital Ws until you reach the limit (which is the length of the field). Notice that it had to scroll to the right. Clear with the F5 key, and type in a last name of iiiiiiiiii (all small letters is to the limit). How do you determine what the size of a control should be?

Answer: Window applications can alter fonts styles which makes this difficult. Plus the fact that you do not know that will be entered (all W or i letters). The Studio will create a size by default that is a very good estimate for the correct size of a control based on the current typeface. If you know what the value of a control and need to alter the size at runtime, use the Text_Extent property. Below is a sample of this.
Procedure Activating Forward Send Activating Send AutoSize "WWWWWWWWWWWWWWWWWWWW" End_Procedure Procedure Autosize String Val Integer iExt iHt iWd Get Text_Extent Val To iExt Move (hi(ext)) to iHt Move (low(ext)) to iWd

450

Data Access Corporation

Discovering Visual DataFlex


Set Guisize To (iHt+3) (iWd+2) Send Adjust_Logicals End_Procedure

Appendix A Did you Discover Answers

7. When using the Object-Order Definition tool, is it important where Textbox objects are listed? Answer: No, they are non-focusable controls so they have no affect in the view navigation.

8. Run our program, and open up the Employee Entry View. Find a Record, then place the cursor on the parent window (Dept) and press Shift+F2 to delete. Wait! What is going to be deleted? The Department or the Employee? Why? Answer: Remember that the Accelerator keys send messages (in this case Request_Delete). The message will travel by delegation to the dbView, and then (because the dbView has it's server set to the Main_DD) the Request_Delete message travels to the Empl_DD. Then, since deletes travel downwards (in the DDO tree), the Employee record is deleted - Not the Dept. You cannot delete a parent record in most VDF programs unless the programmer explicitly codes it.

Data Access Corporation

451

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 4 - Discover Answers


1. What is the normal behavior of the Shift+F10 if the Append_a_Row procedure was not available?

Answer: Normal behavior for the On_Key kAdd_Mode (which is what Shift+F10 sends) is to insert a blank line in the grid where the cursor is located. Our view made the Add-Mode key send the Append_A_Row that jumps us to the end of the table, and then down one row (Append_A_Row procedure).

2. In the DataFlex language, how do you continue a command line to the next line? Answer: Using the semicolon ; will allow you to continue a command to the next line.

3. Within the DeptEmpl View, go to the grid and enter some test data, but do not save with the F2 key. . . click on a window in the header . . . can you exit the line item without a save occurring? What if you use the down arrow or up arrow? Does the save occur?

Answer: Earlier, we set the Child_Table_State of the dbGrid to true. This enforces a save operation before navigation outside the current line is allowed.

4. When the Studio generates the code for an Object the Green Line in the Code Editor will be replace with what?

452

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Answer: With all the Objects properties set in the Object Properties Tool for this object and any nested objects contained by this object.

5. When you find a Department record (in the header section), only the employees for that Department are found and displayed. How does the program know to show only related records in the dbGrid?

Answer: With the Studio running and the DeptEmpl View open, click on the Database Selector icon, and choose DDO Tree. Click the + sign next to EMPL_DD and take note of the settings . . . The DDO_Server means Empl is related to Dept but it is the Constrain file that will only allow related records to be displayed (a filter).

6. Create a new view with two dbForm controls, one showing the Empl.Code and the other one showing the Empl.Last_Name. Make the dbForm for the Empl.Code control using the Database Selector. Make the dbForm for the Empl.Last_Name using the Controls Palette. When you compile and run your new view did both of your controls show data when you find records? What extra step do you have to do with the Controls Palette when creating data-aware controls? Answer: If you are using the Database Selector the connection to the File.Field is already made. If you use the Controls Palette to make Data-aware controls you will have to use the Object Properties dialog (Database tab) and connect to the file.field.

Data Access Corporation

453

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 5 - Discover Answers

1. Where in the Studio and Database Builder will a right-mouse-click call up a popup menu? Answer: The Right Click popup menu is available from almost every entry control in each dialog in Database Builder & the Studio. These menus are helpful for many things including cutting and pasting.

2. What are the advantages of validation tables over creating a parent related file? Answer: Fewer database tables are needed (with the static option there are no database tables used). Database Builder makes the creation and updating of validation tables very easy.

3. What are the advantages of a parent related file over a validation table. Answer: Advantage: Accessing the data for reports can sometimes be easier. Ex:In Crystal Reports, it would be easier to access the data when it is in a related parent file. Disadvantage: A related file would require its own separate file. Data in Validation Tables can be combined into a single file.

454

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 6 - Discover Answers

1. When using the magic wand button in the Structures tab page of Database Builder will it remove unneeded files from the required Child/Parent list? Answer: No! It will only add to the list it will not remove extra files that are already listed that is why it is important to remove all files before using the button. The Magic Wand Button will add to the list any Required Child and Required Parent files that match the file relationships that are not already in the list.

2. What is the difference between the Validation Error No. & Text on the Field Setting | Validation/Lookup Tab and Validation Error No. & Text on the Options tab? Answer: The setting on the Field Setting | Validation/Lookup Tab is only for one field. The setting on the Options Tab creates a Field_Error property where ifield is set to -1, which will then apply this error setting to every field in the file, applying this Error and Text to all fields that are not individually set.

3. In Database Builder under the METHODS tab if you select a method from the Unaugmented list what happens to the Unaugmented and Implemented lists? Answer: The selected method is removed from the Unaugmented list and added to the Impliemented list. A timer event fires and updates both lists.

Data Access Corporation

455

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 7 - Discover Answers


1. If you want two views to always display the same records from the database tables, you should? Answer: Combine the views into one so they both use the same DataDictionarys. Views should operate independent of each other.

456

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 8 - Discover Answers


1. Open any Lookup List (Selection List - SL file) in an editor. The code begins with CD_Popup_Object. What does the CD stand for? Example Code:
CD_Popup_Object Empl_SL is a dbModalPanel

Answer: CD means Create/Destroy. Selection lists are created only when they are poped up and destroyed upon exiting. This is done to speed in application load time. In a program, which contains many selection lists, this lets the program quickly load into memory when it starts. Note: Views are not CD-type objects. Views use a Deferred_View command. This will create the view when first activated, but does not destroy them upon exiting.

2. If you look in the properties of the selection list, the Ordering property (which index to use) is set to zero. Why is that?

Answer: Selection lists automatically re-sort themselves based on the field (column) that has the focus.

3. After the constraint in the Employee View is added, can you save an employee that has a termination date greater than zero? Answer: Yes, you can save an employee with a termination date but after it is saved you will not be able to bring the record up in the view again. Constrains only affect the finding and displaying of records.

Data Access Corporation

457

Appendix A Did you Discover Answers

Discovering Visual DataFlex

4. How could you make the Selection List use the same DataDictionary constraints as the invoking view? (without copying or moving the OnConstrain code from one to the other) Answer: The Auto_Server_State property is exposed in the Studio from the Object Properties dialog. If you set this property to True in your Lookup it will use the DataDictionary of the invoking view and be identically constrained.

458

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 9 - Discover Answers


1. Do properties forward and delegate like procedures and functions?

Answer: Yes

2. If I cancel the Request_Clear procedure in a container object that contains many dbForm objects will it affect the Request_Save? Answer: Yes, the Request_Save cascades many messages one of them is the Request_Clear message so now when you save it will not clear.

3. What would happened if Forward Send Creating was listed before the Move command in TimeCard DD objects Creating procedure we just added in the lab? Here is the code:
Procedure Creating // Since the TimeCard.In_or_Out is only one character long // the psInOut property value will be truncated Move (Uppercase(psInOut(Self))) to TimeCard.In_or_Out Forward Send Creating End_Procedure

Answer: The Empl.Logged field would be blank. Why . . . If you have a Creating procedure in the DDO of the view and a Creating procedure in the .DD file, Both will be executed if the DDO does a Forward send Creating. Looking at the DataDictionary Creating procedure it Move TimeCard.In_or_Out to Empl.Logged this means if the Forward Send Creating is done first there would be nothing in the TimeCard.In_or_Out field to move to the Empl.Logged field.

Data Access Corporation

459

Appendix A Did you Discover Answers

Discovering Visual DataFlex

4. Look in the WinHelp to find the names of the other Accelerator-Keys. Answer: Select the Search key and type Accelerator then select Accelerator KeyMessage and Assignments of the Accelerator-Key-Message-Names.

5. Name as many ways as you can to make a procedure execute. Answer: Commands: Send Forward Send Delegate Send Broadcast Send On_Key ( and predefined Accelerator keys) Classes: (many classes can send messages) Buttons Radios List Events: Timers (will cover in the next lesson) Keyboard (as we type) Mouse

460

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

6. Create a new view with a grid displaying the Empl.Code; Empl.Last_Name and Empl.Term_Date fields. Use the RadioGroup Class to set up a dynamic constraint to show: All Employees Terminated Employees Active Employees
// This would be added to the Empl_DD object Property integer piConstrainVal 0 Procedure OnConstrain Integer iConVal Get piConstrainVal to iConVal If (iConVal = 1) Constrain Empl.Term_Date GT 0 If (iConVal = 2) Constrain Empl.Term_Date EQ 0 End_Procedure

// This would be added to the Empl View built with the Studio. Object RadioGroup1 is a RadioGroup Set Label to "Change Constraints:" Set Size to 39 56 Set Location to 3 7 Set Current_Radio to 0 Object Radio1 is a Radio Set Label to "All Empl Set Size to 10 39 Set Location to 11 5 End_Object // Radio1

Object Radio2 is a Radio Set Label to "Terminated Employees" Set Size to 10 37 Set Location to 24 5 End_Object // Radio2

Object Radio3 is a Radio

Data Access Corporation

461

Appendix A Did you Discover Answers


Set Label to "Active Employees" Set Size to 10 37 Set Location to 24 5 End_Object // Radio2

Discovering Visual DataFlex

Procedure Notify_Select_State Integer iToItem integer iFromItem Forward Send Notify_Select_State iToItem iFromItem Set piConstrainVal of Empl_DD to iToItem Send Rebuild_Constraints of Empl_DD Send Beginning_of_Data to oEmpl_Grid End_Procedure End_Object // RadioGroup1

462

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 10 - Discover Answers


1. The lesson mentioned dbEdit as a multi-item class. Name a few other classes that are multi-item. Answer: Grid/dbGrid List/dbList Edit/dbEdit

2. What information can you get by clicking on "Help/About..." of a running VDF application? Answer: You can see how much memory is being used by the current applications. Note: You can customize your own about package: see DFAbout.Pkg

Data Access Corporation

463

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 11 - Discover Answers


1. What does the Z compiler option do? Answer: It will compile using the debug packages. This will allow you to use the debugger with your running application.

2. What does the S compiler option do? Answer: Compiling your code with the s symbol option will help in debugging. This option will create a larger compiled file because it creates a symbol table in the .EXE file. Now instead of a runtime error message that just has the message number it will give the message name.

Without the -s option: With the -s option:

Invalid message MSG_#### Invalid Message MSG_Print_Label

3. If your users launch 3-4 copies of this program at the same time, how much memory will it use up? Answer: About 2% of system recourses for each copy: not very much! (VDF uses very few system resources).

464

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 12 - Discover Answers


1. Can you make the TC_In view automatically display when the program is executed? Answer: Open the CorporationX Application.Src program to see how it activates each view. Copy the activate message. Open the Studio to the Program/Code dialog and paste the command in just before the line "Start_UI".

2. How can you create an icon on the desktop to automatically run this application? Answer: Open the Window Explorer and Drag the compiled .EXE program to the desktop This will create a shortcut to the program.

3. After completing this lab, will you have to copy the CorpLogo.BMP when deploying your application? What would you suggest be done? Answer: Yes you would have to copy the CorpLogo.BMP file when deploying the application because we did not list the new file in the CorporationX.cfg. To correct this we would add the file via the Program |Properites dialog and then recompile.

Data Access Corporation

465

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 13 - Discover Answers


1. In the lab, we sent the Adjust_Running_Empl_Total message from the Update and Backout procedures. We are only adding one or/and subtracting one employee to the Dept.Number_of_Empl field. Creating is only called on a New save and Deleting is only called on a Deletion of the Empl Record. Could Creating and Deleting procedures been used instead? Answer: No, At first it would look like it is working because the adding and deleting of employees would keep the running count correct but if we change an employee from one dept to another the running totals would not be correct on this edit save, resulting in both dept totals being incorrect.

2. Can you write a business rule so that a company must have a "NAME" (must not be blank?) Answer: Augment Validate_Save in the Company Data Dictionary to make sure the field is not blank or simply set the field option to REQ.

3. Can you write a business rule so that a company record can never be deleted? Answer: If you always use DataDictionarys, you can set the No_Delete_State property to true or augment Validate_Delete of the Company Data Dictionary so that it always returns a value of 1(so the delete will fail). It could also give a message to the customer that tells them what is happening. This will not stop manual deletes that do not use DataDictionarys.

466

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

4. In the Dept Backout and Update, we do not explicitly say "Save Company". When you delete or save a Dept record does the Company total balance get updated and saved? Why?

Answer: Yes, it will be saved. In the view, the "tree" of connected Data Dictionarys makes this happen. The SAVE message propagates up from the main-dd, saving all parent files. The Delete message will propagate downward in the DataDictionary structure, deleting all child records, and then deleting itSelf (as long as the Cascade_Delete_State is true). A SAVE is then sent upwards, saving all the parent files which will save all updates (running totals) to the parent records.

Data Access Corporation

467

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 14 - Discover Answers


1. Why create Subclasses? Answer: To create new tools which will speed development, enforce business rules and to maintain consistency throughout the program.

2. A few classes listed in the Maintain Class-List have the Image and Page columns empty. Why? Answer: These are classes that the Studio will not allow you to drag and drop (such as a DataDictionary) from the Controls Palette tool. Therefore they will not need an image or be listed under any of the Palette Pages.

3. In many lessons, we have discussed ways that make developing faster and easier. Can you name the files extensions that are created to speed development? Answer: TPV - Template Views TPL Template Lookups TPD Template Dialogs TPR Template Reports DFS - DatFlex SubComponents DFO - DataFlex Object Preferences DFC - DataFlex Classes for the Studio PKG - Package Files storing Classes and support code A full description of these files is listed on the next few pages. They can be stored Global or Locally: (local) workspace name\IdeSrc\filename (global) VDF 9.1\\usr\global\IdeSrc\filename

468

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Files that speed Studio development: Template Views can be reused to speed development TPV - Template Views TPL Template Lookups TPD Template Dialogs TPR Template Reports Loaded by: File | New Component Saved by: File | Save as Template DFS Files: DatFlex SubComponents Loaded by: Component | Insert object SubComponent Saved by: Component | Save object SubComponent

More Information/Sample // Entire template view //Lab #4 did this creating the Hdr_Grid.TPV

//AB/ SUBCOMPONENT Object Setup is a Button Set Label to "Printer Setup" Set Location to 63 122 //AB-StoreStart Procedure OnClick Integer iReportObj Get Report_Object_ID To iReportObj Send DFPrintSetup To iReportObj End_Procedure //AB-StoreEnd End_Object // Setup //AB/ OBJECTDEF Object oButton is a Button //AB-StoreStart Procedure OnClick End_Procedure // OnClick //AB-StoreEnd End_Object

DFO Files: DataFlex Object Preferences Used to add extra code into the Studio created object. The sample to the right will add the Procedure OnClick to the object so it will not have to be entered.

Data Access Corporation

469

Appendix A Did you Discover Answers

Discovering Visual DataFlex

DFC Files: DataFlex Classes To add your subclass to the Controls Palette takes 3 steps 1. Create your subclass package .pkg 2. Create the .DFC file 3. Copy the required 24X24 bitmap used by the Controls Palette to the \bitmap area. Add the subclass to the Maintain Class-List under the Tools pull-down. PKG Files: Package Files storing Classes

//AB/ CLASSDEF Class Button IS A AbstractControl Button ; ABMetaButtonMixin ; DefineABMetaButtonMixin // inherit is removed on purpose Property String Label Property NO_EXECUTE Boolean ; Default_State False Property String Bitmap Property Complex Size 14 50 Property Complex Location 0 0 Property String Status_Help End_Class // saved in a MyButton.pkg file Class cMyButton is a Button Procedure Construct_Object Set Size to 30 30 End_Procedure End_Class

4. In an earlier lesson, an Invoice_Style template was created in the Global area. What would have to be done to remove this global template? Answer: File | New Component select the template and press delete button. Or you can go to the \VDF 9.1\User\Global\IDESrc directory and directly delete the Invoice_Style.tpv file

470

Data Access Corporation

Discovering Visual DataFlex

Appendix A Did you Discover Answers

Lesson 15 - Discover Answers


1. Will the Business process still work if you remove the DoProcess Procedure?

Answer: Yes, DoProcess simply supplies the progress line, the main process is done in the OnProcess event.

2. Can you still use procedural Code instead of BPO to process records?

Answer: Yes, you can still do any of the procedural loops or For_All methods BUT they do not use DataDictionarys so your business rules are not being followed. This is why BPOs are the suggested method. In our lab was an example of when DataDictionarys could not be used because we were correcting the relationship field between two files after a newly created relationship was created.

Data Access Corporation

471

Appendix A Did you Discover Answers

Discovering Visual DataFlex

Lesson 16 - Discover Answers


1. Can you print the selection range in the header of a Crystal report?

Answer: Yes you can. In Crystal Reports, create a Parameter. A parameter will prompt the user for information used in running the report. For example, you can create a date parameter that asks the user for a date at runtime, such as invoice date > 1/1/2002 for all this years sales. When you create the selection formula within Crystal Reports, you can choose invoice date > (?parameter name). The parameter name will appear on the dropdown browse list with a ? in front of the name. Then create a text field in the report header and insert that parameter in the test field. This will print whatever selection entered as the parameter. If you don't want the user to enter a parameter, just set the default amount to be whatever you want it to be when you set the parameter up. If you need more info, check the Crystal Reports manual.

472

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Appendix B
Problems & Solutions

Data Access Corporation

473

Appendix B Problems & Solutions

Discovering Visual DataFlex

Popup Messages/Questions
Problem: What is the quickest way to ask a yes/no question?

Solution: If you are simply asking a Yes/No question use the Confirm function found in dfconfirm.pkg:

Get Confirm Do you wish to Continue? to RetVal

Figure 311

Other popup boxes are Info_Box and Stop_Box (both in the Msgbox.pkg).

Figure 312

The YesNoCancel_Box is also available.

Figure 313

Figure 314

Send Info_Box "You do not have rights to this area!" Send Stop_Box It is strongly suggested you \n create a backup before continuing Get YesNoCancel_Box Do you wish to save the current setup profile?" to iRetVal

474

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

On_Key {to object} parameter


Problem: I sometimes have problems using the {of object} parameter with the On_Key command. Solution: The command is evaluated at Compile time, NOT runtime. Therefore the receiving object MUST already be created (adding a Register_Object command will not solve the problem).

Syntax:

On_Key keyname send message {of object} {private}

Workarounds: 1. Move the On_Key command to the bottom of the view so the object is already constructed.

On_Key Key_Alt+Key_T send Do_It of Customer_Form

2. Create a dummy message that then sends the message


On_Key Key_Alt+Key_T send Dummy Procedure Dummy Send Do_It of Customer_Form End_Procedure

Data Access Corporation

475

Appendix B Problems & Solutions

Discovering Visual DataFlex

Auto Activate First View


Problem: I have one view that is the main view. Is it possible to have it activate whenever the application starts?

Solution: To auto-activate, a view you should:

1. Find the activate access method for the desired view (looking at the mainprogram.SRC file will show how it activates the views). For example, the access method for a Customer_Entry view would most likely be Activate_Customer_Entry. 2. Add the following line to the end of your program right before the Start_UI command. You may add this code within the Studio by editing the bottom-code area of your program.

Send Activate_oCustomerView of (Client_Area(Main))

This assumes that your main program has been created by the Studio and the main outer panel objects name is Main and its child client-area objects name is Client_Area. You can auto-activate as many views as you wish using this method. The last view activated will be the view that takes the focus.

476

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

ToolTip
Problem Can I set a ToolTip_Value on my buttons to explain when to use them?

Solution: At the present time you would have to create your own classes to do this. - but future versions of VDF may support this.

Data Access Corporation

477

Appendix B Problems & Solutions

Discovering Visual DataFlex

Multiple directories in a Path


Problem: The Initial_Folder property can only contain one directory, but my bitmap path contains multiple directories. How can I strip the first directory path from a bitmap path that contains many directories?

Solution: This sample will allow you to set the initial folder to the first listed directory that is listed in the bitmap path. If the directory you wish is not the first one then PathAtIndex function of the cWorkspace object can help filter out the N-th path.

Procedure Activating Integer hoWorkspace String sBitmapPath Get phoWorkspace of ghoApplication to hoWorkspace Get psBitmapPath of hoWorkspace To sBitmapPath Get PathAtIndex of hoWorkspace sBitmapPath 1 To sBitmapPath Set Initial_Folder To sBitmapPath Forward Send Activating End_Procedure // Activating // Take the first path entry

478

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Checking filename is only 15 Characters


Problem: The bitmap filename needs to be limited to 15 characters to function correctly. How do I limit the user from selecting a file with more than 15 characters?

Solution: This sample ensures that the bitmap filename entered is limited to 15 characters.
Function Select_Bitmap Returns String String sBitmapFileName Integer iFieldLength iFileNameLength iField Forward Get Select_Bitmap To sBitmapFileName Get_Fieldnumber Empl.Picture_id To iField Get_Attribute DF_FIELD_LENGTH Of Empl.File_Number iField To iFieldLength Move (Length(sBitmapFileName)) To iFileNameLength If (iFieldLength < iFileNameLength) Begin Error 130 ("Filename '" + sBitmapFileName + "' too long (size=" + ; String(iFileNameLength) + ") for picture field (max=" + ; String(iFieldLength) + ; ")\nFilename and therefore selection will not be used!") Move "" To sBitmapFileName End Function_Return sBitmapFileName End_Function // Select_Bitmap

Data Access Corporation

479

Appendix B Problems & Solutions

Discovering Visual DataFlex

Procedure Set
Problem Why do some procedures act like a property?

Solution: This is because they have been created as a procedure set instead of simply a procedure. Procedure set is a short cut it builds a property and procedure in one. So when you set the property it also calls a procedure at the same time. Here is an example:
Procedure Set Item_Options_DisplayOnly integer item# integer state // two things were passed the item# which in our case T_Date## =1 // and state which is Crnt (true if non_zero & false if 0) Set Item_Option Item Item# to NoPut state Set Item_Option Item Item# to NoEnter state End_Procedure // if transaction header exist, disallow entry in date window Procedure Refresh integer iMode Integer iSrvr iCrnt Get Server to iSrvr // get the data_set // get record in data_set | | | -------------------------------------------| Get Current_Record of iSrvr to iCrnt // DispalyOnly = Noput & NoEnter // Date## has already been defined by entry_name_item Set Item_Options_DisplayOnly T_Date## iCrnt Forward Send Refresh iMode // Dont leave us sitting on a DisplayOnly Window If ((iCrnt and (Current_Item (Self) = T_Date##) Send Next End_Procedure // do normal refresh ----------| | | | | | | | | | | |

// Set DisplayOnly to iCrnt (is true if non_zero

When I was learning OOP and using the old OOP Reference manual I was always looking at the beginning of this book at the property chart and then finding what I was looking for was under the procedure chart as a procedure set. Take a look at these charts in the old manual, you will find lots of procedure sets! Or look in the on-line help.

480

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Retrieving data from the Windows Registry


Problem: How do I check the values in the windows registry?

Solution: This sample will create a file called environ.txt and put the value data of .doc found in Windows Registry. [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Extensi ons] in a text file called environ.txt. This is normally not needed! Windows registry setting should really be altered within an interface program like the one found from within
use windows // In previous revisions of DataFlex (3.05x), the command Get_Foreign_Profile_String returned values from .INI files. // Visual DataFlex uses the same command but now retrieves values from the windows registry. // The Get_Foreign_ProfileString will copy values from the registry (regedit.exe). This is similar to Export // Registry File from the registry pull down. It will provide all parameter values. Care must be taken when // parsing the string into acceptable arguments. Incorrect values that are NOT found will return a null string // not an error. This command will NOT change any registry settings. To change settings use the Set_Foreign_Profile_String command. // [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Extensions] string sValData sRegPath sKey sValueName // Must set the registry root to first two branches. set_registry_root to HKEY_LOCAL_MACHINE 'Software' // Include as arguments : path to registry key, key, value name to return value data move 'Microsoft\Windows\CurrentVersion' to sRegPath move 'Extensions' move '.doc' to sValueName get_foreign_profile_string sRegPath sKey sValueName to sValData direct_output 'environ.txt' writeln '.doc value is ' sValData close_output to sKey

Data Access Corporation

481

Appendix B Problems & Solutions

Discovering Visual DataFlex

Deployment
Problem: How do I deploy my application?

Solution: There is a white paper that explains the deploying of VDF applications. You can download it from our web site at http://www.dataaccess.com/.

482

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Saving Resources:
Problem: I have a fairly large application and to make different views look a little different I started adding lots of fonts my application is now running much slower.

Solution: Changing colors does not use up your resources, so do this freely. Changing fonts; font styles (bold/italics) or sizes uses up resources FAST, so do this very sparingly.

Data Access Corporation

483

Appendix B Problems & Solutions

Discovering Visual DataFlex

Customizing error messages:


Class GL_Accts_Data_Set is a Data_Set Procedure Construct_Object integer img# Forward Send Construct_Object img# Set Main_File to GL_Accts.File_Number : Property string Old_Key_ID 0 : End_Procedure // This procedure is called whenever a new record is found Procedure New_Current_Record integer iOldRec# integer iNewRec# Forward Send New_Current_Record iOldRec# iNewRec# Set Old_Key_ID to MyFile.Key_Field End_Procedure // This procedure is called whenever a record is saved Function Validate_Save returns integer String sOldID // Integer iRec# iRetVal Get Current_Record to iRec# Get Old_Key_ID to sOldID // this is our new property! // If an edit (existing record) and the key changed dont save If (iRec# <> 0 and Myfile.Key_Field <> sOldID) Begin Send Operation_Not_Allowed 301 Function_Return 1 End Forward Get Validate_Save to iRetVal If (iRetVal) Function_Return 1 End_Function // augmented for customized error messages (errors generated from the DS) Procedure Operation_Not_Allowed integer iErr# If (iErr# = 301) Error iErr# Cannot change a GL number Else (If iErr# = 4140) Error iErr# Cannot Delete Account has child records Else Forward Send Operation_Not_Allowed iErr# End_Procedure // custom error message

484

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Adding your own Utilities


Adding an external program to the Utility pull-down will make accessing it easy from within the Studio.

Utilities | Configure Utilities [ Add button If you have an external program add it to the right side of the dialog otherwise press cancel

Figure 315

Adding a SEPARATOR will insert a line in the pull-down.

When entering the command line use the browse button to find the program to run. When typing in the command line use quotes around the entered data so directory names containing spaces will not be confused with command line partameters.

Data Access Corporation

485

Appendix B Problems & Solutions

Discovering Visual DataFlex

Maintain Class-Lists
The last item on the tool pull-down allows us to add or edit subclasses (tools) that the Studio will use.

The order of the tab pages in the Controls Palette can be altered by changing the order of the classes in the Maintain Class List tool.
Figure 316

The Global tab page lists classes the Studio will use in all workspaces. The Workspace tab page lists classes used only in the current workspace. Each time you change workspaces the Studio rereads this file.

If the Page column has an entry the Studio will add the class in the Controls Palette tool. The order of the Controls Palette tab pages are determined by the order in the list. If you add a new page name a tab page will be created with that name. In this example the tab pages would be listed Base; Data; Base Containers; and Data Containers. The controls listed under the tab

Figure 317

pages will also be in the order found in the Class-List.

486

Data Access Corporation

Discovering Visual DataFlex

Appendix B Problems & Solutions

Field_Default_Value Property
This property is used to set defaults. Field_Entry_msg procedures (described later) and Field_Defaults procedures (described below) are the most common places the Field_Default_Value property is used. This example is from the OrderHea DataDictionary of the Order Sample.

Procedure Field_Defaults is available from the Method Tab.

Figure 318

Note (prior OOP programmers) This procedure is similar to the Entry_Defaults procedure in the DEOs.

The Field_Defaults procedure sets the field value without setting the DSOs Changed_State. This will allow the default to show in grids without creating unwanted records in the database upon entering and exiting a blank row.
Class OrderHea_DataDictionary is a DataDictionary Procedure Field_Defaults Forward Send Field_Defaults Date dDate SysDate dDate Set Field_Default_Value Field Orderhea.Date to dDate Set Field_Default_Value Field Orderhea.Terms to CASH End_Procedure //Field_Defaults

Data Access Corporation

487

Discovering Visual DataFlex

Appendix C Core Information

Appendix C
Core Information

Data Access Corporation

489

Appendix C Core Information

Discovering Visual DataFlex

Accelerator Keys
Function Key 1 2 3 4 5 6 7 8 9 0 R F Z X l r t b s B h e 490 Function Key S+ Function Key Help Save Record Exit Function Prompt Clear Panel Switch to Next Area Find Previous Find Next Find Switch to Action Bar Accept Next item Insert/Overtype Toggle Delete Character Cursor Left Cursor Right Cursor Up Cursor Down Selection Toggle Destructive Backspace Beginning of Line End of Line Erase to End of Line Beginning of Data End of Data Data Access Corporation Non-WP Bksp Skip Word Left Skip Word Right Beginning of Panel End of Panel Previous item Print Screen Refresh Screen Switch to Prev.Area Superfind Previous Superfind Next Superfind Add Mode on/off * Clear and Return Zoom Clear all Panels Switch Prev. Panel * Delete Record Trace Mode * C+ Function Key A+ Function Key User Key 1 User Key 2 Trace on/off * Exit Application Calculate Switch Next Panel *

Discovering Visual DataFlex Function Key u d E / + Copy Function Key S+ Function Key Scroll Page Up Scroll Page Down Cancel Mark

Appendix C Core Information C+ Function Key Scroll Page Left Scroll Page Right A+ Function Key

Paste Cut

* = Defined only in Data Access packages see package documentation

Data Access Corporation

491

Appendix C Core Information

Discovering Visual DataFlex

Studio Hot Keys


Feature Toggle between Visual Designer and Component Explorer Toggle between Outline and Full Source in Component Explorer Find in Files Database Selector Object Properties Controls Palette Alignment Palette Arrange Object Nudge Objects Drag Lock Open Component New Component Print Save Help CLIPBOARD Undo Cut Copy Paste Delete COMPILE & RUN Compile and debug-run program Debug-run program Compile and debug-run component Compile
492

Hot Key F12 F11 Ctrl + 1 Ctrl + 2 Ctrl + 3 Ctrl + 4 Ctrl + 5 Ctrl + 6 Ctrl + 7 Ctrl + L Ctrl + O Ctrl + N Ctrl + P Ctrl + S F1 Ctrl + Z Ctrl + X Ctrl + C Ctrl + V Del F7 F8 F9 Ctrl + F7
Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Run EDITOR Code-List Code-Expand Next Insertion Point Match parenthesis Goto line Next ToDo item Uppercase Lowercase Toggle comments Indent Outdent Toggle Whitespace Delete Line Select Line Find Find again Replace Context Help Toggle Bookmark Previous Bookmark Next Bookmark Properties Record Macro Redo Set Repeat Count Toggle Overtype Line Open Above
Data Access Corporation

Ctrl + F8 Ctrl + Space Ctrl + J Ctrl + I Ctrl + ] Ctrl + G Ctrl + T Ctrl + Shift + U Ctrl + U Ctrl + / Tab Shift + Tab Ctrl + Alt + T Ctrl + Y Ctrl + Alt + F8 Ctrl + F F3 Ctrl + Alt + F3 Ctrl + F1 Ctrl + F2 Shift + F2 F2 Alt + Enter Control + Shift + R Control + A Control + R Insert Control + Shift + N
493

Appendix C Core Information

Discovering Visual DataFlex

Sentence Cut Sentence Left Sentence Right Window Scroll Down Window Scroll Left Window Scroll Right Window Scroll Up Word Delete-To-End Word Delete-To-Start Word Left Word Left-Extend Word Right Word Right-Extend Document End Document End-Extend Document Start Document Start-Extend Home Extend Line End-Extend

Control + Alt + K Control + Alt + Left Control + Alt + Right Control + Up Control + PageUp Control + PageDown Control + Down Control + Delete Control + Backspace Control + Left Control + Shift + Left Control + Right Control + Shift + Right Control + End Control + Shift + End Control + Home Control + Shift + Home Shift + Home Shift + End

494

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Visual DataFlex Core Information


The Visual DataFlex language is a mature language (approximately 25 years) that allows developers to create powerful character-mode; OOP (Object-Oriented Programming); Windows; or Web applications quickly and easily. DataFlex 3.x versions allow you to write procedural code or character-based OOP code. Visual DataFlex (VDF) creates Windows and Web applications.

Some DataFlex terms are confusing to developers use to other languages Standard Term Table Column Row Index Database DataFlex Term Data File Field Record Index (K file) Visual DataFlex has no single database file type. DataFlex tables each are in their own individual file. For example, Access has a .MDB file that contains multiple tables. Embedded (DataFlex) data files each have a separate set of files (.DAT, .HDR, .VLD, .K*, etc).

Data Access Corporation

495

Appendix C Core Information

Discovering Visual DataFlex

The Main Utilities Studio The Studio is the hub of application development. It contains everything from powerful RAD wizards to links to all the other major utilities Database Builder Database Builder enables you to create, modify, and delete the database files used in a Visual DataFlex application. It supports creation and design of Data Dictionarys (.DD files), including declaration and configuration of the data-dictionary subclass required for every database file. In addition, it enables you to repair indexes and data, and to restructure files (including files from earlier revisions of DataFlex). Database Explorer Database Explorer allows you to browse through the list of data files of any environment or workspace and open the files to inspect their data. Many database features are incorporated in this utility such as the Database Export Wizard, which allows you to export your data to different formats. Compiler Once a program source-code file is created it must compile it into another file for the Visual DataFlex runtime to execute. The compiler does this operation.

496

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

File Relationships File relationships connect your files together. They stop data redundancy in your database table and allow your files to work harmoniously together. The whole key to solid code in Visual DataFlex is solid relational database tables. Your database structure must be correct to accomplish your needs.

The Parent-Child relationship is established within the Database Builder utility. If you have a parent file, OrderHea file and a child file, OrderDtl the OrderDtl file would relate to the parent OrderHea file. The related fields in both files must be the same type and length. In this case the related field is Order_Number.

Data Access Corporation

497

Appendix C Core Information

Discovering Visual DataFlex

The general rule to determine which file is the child and which is the parent is to determine which file will have many records to a single record in the other file. In this example there can be many child OrderDtl records for each parent OrderHea record. The exception to this logic is the one to one relationships. In these cases it make little difference which way the relationship points. An example of a One-to-One relationship is an employee file and a password file, you may need the password in a separate file for security but there should only be one password for each employee record

File Relationships Rules: 1. N to one relationship 2. Parent related field must be uniquely indexed 3. Related fields must be the same type and length

Some Sample Relationships

Chain Relationship: Child Books Parent Author Grandparent Publisher

One to One Relationship: Employee Password

Sibling Relationship: Employee

TimeCard

Wk_Summary

498

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Bridge Relationship: Orderhea Inventory Students Classes

Orderdtl

St_Cl

The Orderdtl child file contains a related field for both Orderhea and Inventory and also needed data about the detail line item. However, the St_Cl file contains only two fields one relating to the Student file and the other field relating to the Classes file. The single purpose of this file is to link the two parent files together to solve the many to many relationship that is not supported directly. To find all the students in Biology 101 you simply find all the Class code Bio101 in the St_Cl file. To find all the classes that student 1013 is registered in, you again go to the St_Cl file and find all the records with student ID 1013.

Data Access Corporation

499

Appendix C Core Information

Discovering Visual DataFlex

Data Integrity Whenever data is stored, business rules are generated in order to ensure the data being saved is correct. The old saying Garbage IN = Garbage OUT results when the business rules are not followed.

Business rules are validations preformed prior to allowing any operation to the database table (such as saves or deletes). They can be something as simple as making sure the State Abbreviated field is always capitalized or as complex as making sure that an order has sufficient inventory before a save is allowed.

The Database Builder utility creates a DataDictionary class for each database table. This file has the extension of DD. A Database table called Customer will have a DataDictionary Class created in a file called Customer.DD that holds the business rules for the database. This means all business rules are centralized in one place. This makes updates and maintaining the business rules easier.

The last four tab pages of Database Builder generate the code to create this DataDictionary file from you.

500

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

What Happens During a Save to Keep the Related Fields the Same? When DataDictionarys perform a save operation, an Attach command is also performed. This moves the parent-related field to the child-related field. This is the reason that the parent related field, not the child related field should be added to entry views (wizards will replace any Child.Related_Field with the Parent.Related_Field automatically). In our example of the order program only the OrderHea.Order_Number field is present on screen. But everytime an OrderDtl record is saved the OrderHea.Order_Number field is moved into the OrderDtl.Order_Number field prior to the save. This is why when you look at the code for the Order example you will see that a parent record must be found before it allows the user to enter the dbGrid to enter child records.

If a child record was created without having found a parent record first, it would result in a disconnected orphan child record and would display in the grid whenever the parent record was blank. This is NOT what is wanted!

Data Access Corporation

501

Appendix C Core Information

Discovering Visual DataFlex

File Normalization Normalization is the elimination of data duplication between files. To create file relationships we need to duplicate the related field in both files in order to link the files together, but this should be the only data duplicated. A good file structure will eliminate the need to duplicate data among files.

When data is duplicated between files Maintenance must be duplicated in order to update the data. Data integrity is sacrificed, as the data is not updated properly.

Examples of Bad Normalization: Customer Addresses are maintained in several files Customer Name is used instead of a Customer Code field for relationships (names are not unique and can change exceptionally for woman when they marry/divorce)

502

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

DataFlex File Extensions

Database files: Extensions Filelist.CFG DAT HDR K?? RPT TAG VLD FD DEF Description This file lists all database table file names Data files Header files used to repair the header of the .DAT file Index (Key) files making finds quicker Crystal Report files created by the Seagate Crystal Report program Field name file used by Database Builder/Database Explorer/Crystal Variable Length Data files stores the data when compression is used File Definition an ASCII file used by the compiler to convert File.Field names into File#.Field# ASCII Definition files - contains a database file definition

Common Application files: Extensions DD SRC VW RV PKG INC EXE Description Data Dictionary files Contains the Class with the Business Rules Main Source code files View code files Report View code files Package files external code files for classes etc Include files external code files Compiled VDF Code

Data Access Corporation

503

Appendix C Core Information

Discovering Visual DataFlex

Maintenance of Files
Database Builder utility is used for most maintenance that needs to be preformed on the database tables. Maximum Records: If you are using an embedded (DataFlex) database table, this number is very important. The embedded database uses the Max Records parameter for organizing its indexes efficiently. You should set a value for each file that is sufficiently large to accommodate the expected growth of records in the file. You should never allow the number of records in a file to exceed the Max Records; this can result in corruption of one or more indexes. Many developers will add into their code a feature that will check and adjust this number without user intervention. Each time you save a change to the Max Records parameter, Database Builder must rebuild the files indexes, and will do so automatically. When you set Max Records to 1, Visual DataFlex will treat the file as a system file and automatically place a check in the System File checkbox. Database Builder can also run a Percentage Filled Report, which will show how close your files are to this setting.
Figure 319

Set Max Records to 20% more than your expected size for the database table.

504

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Reindexing Occasionally, index files will become corrupt and will need to be rebuilt. Corruption can occur if the computer is turned off while writing to the hard drive. Reindexing will read through the main file and rebuild all the index (.K*) files.

Figure 320

Reindexing can be accomplished from the Maintenance pull-down of Database Builder or programmable using the Sort command.

Data Access Corporation

505

Appendix C Core Information

Discovering Visual DataFlex

OOP Core Information


Most procedural developers looking at Object Oriented Programming (OOP) Languages feel that they would like to dive in, but horror stories of the dark, deep waters of the object oriented learning curve have stopped them before they even got their feet wet. They may try struggling to learn it on their own hoping to sail through on a weekend, but the terminology alone is enough to make them feel like they are drowning. Frustration sets in and by the time they read through a few pages of messages, delegation, encapsulation, not to mention polymorphism, they are ready to abandon ship and jump back into the familiar procedural boat and keep drifting along. This old reliable procedural boat is a solid vessel, but more and more of their customers are demanding the new look and feel of a nice cruise liner. Customers want a better interface and mouse support (yes, this boat is full of mice!). The Object Oriented ship is not totally out of reach, the procedural developer just needs a nudge to get their feet wet. If you have been treading procedural water the time is now to take that OOP plunge! I believe it must be a plan and a commitment in order to learn it efficiently! These pages hopefully will make it easier. The goal is to fill the waters with enough life jackets to help procedural programmers feel safe about taking the plunge into the waters that will lead them to the object oriented cruise liner. To change your code from procedural to Visual DataFlex or WebApp object oriented, it must be rewritten! This sounds really nasty at first. I will not lie to you, theres no magical wand that can be waved and transform your procedural code into Object Oriented code. Application Framework is now fully incorporated into the language, and this methodology gives your application the solid building blocks needed to succeed. Theres much to learn but dont believe those horror stories of shark infested waters as you learn Object Oriented. The benefits far outweigh a little study time. You may have heard that Object Oriented coding is a totally different way of programming than procedural. Lets say that this is only partially true. In fact, Id like to concentrate on the similarities instead of the differences. There are many concepts that are the same in both languages. The names have just been changed, but the basic concepts are the same! At first I find the biggest problem to face is trying to get a firm understanding of the obtuse words OBJECTS and CLASSES! I strongly feel that a firm understanding of Objects and Classes is the key to success.
506 Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Definition of Classes and Objects: Classes are the tools and Objects are the instance of using those tools. That still sounds like Greek, so lets relate them to something in the REAL world. Think of Classes as a cookie cutter and every time you use this tool is an instance of the tool (a cookie)! If you use a Star Cookie Cutter, you will create a Star Cookie. Use this tool every time you want your cookies to have five points. If you want heart cookies you use the heart cookie cutter (tool = class). The cookie cutter and the cookies are both called a star or a heart but there is a big difference between them, just like there is a big difference between Classes and Objects. It is confusing because you call each by its cutter/cookie shape or by its class/object purpose. You have DataDictionary classes and DataDictionary objects; array classes and array objects. You would use the cookie cutter tool to create the cookies to eat. In OOP you would use the Class to create the Objects for the application to run. Someone has to create the tools. If you look at the FMAC file (a file that holds all the underlining commands to make the basic language work) you could see how the Enter Macro was created. These lines of code in FMAC make the Enter Macro command operational, much like code that make Classes operate. Most of the classes have corresponding package (.PKG) files that have the code to make the class/tool work. The code in FMAC does nothing by itSelf. You must use the Enter Macro Command in your source code in order for the program to allow the user to enter data. In OOP, you create objects from your class/tools to allow the user to interact and accomplish their required tasks. There are many classes/tools that come with the language. One of the things that you must learn is the most common classes (tools) that are used. One common class (tool) is an Array class. Each time you use this Array class (tool) you create an Array Object, (cookie). This object (cookie) will have all the functionality of the class (cookie cutter). In the DataFlex procedural language, you had three macros Enter Macro; EnterGroup Macro and the Report Macro. These were tools very much like Classes. Using these tools made coding faster and easier. One of the drawbacks of the 2.3b Enter and Report Macros were that you could only use them once per program because they used labels to navigate, and of course you could not have two labels with the same name. DataFlex Object Oriented tools do not have this limit. Reusing code (classes) over and over is the fundamental purpose of OOP.

Data Access Corporation

507

Appendix C Core Information

Discovering Visual DataFlex

Common Classes (Tools) Class Array Button DataDictionary Tool Use Used to store data as a temporary memory storage area. Its size grows dynamically to accommodate the storage requirements To create visual representations of keys or buttons that, when pressed by users, produce a specific action (event). The tool that provides database services (finds, saves, deletes and clears). Stores the Business Rules for the database table.

Some classes are product or application-type specific Character-Based Entry_View_Client VDF (Windows apps) DbView VDF (Web apps) cWebApp Class Use a container specially suited as the outer container of a view data entry tool (display & edit) of a single record data entry (display & edit) a scrollable, multi-column list of records data entry tool for text fields cWebReport cWebBusiness Process Used to create reports To contain and execute the statements to perform a batch process on an applications database files

Entry_Form Table

DbForm DbGrid

Text_Window BasicReport BusinessProcess

DbEdit BasicReport BusinessProcess

OOP terminology is sort of like learning a foreign language. At first, every time you learn a new word; you must convert it to your native tongue, or relate it to something you understand. So far you have Class = (Tool or Cookie Cutter, or Enter Macro) and Object = (an imprint from a class or Cookie, like the code using an Enter Macro).
508 Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Lets look at some code. The comparison is between Procedural code with DOS object oriented classes. Procedural Example
// code for the enter macro is in FMAC

Character-mode Object Oriented Example


Use EntyForm // inserts code to make Entry_Form Class // operate. This code is kept in .PKG files

/TimeCard_Image ID # Name ____ ______________

/TimeCard_Image ID # Name ____ ______________

Rate Hours Pay /*

__.__ __ ___.__ /*

Rate Hours Pay

__.__ __ ___.__

Enter TimeFile Empl // Enter macro requires child file listed first

Object TimeCard is an Entry_Form TimeCard_Image // (using clause link to Data_Set left out for this example) Item_List

Entry Emp.ID Entry Empl.Name Entry TimeFile.Rate

{AutoFind} {CapsLock}

Entry_Item Empl.ID Entry_Item Empl.Name Entry _ItemTimeFile.Rate

{AutoFind} {CapsLock}

Entry TimeFile.Hours Entry TimeFile.Pay

Entry_Item TimeFile.Hours Entry_Item TimeFile.Pay End_Item_List

EnterEnd

End_Object

In the above example, TimeCard is the Object and Entry_Form is the Class. Classes are the tools and Objects are the instance of using these tools. Just knowing that the object was created from the Entry_Form Class you know its purpose is to allow the user to edit and display single records. The object is an imprint from the tool that it was created from. Just like cookies were imprints from the cookie cutter.

Data Access Corporation

509

Appendix C Core Information

Discovering Visual DataFlex

Procedures & Local Variables Procedural code had structural code where you used GoSubs to execute sections of code. In Object Oriented, you send messages but basically they are doing the same thing. Procedural Example
//declaring global variables Number nHours nRate nPay GoSub Calc_It // Jump to a label called Calc_It & execute the // subroutine until a Return command is encounter.

Object Oriented Example


// Local variables in procedures are more efficient. // Memory is release upon the end_procedure command Send Calc_IT // Jump to a procedure called Calc_it & execute the // commands until an End_Procedure is encounter.

Calc_It:

Procedure Calc_It Number nHours nRate nPay

Move image.3 to nRate Move image.4 to nHours

// One Based

Get Field_Current_Value field Empl.Rate to nRate Get Field_Current_Value field Empl.Hours to nHours Calc (nHours * nRate) to nPay Set Field_Current_Value field Tcard.Pay to nPay End_Procedure

Calc (nHours * nRate ) to nPay Move Pay to image.5 Return

Notice the use of local variables in the OOP procedures and global variables used in the procedural code. The local variables used in procedures are dynamic variables (meaning they will grow as needed, so you no longer indicate the length of string variables). Local variables are destroyed and the memory released as soon as the end_procedure command is reached. This is much more efficient! The Get and Set commands retrieve and set properties. Properties are special object variables or item variables that are used to determine the current state of the object/item. Procedural code had predefined variables. For example, the Report Macro used PageEnd and PageFeed. The Move command could address these predefined variables directly. OOP properties (which are similar to predefined variables) use the get and set commands to obtain or change properties. You may have heard that Object Oriented Programming is Event Driven. That is an event triggers the direction flow that the program takes. Procedural programming is more sequential in its flow. At first, a programmer may feel he has lost control over the user that now has this mouse and can easily jump anywhere! These events that drive the program flow can be controlled. It just may seem different, at first, as you learn all the events that allow you to send messages (which are like gosubs to subroutines).

510

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

If your OOP page allows database table operations to the Customer file, the Customer_DD (DDO) is being used to perform these operations. The Server property will connect the entry object to the Customer DataDictionary Object. This DataDictionary Object will supply the database table operations for find, clear, save, and delete operations. The procedural Enter macro has the ability to perform database table operations (finds/saves/deletes/clears) within the macro tool itSelf. The DataDictionary class also has these functions built into the class. In OOP you will be using many tools, and it would be a waste to have each class (tool) understand how to perform the complex multi-user database table operations. Therefore, you separate these tasks out and whenever a class needs these database table operations, they are linked to the DataDictionary object that should be servicing it for finds, clears, saves, and deletes. In OOP you link your Data Entry Object DEO (Web Business Object -WBO in Web apps) and DataDictionary Objects (DDO) together to give the DEO/WBO access to the database table. Each DEO/WBO will link (via the Main_DD property) to their main DataDictionary Object. This is sort of like a computer operating system. If you wish your computer to save a file to the floppy drive, you do not ask the computer - you ask the operating system to ask the computer. The operating system knows how to do this and does it well, so you let it do all the work of finding all the fragmented parts of the file and moving them to the floppy in drive A. Then, it updates the File allocation table so the file will show up the next time you do a DIR A:. DataDictionarys do all the overhead work of rereading and locking your files. They do all these database table tasks so well that you should always allow them to perform these types of tasks.

Data Access Corporation

511

Appendix C Core Information

Discovering Visual DataFlex

Multiple DataDictionary Objects (DDOs) Lets look at a VDF view using DataDictionary classes.
Use Windows ACTIVATE_VIEW Activate_oView FOR oView Object oView is a dbView // A framework rule states that there should be a Data Dictionary Object for every File opened. Object Employee_DD is an Employee_DataDictionary End_Object Object TimeCard_DD is a TimeCard_DataDictionary Set DDO_Server to Employee_DD End_Object Object Empl_ID is an dbForm Set Server to (Employee_DataDictionary (Self)) Entry_Item Empl.ID End_Object Object Hours is an dbForm Set Server to (TimeCard_DataDictionary (Self)) Entry_Item TimeCard.Hours End_Object Object Rate is an dbForm Set Server to (TimeCard_DataDictionary (Self)) Entry_Item TimeCard.Rate End_Object End_Object

The DDO Server Clause establishes a two way communication between these DDOs.

Employee_Data_Set Object TimeCard Object Connected to Employee_DD Empl_ID Object Server Employee_DD Hours Object Server TimeCard_DD Rate Object Server TimeCard_DD

The Enter Macro had rules that had to be followed when you used related files. All files were listed after the Enter Command. The order that the files were listed was very important for the correct saving and deleting of the data in the related files. Lower (child) files were listed first, followed by higher (parent) files. In OOP, you connect the DEO/WBO to the main DataDictionary Object (DDO) via the
512 Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Server property, just like in the last example. Then, if there are multiple related files, you connect the DataDictionary Objects together via the DDO_Server property. You link your DataDictionary Objects together just like the related file structure created in Database table Builder (DFFile). Hopefully, you are starting to see the power of OOP. You take classes (tools) and by making objects (imprints from them) you create an application that users can interact with to have access to the database table.

Data Access Corporation

513

Appendix C Core Information

Discovering Visual DataFlex

Encapsulation An object-oriented term that is heard often is encapsulation. The definition of encapsulation is combining data and procedures into a single entity capable of manipulating itSelf. The easiest way to understand these terms is to relate them back to procedural code. Individual programs in their own source code (.SRC or .FRM) file. Each a stand-alone (encapsulated) section of code.

Procedural Menus

Main Menu ----------------------------------------------Data Entry Menu Report Menu System Parameters Employee Entry ----------------------------------------------Employee ID _____ Dept ____ Name: __________________

Address __________________ Data Entry Menu ----------------------------------------------Employee Entry Department Entry Time Card Entry Department Entry ----------------------------------------------Dept ____ Name: __________________ City ____________ St__ Zip ____

Time Card Entry ----------------------------------------------ID ____ Name: __________________

Rate

____.__

514

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Procedural code normally had a menu program that executed, via Chain wait commands, all the separate .FLX programs. An OOP application will combine all the views into a single application (.src) and from a starting page or menu bar launch the individual views (web pages).

The different views all can be displaying different Individual views each records from the same file. with their own .VW The DataFlex language still (WBO & ASP) file. only has one record buffer for each opened file, how is it possible that the views all display/save/delete different records? Each view contains its own DataDictionary object for the Employee file. The Employee view has an Figure 321 Employee_DataDictionary Object, the Department View might also be displaying an Employee record, however that view has its own Employee_DataDictionary Object. Remember these DataDictionary Objects service the view objects for Finds/Clears/Saves/& Deletes. They are responsible for making sure that the correct record is in the record buffer! This is a task that the Data Dictionarys do well. The user now can bring up all the views on screen at the same time and jump between them with the mouse! The DataDictionary just sits back and keeps track of the correct record for you! What a great tool (class).

Data Access Corporation

515

Appendix C Core Information

Discovering Visual DataFlex

Message Forwarding Procedural Code came with 3 macro tools, but Object Oriented has MANY.

A small section of the Class Hierarchy Chart.

UI_Object Menu List EntryList Wide_List Data_List Table The entire Hierarchy Chart is large. However only a handful of classes are used often. One tool is built off the tool above it. Instead of rebuilding the wheel each time you create a new tool, you simply add the new features in the new tool. The tools get more and more powerful as they are subclassed. An example of how the tasks are passed from class to class, would be similar to how networks and operating systems pass commands along. They do basically the same thing the classes are doing. If you are running a Novell network all commands typed at the prompt go to Novell. Novell will perform the task if it is a Novell command like NDIR or CAPTURE but if it is a DOS command, Novell just hands it to DOS to handle. If you type DIR, Novell will (take this command) find that it does not know how to do this task and forwards the command to DOS. Since DOS knows how to handle this command, the DIR task is performed. It would not be efficient to rewrite all the DOS commands in Novell just like it would not be effective to do this whenever you create a new class. DIR Command

Novell

DOS

Since Novell is built from DOS, there is no need to make Novell understand how to do a DIR. It only has to forward it to DOS to handle. Classes operate the same way. The message Bell is sent to an object built from the Button class. It may not know how to ring the computer bell but it will forward this message up to its super-class and if that
516 Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

super-class cannot ring the bell it will forward the message up the branch until a class understands how to ring the bell. Just like you do not care if Novell or DOS takes care of a command the user will not care who handles the message Send Bell. Just for your information the defining class for the message bell is the UI_Object Class. How do you find out? The On-Line help will list all predefined procedures and functions (similar to subroutines) in a chart. This chart will tell you the defining class. Looking up the procedure under the Defining Class section will give you a full description of the purpose and use of the message. Now that you are aware that messages may be passed up the class hierarchy structure, it is time to take a look at building a class. It is important to note that developers will find the DataFlex predefined classes to be sufficient for most programming needs, but occasionally there will be a need to build a class (tool). The most common class that you will need to build is a class built from the DataDictionary class. Database Builder makes creating DataDictionary classes very easy from four tab pages that allow you to fill in a group of forms and checkboxes. The Enter Macro had the database table operations built in, but in OOP they are separated out into the DataDictionary Class. In procedural coding, there are times when you needed to perform certain tasks during the lock state of save and delete operations. The Enter.Save and Enter.Edit were provided to perform operations such as automatically assigning the next available ID number from a SysFile or keeping track of running totals. In Object Oriented, the Creating Procedure is only called during a new save and the Update and Backout procedures are used to maintain running totals.

Data Access Corporation

517

Appendix C Core Information

Discovering Visual DataFlex

Event Driven OOP is an event driven language. Events are actions that trigger messages to flow. In OOP nothing is done until a message is sent. Therefore it is very important to know how to trigger these messages.

Trigger Messages by: Classes

Description The purpose of some classes is to trigger messages. The button class is sends the OnClick event when clicked. (i.e.; Menu bars; Tool-bars). The purpose of accelerator keys is to send messages. (i.e.; F2 sends the Request_Save message and Shift+F2 sends the Request_Delete message. The purpose of the On_Key command is to trigger a message when the defined key stroke is pressed. (i.e.; On_Key Key_Alt+Key_P send Print_It. The Send command will trigger a message. There are many variations to the send command; Delegate; Forward; Broadcast. Many pre-existing messages can be augmented to perform extra processing or additional messages whenever they are normally triggered. A special command that starts the User Interface.

Accelerator Keys

On_Key

Send Augmenting Existing Messages Start_UI

518

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Building New Classes: New classes are built so objects built form them will contain the new class features. This is how the business rules are added into one location and affect all views. The CapsLock option is added into the DataDictionary class and after recompiling it will effect all views that contain this field. // Empl.DD File
// Employee_DD Class built from DataDictionary Class

Class Employee_DataDictionary is a DataDictionary

Procedure Define_Fields Forward Send Define_Fields Set Main_File to Empl.file_number Set Field_Options Field Customer.State To DD_CAPSLOCK // other business rules

End_Procedure End_Class

//Empl_Grid.VW File Employee Grid View Use Empl.DD

Object Employee_DD is an Employee_DataDictionary End_Object //Empl.VW File Employee Entry View Use Empl.DD

Object Employee_DD is an Employee_DataDictionary End_Object

Data Access Corporation

519

Appendix C Core Information

Discovering Visual DataFlex

The UIMS User Interface Management System (UIMS) is like a shell level in DOS. At the command line, DOS just sits and waits for the user to type a command and press return. The UIMS is similar to an operating system waiting for a command or an event to happen that will trigger (send) a message.

Let us look at an OOP view made into an application:


Use DataDictionary Use dbGrid Use Customer.DD Object Customer_DD is a Customer_DataDictionary End_Object

Customer DataDictionary

Object Customer_Grid is a dbGrid Set Server to (Customer_DD(Self)) Begin_Row Entry_Item Cust.ID Entry_Item Cust.Name Entry_Item Cust.Phone End_Row End_Object Start_UI (Customer_Grid(Self))

Customer_Grid

In the program nothing really happened until the last line, when the Start_UI command is reached. All the objects are simply built in memory. The Start_UI command is really two commands in one. It starts the User Interface (UI) rolling. Remember messages are just the gosub that will execute a procedure (subroutine). The UI starts and simply waits for those events to trigger the sending of messages that make the program run. There are many ways to trigger messages to be sent (e.g., keyboard entry, mouse clicks, timers firing, entry options, setting certain properties). At first, procedural programmers may feel like they have lost control to the user or UIMS. In procedural code the user was pushed straight through your code. The user
520 Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

could navigate up and down through the entry windows and with this limit, the programmer had complete control over the actions of the user. Now with the mouse the user can navigate anywhere - anytime or so it seems. The real skill of OOP comes with the coding of these events that will trigger your messages at the correct time. The more you code in Object Oriented, the easier it will become. One of the biggest benefits is the increase in data integrity. This is accomplished by separating the database table operations from the Data Entry operations. This is a logical separation and one that has many benefits!

Data Access Corporation

521

Appendix C Core Information

Discovering Visual DataFlex

Summary In this OOP overview many concepts have been quickly covered. There is still much to learn but hopefully you will have a good general understanding of some of the basic principals of object-oriented programming and how it works, so the rest of your reading is easier.

Topics Covered: An understanding of the terms Classes and Objects A general idea and use of the commonly used classes. An understanding of forwarding messages through the class hierarchy structure The use of Procedures to accomplish tasks and how to trigger them by sending messages. A general understanding of the DataDictionary Class. Its importance as the server of view Objects via the phMainDD property. How DataDictionary Objects are linked together with the DDO_Server property similar to the file relationship structure. The power of creating new classes (tools) in order to stop duplication of code. The need to create new classes (tools). Example: creating business rule in the DataDictionary class. How encapsulation of each view linked together via the .SRC file. General understanding of the UIMS operation. A general connection between Procedural code to Object Oriented code.

522

Data Access Corporation

Discovering Visual DataFlex

Appendix C Core Information

Prior DataFlex Users


Prior DataFlex Procedural Users We no longer rely on DFPATH or DFENV to locate our files. The workspacename.WS file located in the workspace will now do this.

Prior DataFlex Character-Based OOP Users Modal state is now used in place of Block_Mouse_State. There are many changes and you should read the Whats New section whenever upgrading your application.

Everyone New to VDF8 Refer to the Whats New sections in the on-line help. There are so many items that have changed in the different versions of VDF. This great section will outline the many new improvements made to the latest VDF version(s). The links in this section will jump you to full descriptions of the great features that have been added.

Data Access Corporation

523

Appendix C Core Information

Discovering Visual DataFlex

524

Data Access Corporation

Discovering Visual DataFlex

Glossary

Glossary
The words in this list are used in Visual DataFlex documentation with specific meanings beyond their meaning in general contexts, even general computer-oriented contexts. Consult this list whenever you encounter a word in the documentation that seems to be used with a special meaning.

Data Access Corporation

525

Glossary

Discovering Visual DataFlex

Terms Accelerator Key

Definitions A key, or combination of keys, that invokes an applicationdefined procedure. The keys are referenced within a program by a predefined name preceded by the letter "k," (e.g., kcancel). Each accelerator key is mapped to an actual key on the keyboard and the mapping can be changed through the DataFlex Configuration. See also Flex-Key. A reference created by the compiler to address the object. This reference can be used to address objects in the program. At compile time, the compiler creates a special function, which uses the same name as the object, which is being accessed. That function returns the object's absolute object identifier. For example, if Object b is nested within Object a, you would use (b(a.obj)) to reference Object b. This is the access method by which Object b may be referenced. See also Object; Object Identifier. A horizontal bar that contains pull down lists giving choices for specific actions. Like Menus A term denoting a parent, grandparent, great grandparent, etc., of an object or class. See also Child Object; Class; Descendent; Object; Parent Object. Is the methodology to construct and connect object-oriented sections together correctly. A parameter passed to a procedure, function, or a macro to control the process. See also Function; Macro; Procedure. The process by which an inherited procedure or function is given, adds functionality in a subclass. A procedure or function is augmented by defining a procedure or function with the same name as the inherited one and including in the new definition, a forward command that sends the message to the class from which it was originally inherited. See also Override.

Access Method

Action Bars Ancestor

Application Frame Work Argument Augment

526

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Backout Procedure

Definitions A procedure in the Data_Set class called during deletes and edit saves that allows the programmer to code during a lock state (such as maintaining running totals). Like the Enter.Edit in DataFlex procedural code. The process in which a parent object sends the same message to all of its child objects. If the message sent returns a value, only the last value is retained. For example, an object might broadcast the message, initialize, to all of its children as preparation to further operations. Message delegation is turned off during a broadcast. See also Delegate. An area in the computers memory which is used to store and manipulate the data being entered by the user in the edit class. See also Class, Base; Edit. An area in the computers memory that contains a record from each opened database file. The place in memory where these records are active is called the record buffer. When a record has been read from disk to the record buffer, data can then be extracted, added to, and/or modified in that record. The record can then be written back to disk (saved). Likewise, in order to delete a record, the record must first be active. The record buffer is where DataFlex does its work on a given record. See also File, Database; Record. An area in memory where the active image is located. There are image-name-line options, resident and resource, which place an image in memory for the duration of the program. See also Current Image; Current Window; Image; Window. A naming convention database file which is relating to another file and there is a valid relationship established. This database file extracts the related fields from the related to database file (Parent) and allows for a seamless data structure within a program. See also Parent File.

Broadcast

Buffer, Edit

Buffer, Record

Buffer, Screen

Child File

Data Access Corporation

527

Glossary

Discovering Visual DataFlex

Terms Child Object

Definitions An object-creation block which is nested inside an objectcreation block. Parentage provides a route for the child object to inherit properties, including messages and accelerator keys. See also Descendent; Object; Parent Object. A group of properties, children and messages that define specific behaviors to objects. Classes are designed by behavioral description, or, a class may be constructed as the intersection of the properties of a set of similar objects. A class must be based on another class, called its superclass. See also Class, Base; Superclass. We can also think of them as Tools that our objects are built from. Like the Enter or Report macro in DataFlex procedural code. A set of classes supplied with Visual DataFlex defined `below' the level of DataFlex itself (as distinguished from classes created with the class command). The base classes, also called "data structures" are Message, Menu, DFList, Edit, Scrollb (Scroll Bar), and Array. See also Class; Superclass. A .PKG file that contains the source code for a class definition. This code is included in the program at compile time through the use command. Examples: Windows.PKG, DfAllEnt.PKG An abstract term denoting an area in memory that stores data. It is designed to be used as the source and destination for cut and paste operations. The clipboard is automatically created by the system, and is available to the programmer at any time a cut source or destination is needed. The clipboard is retained across chain and chain wait operations, so it can be used to transfer information between programs or modules of an application. The clipboard can receive all of the messages of the edit class objects. See also Edit; Object.

Class

Class, Base

Class Package

Clipboard

528

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Command

Definitions A word or series of words in program source code which execute a predefined procedure (i.e., goto X1, sends execution to Label x1) or string abc (creates a variable named abc with a length of 80 characters). DataFlex commands are macros, which are defined in the file FLEX.CFL. FLEX.CFL is what the compiler reads as it processes your program source code. Commands can also be defined with compiler directives in programs and packages. See also Macro. The method of comparing values using any of the following logical functions: matches, contains, min, max, ior, iand, <>, >, <, =, <=, and >= in expressions, and ne, eq, lt, gt, ge, le, match, and in commands. See also Function. A procedure in the DataDictionary class called only during new saves that that allows the programmer to code during a lock state (such as assigning next available ID numbers). Like the Enter.Save in DataFlex procedural code. An active object currently being used. An object becomes the current focus in the focus list when 1) a message is sent or a command is executed to activate an object or group of objects, 2) a procedure or function uses the procedure_return or function_return command to return a non-zero value to a start_ui or ui_accept command, or 3) the user clicks the mouse cursor on an object which is already activated, but not the current focus. See also Focus List. The image being acted upon. Images are numbered consecutively (top to bottom) within a program when compiled. The image being acted upon is internally maintained by the current_image system variable. See also Buffer Screen, Current Window, Image, Window. A predefined integer that contains the number of the message that invoked the currently executing procedure. current_message is useful when the message number of a procedure must be passed to another procedure.

Comparison Mode

Creating Procedure

Current Focus

Current Image

Current Message

Data Access Corporation

529

Glossary

Discovering Visual DataFlex

Terms Current_Object

Definitions A predefined integer that always contains the absolute object identifier for the object owning the procedure currently executing. See also Focus, Focus List, Object, Object Identifier. The window being acted upon. Windows are numbered consecutively (left to right, top to bottom) within a program, regardless of the image they belong to when compiled. The window being acted upon is internally maintained by the current_window system variable. See also Current Image, Image, Window. A visual cue that shows users the current position of the mouse input focus (current position). See also Cursor Text, Cursor Selection. A visual cue whereby users indicate with the keyboard the choice they want to interact with. It is represented by highlighting the choice with an inverse bar. For example, if you were making a selection from a scrolling list, the selection cursor would be located on the choice in the list, which is highlighted. See also Cursor Text.

Current Window

Cursor, Mouse

Cursor, Selection

Cursor, Text

A visual cue that shows users the current position of the keyboard input focus (current location). See also Cursor Mouse, Cursor Selection. The .DAT files are the data files where DataFlex stores the raw data entered, unless compression is used in which case the data is stored in the .VLD file and the .DAT is used as a pointer to locate the correct record in the .VLD file

.DAT files

530

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Date

Definitions A field, variable or window used for evaluating and storing dates. There are three formats supported; mm/dd/yyyy (USA), dd/mm/yyyy (European) and yyyy.mm.dd (Military), where mm indicates two digits representing the month, dd represents two digits representing the day, and yyyy represents four digits representing the year. Two-digit entry and recording of years is allowed optionally. The format is set as a system option in the DataFlex Configuration. Dates are stored in Julian form as numbers, allowing for operations requiring calculations without type conversion. The display is a de-coded representation of the numeric format storage. There is a date command, which defines a variable of Type Date. See also Variable, Window.

.DEF files

The .DEF files have an entire file structure of a database described in an ASCII format. These ACSII files can be created from DFFile or DFMaint and can be used in DFFile to create a duplicate file structure. The process by which a message is sent to the parent object of the current object. Any message that cannot be understood by the current object or the class of the current object is automatically delegated (sent to the parent of that object or class). This delegation continues until the message reaches the Desktop; if the Desktop cannot understand the message, an error is generated. There is also a delegate command in DataFlex that causes messages to be sent directly to the parent. Data-Entry Objects are objects that allow data-entry. A term denoting a child, grandchild, great grandchild, etc., of an object or class. See also Ancestor; Object; Class; Object; Parent Object. An "invisible" object which is the ultimate ancestor of all objects within a program. The desktop is the background upon which all other objects are displayed. Likewise, it is the final receiver of messages that are delegated by global objects. There can only be one desktop within a program. Deviations of objects from their superclass
531

Delegate

DEO Descendent

Desktop

Differentiation
Data Access Corporation

Glossary

Discovering Visual DataFlex

Terms DSO

Definitions Data Set Objects are objects that are built from the Data_Set class or a subclass built from this important class. Data Sets Objects are used as the servers to the DEOs. They handle the database operation such as finds, clears, saves, and deletes. See Class, Base.

Edit

Encapsulation

A section of code that can operate alone This does not mean it needs no external connections. An object is an encapsulated code segment; it is a black box whose makeup you need not know exactly, just the interfaces that allow you to interact with it (i.e. what properties and messages can be sent to it). The object may have external dependencies, such as a DEO being connected to a DataDictionay Object. Options that are connected to an item Windows that will perform a desired action when the user enters or leaves a window. Example: {CapsLock} will force the contents of the window to only be capital letters: Field_Entry_msg property will send the corresponding message just prior to entering the window. The ability for a user to process requests for action at almost any time. When users navigate with the arrow keys, input, select items with the mouse, or press accelerator keys, the program is continually asked to respond to events. These events may be directed at any active object, or cause the activation of objects. Events that determine the flow of the program. Like a KeyProc used in DataFlex procedural code. See also User Interface.

Entry Item Options

Event-Driven Interface

Expression

A set of commands encompassed by "(" and ")" which are executed jointly to process data. All expressions return a value. Expressions can be nested. For example (length(trim(temp_string))), in this expression the variable temp_string is first trimmed then the length of it is calculated. See also Command.
Data Access Corporation

532

Discovering Visual DataFlex

Glossary

Terms Field

Definitions A discrete piece of data that is of a defined type and size which is stored in a record. There are usually many fields in a record. Each field is given a name that is unique to that database file, and common to every record. Database fields are sometimes referred to as the elements in the file. You can have up to 255 fields per record. See also File, Database; Record. An area on disk that holds structured data, which makes up a particular information system. A database consists of records, which contain fields (file elements). Database file definitions contain the name of the file, the numbers, lengths, and types of the fields, which fields make up the indexes, etc. Database files are analogous to a file cabinet drawer (database file) containing folders of employees (records), which contain the employees employment form (the data in the employees employment form are the fields). See also Field; File System; Record.

File, Database

File, Index

A file (organized listing) used to expedite the finding of records for a database file. The file structure is B+ Multi-level ISAM. There are two types of index files; online (maintained automatically by the programs) and batch (must be reindexed prior to its use). Index files determine if the fields of a database file can be duplicated (the record number is part of the index) or not. An index file is created by the DataFlex Database Builder or the DataFlex Index Tool. See also Field; File, Database; Record; Reindex. Filelist.CFG contains a list of all the filenames (Rootname, DataFlex name, User name) for each file that is accessible.

Filelist.CFG

The numbered list of database files in a system, kept in a file default-named Filelist.CFG. The compiler and the runtime uses Filelist.CFG to find the physical disk fileset containing the desired data.

Data Access Corporation

533

Glossary

Discovering Visual DataFlex

Terms File, Sequential

Definitions Data in sequential files can only be accessed sequentially, rather than randomly as in database files. The read, readln and read_block commands are used to access the data in sequential files. One of the most common types of sequential files is ASCII text files.

File, System

A database file with unique limitations. The file can not contain more than one record, be indexed, or have a relationship established with another database file. The buffer of a system file is automatically loaded with the data contained in its record upon open. The purpose of this type of database file is to keep system (global) information in it (i.e., your company name, address, city, state and zipcode). See also Child File; File, Database; File, Index; Parent File. Any of 13 standard DataFlex functions activated by a single keypress or shift-key combination. The functions pertain to database operations (finding, deleting, saving) and text editing (backspace, arrows), and have standard names in DataFlex to make the function independent of the particular physical keys to which they are mapped. The mapping is configurable at each site, and for each machine using a multi-user license. See also Accelerator Key. See Current Focus.

Flex-Key

Focus

Focus List

A list of objects that are currently activated. This list is modified by the activation (activate) and deactivation (deactivate) of objects. This list is set up so that each object in the list knows 1) what object had the focus prior to its own activation (prior_focus), and 2) what object took the focus after it was activated (next_focus). In programmer terms, the focus list is a doubly-linked list. How this list is maintained is critical to the design of an application - the order of activation and parentage of objects must follow a particular structure for a program to function properly. The object that currently is capable of user interaction.
Data Access Corporation

Focus Object
534

Discovering Visual DataFlex

Glossary

Terms Focus Tree

Definitions UIMS applications organize objects in a manner allowing logical navigation paths between objects. As objects activate and deactivate, this tree is updated to reflect the objects position in relation to other active objects. Four properties indicate the objects position: Prior_Focus, Next_Focus, Prior_Level, and Next_Level. The process of sending a message to the ancestor class of an object or class. If no ancestor of an object understands a message, then it is delegated to the parent of the object to which it was sent. The forward command causes messages to be sent to the ancestor class. See also Delegate. To reference an object not yet created. When it is necessary to reference an object not yet created, use the Register_Object command, so it creates an access method for that object. See also Access Method; Object. A block of code which incorporates a set of commands that jointly define messages sent to an object. The message is defined using the get command. A function is defined by the function and End_Function commands. Functions return a value of a particular type using the function_return command. Functions can not be nested. Functions are like subroutines in procedural code that always return a value. See also Command; Delegate; Message; Object; Procedure. Something is global when it is not contained within the bounds of a class, object, function or procedure. For example, a variable not specifically declared within a procedure is global. A procedure, function, or object is global when it is not nested within any other object. Global code and data structures can generally be referenced by any part of the program. An object whose parent is the desktop. These objects are described as `children of the desktop' or global objects, and may be addressed without access methods. See also Access Method; Child Object; Parent Object.

Forward

Forward Reference

Function

Global

Global, Object

Data Access Corporation

535

Glossary

Discovering Visual DataFlex

Terms Handler

Definitions A handler is another term for a message-handling procedure. The name comes from the idea that the handler "handles" or responds to a message it receives. See also Message; Procedure. An area in memory that holds static and data-output areas (Windows). In source code, an image (also referred to as a "page") is defined by a slash (/) in the first (0) column and followed by a name (page name) which must contain a letter in the first character. An image continues until the start of another image ("/pagename") or the end of the image section (indicated by "/*" at the start of the first line after the last image). Each image can be manipulated individually by the program. Images can be used for output to a device (printer, console or file). Each image is identified by a page name. See also Window. The ability for an object to change the image (visual property) at runtime. Certain objects can change their visual properties at runtime. For example, the edit object may change its height and width merely by changing the value of its size property. The scrollbar object adjusts its length based on the length of its parent. Images that can be changed at runtime are dynamic images. A special type of argument (often referred to as "flags") which conditionally controls command line execution. Boolean in nature, it can only be set to true or false. It is created with the indicator command and defaults to a false status until some other event in the program resets it to true (i.e., indicator select). Once defined, an indicator is addressed by enclosing its name in brackets ("[" and "]") to identify it to the command processor (i.e., [not select] return). The process of assuming properties and message handlers from an object's class. Inheritance saves the effort and potential error of having to define the properties and messages of every object explicitly. See also Subclass; Superclass.

Image

Image, Dynamic

Indicator

Inheritance

536

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Instance

Definitions The coming to existence of an object (i.e., an object is an instance of a class). The realization of a class definition. In a class, the construct_object is the operation, which is executed on a new instance of the class to configure the instance to conform to the class's definition. See also Class; Object. One of three types of numeric representations that can be used as the subject of a command's execution or expression evaluation. A field, variable or window used for storing number types. Only whole numbers can be stored in this type, ranging from 0 to 2,147,483,647. There is an integer command, which defines a variable type integer. See also Variable; Window. A message not understood by the receiving object, its ancestors or the desktop. When the message reaches the desktop and it can not understand it, an error is generated. See also Message. A storage area for data associated with an object, displayed for user interaction. When an object, which contains items, is displayed for interaction with the user, the data for the items will be displayed in the windows of the object's image. The data for each item is initialized when the item is created, according to the command used to create the item. All items have a value property associated with them. The data stored in the value property of an item is a string and is displayed when the user is interacting with the object. Items may contain different types of data and maintain various states, depending on the class of the object in which the item is created. There are five types of item lists, which can be created by DataFlex; Static, Dynamic, Entry, Window and Array. See also Item List, Dynamic; Item List, Static; Object.

Integer

Invalid Message

Item

Data Access Corporation

537

Glossary

Discovering Visual DataFlex

Terms Item List, Dynamic

Definitions A list where not all of the items in an object can be seen in the windows at once. Consequently these objects also automatically create a scroll bar to indicate when there are more items above or below the items currently displayed. The classes, which support dynamic item lists, are DFList, Checklist, Entrylist, and Formlist. The add_item and insert_item commands are used to create items in objects of these classes, while the delete_item message can be used to remove items from the list. The syntax for add_item and insert_item allow the item's message and value to be specified, but the item selection message is always sent to the object in which the items are created. See also Item; Item List, Static; Object. A list where all the items of an object can be seen in the windows at once. The classes that use static item lists are Menu, MenuBar, Button, Checkbox, Entry, and Form. Items in objects based on one of these classes must be created within an item_list-end_item_list structure using the on_item command. See also Item; Item List, Dynamic; Object. A program location identifier used by control commands (i.e., goto, gosub, return) to jump over commands and group of commands. It is defined as any continuous string of characters at the beginning of a line followed immediately by a colon (:). Labels must begin with a letter, which may be followed by up to 79 numbers or letters (no spaces or punctuation). A variable which cannot be referenced outside the procedure or function which defined it. They are defined by invoking the local command preceding the variable type. Multiple procedures may define local variables with the same name but each will have its own value. A local variable may not have the same name as a global variable. Local variables release their memory area upon the end_procedure line. See also Global; Variable.

Item List, Static

Label

Local Variable

538

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Macro

Definitions A set of code (which the compiler understands) that accepts arguments and textually substitutes the values of the arguments into the command model. The resultant commands are then compiled and included with the rest of the code. Macros can be defined directly within one or more programs, or they can be defined in packages. Macros are expanded every time the compiler finds a call to it. See also Command; Subroutine. There is a menu object class, and a user-interface element called menu. The class is frequently user to create the element in programs. See Menu bar Pulldown; Class, Base. An extension of the menu bar that displays a list of choices available for a selected choice in the menu bar. After a user selects a choice in the menu bar, the pulldown appears. Another term is Menu. A request for an object to perform one of its operations. It is not a behavior, it is a name (and the arguments) of a behavior. They are the only interface to an object. Messages are sent and received by the send, get, and set commands. These is also a message class. Messages are like a gosub in procedural code. See Class, Base. A type of property which has a finite number of values it can contain. The number of properties is usually three or more; properties with only two possible values are generally considered to be states, not modes. An example of a mode is search_mode which may be set to first_character, incremental, capital, and no_search. See also State, Property. Users are required to finish one task before moving to the next One of three types of numeric representations that can be used as the subject of a command's execution or expression evaluation. A field, variable or window used for storing number types. Only fixed point numbers can be stored in this type, ranging from .00000001 to 99,999,999,999,999.99999999. There is a number command which defines a variable of type Numeric. See also Variable; Window.

Menu

Menu bar Pulldown

Message

Mode, Property

Model Navigation: Number

Data Access Corporation

539

Glossary

Discovering Visual DataFlex

Terms Object

Definitions An object is the realization of a class (sometimes referred to as the object's type). An object can be defined in terms of the properties and messages that it understands. The commands between object and End_Object commands are executed by the runtime (not the compiler) during the creation of the object. An object relationship to a class is similar to the variable's relationship to its type. See also Access Method; Global Object; Object Identifier. Objects are the instance of using a class. Like: the Enter Macro in procedural code An integer unique to each object assigned at runtime when the object command is executed. This integer is called the absolute object identifier. If an object is the child of the desktop the compiler issues a global object identifier. See also Access Method; Object. A style of programming which uses objects as the unit of software division and messages as the way to connect objects. Data is encapsulated within an object, making it part of the process and is not treated globally. The messages that are provided for the object class defined by the package. Of these, the important messages are listed under the package category of Usage. See also Usage, Package. A .PKG file that contains a predefined structure of objects that may be used in programs. Example: Confirm.PKG Commands that will allow you to define program action. Like a KeyProc in DataFlex procedural code. The practice of using message arguments in a class or object that have a slightly different purpose in the class from which they are inherited. Overloading is apparent to the programmer when it is used together with (unchanging) keywords, such as item, where the actual argument is something slightly different, such as a line number. See also Encapsulation; Polymorphism.

Object Identifier

Object-Oriented Programming

Operation, Package

Object Package On_Key Overloading

540

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Override

Definitions The process of redefining an inherited property or message. Creating a procedure, function, or property with the same name as the one inherited causes the new definition to be used in place of the old, thus overriding the inherited property. See also Augment. A body of source code frequently composed of several classes, objects and screen definitions (images). They are a finished piece of code including the user interface, ready for implementation into your program. Packages are plain ASCII files, but must use the extension .PKG in their filenames. An example is the List package which provides users with a class that defines a pop-up look up list. A portion of the screen, usually rectangular, containing data relating to a particular function among those displayed on the screen. Panels often contain several lines and several windows, and may pop up and disappear with user interaction. Panels representing sub-functions outside which the mouse is disabled (modal dialogs) are surrounded with a double line, while others, outside which mouse action is allowed, are surrounded with a single line. See also Image; Window. A parameter is a value, or one of several values included in a procedure or function call. These values are "passed" to the procedure or function to allow it to have some desired effect. For example, a procedure designed to draw a box on the screen could be passed the height and width of the box as parameters. A naming convention denoting a database file which is being related to and there is a valid relationship established. This database file requires the field upon which the relation is based to be uniquely identifiable (main index for that field must not contain record number). Once a valid relationship is established both the Parent and Child database files will feel like one large database. The benefits for relating database files are efficient utilization of disk space (reduce data redundancy), improved efficiency in changing data, greater consistency and an easier view of the system conceptually. See also Child File.

Package

Panel

Parameter

Parent File

Data Access Corporation

541

Glossary

Discovering Visual DataFlex

Terms Parent Object

Definitions An object-creation block with nested object-creation blocks in it. Parentage provides a route for inheritance of properties and delegation of messages. See also Ancestor; Child Object. The characteristic of objects and message definitions that permits the use of object and variable names that match in more than one place without conflict between the same-named objects and/or messages. In object and message names, this arises from the fact that objects and their messages can be address from outside the object only through their full parentage. In the names of variables used in messages, it arises from the fact that message arguments are automatically created as local variables, and local variables are normally used when declared inside message definitions. See also Access Method; Encapsulation; Local Variable; Overloading. A movable window, fixed in size, in which users provide information that is required by an application so it can continue a user request. See also Menu bar Pulldown. A programming style which places emphasis on algorithmic description, or how a procedure works. Procedural programs are built out of procedures and global data used by the procedures. Data, when considered at all, is secondary, global, and often considered unrelated to procedures. See also ObjectOriented Programming. A block of code inside an object which incorporates a set of commands that jointly define messages sent to the object. The message is defined using the set and send commands. It is defined by the procedure and end_procedure commands. Procedures can receive and/or send messages. Procedures can not be nested. They are like a subroutine in procedural code. See also Command; Delegate; Function; Message; Object.

Polymorphism

Pop-Up Window

Procedural Programming

Procedure

542

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Property

Definitions The characteristics determining the uniqueness of an object. The characteristics are determined by the class and set by the object itSelf. location is an example of a property. The information in a property may not necessarily have a direct effect on the appearance of an object. A property is simply a data storage area associated with a particular object. They are like predefined variables in DataFlex procedural code. See Menu bar Pulldown. One of three types of numeric representations that can be used as the subject of a command's execution or expression evaluation. A variable or window used for storing number types. Only floating point numbers can be stored in this type, in the range 10306. There is a real command which defines a variable of Type Real. See also Variable; Window. An area in a database file composed of fields (pieces of information) relating to a particular thing. Records are automatically assigned a unique record number when it is created. You can have up to 16.6 million records in a database file and 255 fields within a record. See also Field; File, Database. The process of redrawing all objects on the screen. This is done so that the screen shows the current state of the application or applications. The process of updating an index file. This process is generated by using the DataFlex Index Tool. Its use is to update batch index files and online index files which have become corrupt (due to programming error or hardware failure). See also File, Index.

PullDown Real

Record

Refresh Screen

Reindex

Data Access Corporation

543

Glossary

Discovering Visual DataFlex

Terms Relative Identifier

Definitions A way to access objects which are created as immediate children of that class. The syntax is, the class name, followed by a period, the object name, and `.OBJ'. The identifier is relative in that it is only valid in relation to the class being defined, and cannot be used outside the class definition structure. A relative identifier is quicker and easier to use within a class definition, and is the preferred method to reference objects in class definitions. See also Class; Object. The shifting of the current focus from one object to another in the Focus List. See also Focus List; Object. A set of objects that are meant to be accessed as a single unit. When a parent object has its scope_state set to true, all of its children are within the scope. Objects which have the scope_state set to true are accessed by the msg_entering_scope and msg_exiting_scope messages. Scopes are used to isolate parts of the application which are independent of each other. See also Message; Object; Property. The class, all of the values of all the properties of an object and its children. If any of these change then the object has changed state. A property which may have one of two values. Examples would be on/off, true/false, right/left. A property which has some number of finite values greater than two is generally referred to as a mode. See also Mode, Property. A command used to create a variable of type ASCII, representing a string of characters which will have a consistent meaning (but with contents that vary). The variable created will default to 80 characters in length, if the length is not specified in the command line (i.e., string varname 40; this will create a variable of type ASCII called varname with a length of 40 characters). See also Variable. A naming convention denoting a descendent class; a class which inherits from another class. See also Inheritance; Superclass.

Rotate

Scope

State, Object

State, Property

String

Subclass

544

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Subimage Subroutine

Definitions See Image, Shared. A block of code created after the end of the program (abort or system command). A subroutine is defined with a label and normally ends with a return command. A subroutine is accessed by a gosub control command with the label identifying the subroutine. Subroutines are read by the compiler once (saves compile lines). They are created to stop redundant coding (same block of code is used in several places). See also Label. A class used to base a class-creation block on. An ancestor or parent of a class which provides properties and messages for its descendent to inherit. See also Class; Class, Base; Inheritance; Subclass. Many packages create commands exclusively for use with objects created from the class defined in the package. These commands are discussed in the "Support Commands" section of the documentation of each package. See File Sequential.

Superclass

Support Command, Package

Text

UIMS

User Interface Management System (UIMS) is a programming environment in which DataFlex programmers can create and maintain attractive, intuitive, and powerful user interfaces for applications. A procedure in the Data_Set class called during new & edit saves that allows the programmer to code during a lock state (such as maintaining running totals). Like Enter.Save The primary documentation of how to use a class defined by a package. This section documents the basic use and syntax of the package as well all the messages and attributes which we expect you to use under "normal" circumstances. Includes a file into the code if it has not already been included. Like #INCLUDE command.

Update Procedure

Usage, Package

Use Command

Data Access Corporation

545

Glossary

Discovering Visual DataFlex

Terms User Interface

Definitions The method by which the program communicates with the user. Examples are popupMenus, pop-up screens, error and prompt messages, scrolling windows, accelerator keys, etc. See also Event-Driven Interface. Validation refers to the process of determining whether some specified data meets a set of criteria. For example, before we save a new record, we might wish to validate it by checking that all the fields had been filled in with acceptable entries. In reference to the items of an object, value generally refers to the data which that item holds. For example, the value of a particular item of a list would be the text displayed in that item. Data values that can be changed in the course of a program's execution. They are stored in memory, and are of a fixed length. Variable names may be up to 80 characters in length, must begin with a letter, and may not contain a space. The data types stored in variables are Date, Numeric, Real and String. Once a variable is designated a data type it can contain information consistent with its type. If data is not of the same type it will convert it to the proper type when it is moved (see move command in the DataFlex Command Reference). See also Date; Number; Real; String. A method of reading data into the buffer from disk. Virtual objects only read the data necessary for interaction, as opposed to batch objects which read all of the data at once. This method of reading data is useful when handling large amounts of data. See also Object. A section of code (usually encapsulated in an Entry_View_Client Object and activated by way of selection from a pulldown menu). That handles one aspect of a large application. E.g., The data-entry section allowing customer entry. These independent views are coded and tested stand alone and then combined with other views to create an application.

Validate

Value

Variable

Virtual

View

546

Data Access Corporation

Discovering Visual DataFlex

Glossary

Terms Window

Definitions An area of an image designated for data output. A window is formatted to accept one of three data types (ASCII, Numeric, or Date). Data is validated based on the format given to the window. They are addressed by reference to the name of the image of which they are a component, and their sequential position in that image (i.e., move body.2 to body.6, copies the contents of the second window in the image called body to the sixth window of the image called body). The sequence is established by numbering the windows on each line from left to right, moving from the top to the bottom lines of the image. See also Current Image; Current Window; Image. 1) The DataFlex language has always used this to refer to an area of the screen with visible boundaries through which information is displayed. A window can be smaller than or equal in size to the screen. 2) A choice in the menu bar of multiple-document interface applications. See also Image. A system of numbering which uses zero as the first number (starts with 0). For example, the numbering of all items in objects is zero-based. This means that the first item in an object is always Item 0, not Item 1.

Window

Zero-Based

Data Access Corporation

547

Glossary

Discovering Visual DataFlex

548

Data Access Corporation

Evaluation
Visual DataFlex Class & Manual
Students completing a class, please fill out both parts A and B. Students using the manual as a Self taught course, please answer only part B. When complete, simply pull this page out, fold on dotted line, tape where indicated, stamp, and drop in the mail. Part A: Date: Location: Instructor: ________________________ ________________________ ________________________ ____

Would you recommend the class to a friend? Part B:

Please rate the following on a scale from 1 to 10 (10 being the best) Class overall? Instructor? Training manual? Handouts and other training media? ____ ____ ____ ____

Additional Comments: _______________________________________________________________________ _______________________________________________________________________ _______________________________________________________________________ _______________________________________________ Training Manual errors: Page Number ___________ ___________ ___________ ___________ Discrepancy _______________________________________________ _______________________________________________ _______________________________________________ _______________________________________________

Thank you for your comments. -------------------------------------------------------------

Data Access Worldwide Training Dept. 14000 S.W. 119 Avenue Miami, FL USA 33186-6017

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

tape here

You might also like