[ 1 ] [ 2 ] [ 3 ] [ 4 ] [ 5 ] [ 6 ] [ 7] [ 8 ] [ 9 ]

Session E-HOWX

The VFP 6 Framework andHow to Extend It
 

Lisa Slater Nicholls
lisa@softspoken.co.nz


What this session, and the VFP 6 framework, is for

When the VFP 6 Application Wizard generates an application for you, what has it done, and how can you adapt or extend the results?

In this session, you'll see how the framework uses generic Foundation Class components, and how it implements additional, framework-specific behavior. You'll learn how and why you'd subclass the framework's application object and other framework-specific classes, as well as how to quickly "framework-enable" any form or formset in an VCX or SCX you've created separately.

When you understand the internals of the framework classes and design, you can exploit the framework fully - or incorporate these ideas into your own framework and development practices in completely new ways.

What this session, and the VFP 6 framework, is for

This year, I hope I can assume most VFP developers already understand why frameworks are necessary for developing extensive applications.

You understand the principles of re-use. You have absorbed the value of acquiring and deploying well-designed class libraries. You want to settle on a robust implementation of some approach, and invest yourselves in learning to use that implementation.

Above all you want to get on with your lives! You want to hang application- and business- specific elements off the framework to complete your applications on time and with confidence.

In the past I've encouraged people to build their own frameworks, mining my own work for ideas. I still think that people learn a lot from doing this, and that you'll ultimately get the framework you really want if you build your own.

Now, however, I'm more interested in seeing how a team can benefit from using a framework than what they learn in building it. The short answer to the question "Why this framework?" is: "because it is designed to benefit different types, and levels, of developers working together in a team".

This framework may not fit your working style or the UI you prefer. There may be other reasons why it's not the right framework for you. For one, you may already be very happy with another framework that you use.

In any of these cases, you should be able to graft this thought - a framework should benefit a team and enhance the development experience of all its team members - and some aspects of its implementation onto the framework of your choice.

If that's good enough for you, and if you're not interested in hearing more about my thoughts on developer team interactions - which underscore the "why" of framework use - skip over the balance of this section and go right into the what and how, in the rest of the paper.

The team and the sandbox

Java people use the expression "the sandbox" to talk about the discrete environment in which a Java applet can exercise influence on the client computer. They're talking about keeping the sand in and the weeds and dirt out. These are security and encapsulation issues. In essence they're talking about the limited environment in which the Java developer can "play", when exercising influence through the applet.

In thinking about this, I realized that the sandbox metaphor has a wider, more illuminating validity when applied to frameworks and the development process.

A sandbox isn't a holding pen to keep the kids from crawling around or the adults from getting sandy. A sandbox is a great place to play. A great place to play is not just safe and clean, but fun, and full of opportunity. During truly great play, you learn things, and so does anybody watching you from the periphery.

A really good sandbox has facilities to attract adults on its periphery, because a truly great place to play provides for inter-generational communication. Otherwise no growth occurs on either side of the relationship. The kids might as well be in front of re-runs on television, and the adults might as well be at the office.

Sometimes the adults reach in and suggest a digging toy or another way to improve a construction in progress. Sometimes the kids are occupied without intervention, and the adults are perched on the edge, observing and exchanging comments and ideas amongst themselves.

In standard "pattern-speak", I've just described a model for interaction between elaborators and abstractors. In "team-speak", I've just describe the way I think experienced and apprenticed developers should relate as they go about their daily business of work/play.

I think we need a sandbox-based developer community. How about you?

Building a better sandbox

To make a whole team productive and to give each member job satisfaction, a framework has to give beginners an opportunity to contribute and construct usable application elements. They shouldn't have to know much about the underpinnings of VFP or the framework to do real work (as opposed to exercises).

In this framework, a beginner can construct a form from VFP baseclasses, or your recommended set of baseclasses, or the Wizard-generated classes, or the FFC classes, and this form will be both easy to plug into the application and also properly-behaved under the application. In other words, they can play, learn, build, and cooperate.

To make a whole team productive and to give each member job satisfaction, a framework must give experienced developers scope for decision and choice, without imposing assumptions or limits. It should also be easy to "grow the framework" with these decisions and choices, so that they are shared for use by the less-experienced members of the team in a natural way. In other words, senior members of the team should be able to play, learn, build, and share.

The balance of this paper is about ways this framework allows scope, decision, growth, and choice and (I hope) will give you the idea that there are very few limits indeed. That's practically an experienced VFP developer's definition of a "great place to play", right there!

Shall we get on with it, then?

What you get

The VFP 6 framework application object is a direct descendent of the VFP 5 framework object (not the application object in Tastrade, but rather the one that the VFP 5 Application Wizard generated). If you ever generated one of the template applications in VFP 5, some aspects of this application object will be familiar immediately.

NOTE: If you generated a VFP 5 application and wish to bring it into the new framework, in fact, almost everything will work perfectly. The only problems you're likely to find are a few Set… and Get… methods you may have executed (some of these have been changed to assign and access methods in the new application object). You may also have to adjust the main program slightly, using the application-specific header file that the new wizard supplies.

On the other hand, this new member of the family has:

  • over 200 new custom properties and methods
  • a host of new members
  • a raft of new supporting classes
  • a new and non-main-program-dependent method of instantiation
  • the ability to manage toolbars and forms in a "top form", true MDI-type application
  • the ability to create modular applications that hook together under one READ EVENTS or exist in the VFP development environment
  • many new features borrowed from the FFC components delivered with the product
  • integration with the Project Manager and a new Application Builder through the VFP 6 Project Hook feature

The last two items I mentioned are especially significant. To be efficient, a framework should make use of as many standard components as possible. To meet our goals of effective team use, a framework has to be well-integrated into the VFP development environment.

If you create a form and incorporate it into a framework application, you shouldn't have to work hard to tell the framework or the application it's there. The Application Builder and Project Hook give you this facility.

When you start a new application, to meet our goals of extensibility, the creation of each new application should go smoothly and allow you to specify whatever you like about the generated components. The Application Wizard does the "smooth" part, and later on in this paper I'll show you how to specify all the App Wizard's generated pieces without sacrificing any "smooth".

Jack-in-the-box is jack-of-all-trades

Because this framework is delivered in the box with VFP, it has a good opportunity to integrate smoothly with the other features in the box, including the project hook.

The project hook, in my view, is the critical feature that VFP framework developers have been waiting for as long as there's been a Fox PJX file and APP format. Of course, this is also its opportunity to teach you how you can integrate your framework with these features.

Because this framework is in the box, also, it is limited in the assumptions it can make. It doesn't expect you to follow any particular theory or practice when it comes to your main job, data handling. It will accept any form of data buffering and will behave the same way whether you open your tables in the Load, the Init, or the Data Environment. It will be happy to instantiate forms or formsets, from VCXs or SCXs.

To be as accepting as I've just indicated it is, this framework must be unusually stingy about use of the OOP practice known as collaboration. There is no collaboration required of application-specific items you add into a framework application, whether they're toolbars, forms, or reports. They can collaborate -- you'll see that the framework tries to make it easy for them to access various application features -- it's just not required that they do so.

To use another, more formal, way to express this idea: the VFP 6 framework is tightly coupled to some FFC components to provide its core functionality, but it is extremely loosely coupled to application elements you add.

What gives it to you:
a summary of generated and automated components

Here's a high-level summary of the way the framework features are delivered to you.

  1. The Application Wizard takes your choices for a location and project name, and generates a project file. It adds a class library with appropriate application-specific subclasses of the framework's own class library. To distinguish these generated classes, it adds a special prefix to them all. It adds template-generated, application specific versions of all the non-OOP components the application needs. It adds a special suffix to distinguish generated files from other files in your application. You can see these class- and file- naming conventions in the sample project shown in the first figure below.
  2. The Application Builder provides an interface you can use to customize the framework aspects of any framework-enabled project, throughout the life of the project. It creates a natural "bridge" between the data sources that are the life-blood of any FoxPro application and the documents users need to gather and then display results of this data. It allows users easy and organized access to the other VFP Wizards that generate application-specific pieces, including these documents and the underlying data.
  3. Throughout the life of the project, also, the associated Project Hook object for a framework-enabled project can help incorporate any new files you add directly to the project, alerting the framework elements to these new files as necessary.
  4. At runtime, a framework-enabled application generates some additional application files as needed (primarily a user preferences table and, when errors occur, an error log).
  5. All these features and files are usable as is. Although a few of the supporting classes are primarily meant as teaching examples, none are samples you need to "fix" before they can go into your application. None use "demonstration data" or other inappropriate assumptions for a shipping application. That helps beginners drive the framework automatic-transmission style. When you're interested in doing more work, almost all can be easily swapped for versions that you prefer, and all can be customized. That means experienced developers can switch to stick shift whenever they want.

What else you get

Before we go on to "how you get it" in detail, I'd like to draw your attention to two more of the new features in this application framework, which are conceptual in nature.

Flexible application types

The framework generates multiple application "types". This is an example of the framework's attempt to do whatever VFP 6 can do, without imposing restraints on you.

A "framework-enabled project" generated by Application-Wizard has files and classes with some standard naming conventions provided by the Wizard. The Application Builder customizes the generated project, and makes it easy for you to adjust framework choices.

As you can see in the Application Builder, there are "normal", "top form" and "module" application types available. By "normal", the Builder means one in which a VFP application takes over _SCREEN, owns various global properties (such as SYSMENU, or the ability to CLEAR MACROS or issue ON SHUTDOWN and ON ERROR commands), and generally brings other activity to a grinding halt until it finishes executing. When it's good and ready, a "normal" application has a chance to restore earlier values of these global attributes before returning control to anybody.

In VFP, as you know, this control of the environment is usually accomplished with a READ EVENTS statement.

By contrast, some applications have to fit in wherever they're called. Such an app may be a modaless application you run during your development work. It may also be a subsidiary application in a larger application you've already built, which just adds an extra menu pad and choices.

Think of the power of this idea: you can take your already-built application and give it framework features without touching the rest of it, and without worrying that this new "framework module" will have untoward effect on your application's global environment.

Think, also, about building a new, large application out of a bunch of modules, simply by instantiating two or more framework module application, even deciding at runtime which ones should exist. The framing program may be another framework app, or it may be a bare-bones PRG that instantiates the appropriate modules and adds a READ EVENTS (or not).

Now think a little more about how you may want these applications to look. Some applications that "own the VFP session" (use a READ EVENTS) may not work well in _SCREEN. They're more manageable in a separate MDI frame. A separate frame gives you a more controllable MDI parent window than _SCREEN, with triggered events you can program like those of other forms. Some applications that act within other applications, or within the VFP development environment, may deserve their own frame as well. Think of the Debugger as an example.

These are all things VFP knows how to do. The framework has many properties and methods designed to make them easy to do.

The designations "normal", "module", and "top" are just the Builder's way of presenting a whole lot of complicated property settings and choices available within the framework.

There isn't really any such thing as a "normal" app in the framework, there are just some "applications that issue READ EVENTS and are allowed to take over the environment" and "others that aren't". A "top form" app may share many features with a "normal" or a "module" framework, depending on what it is supposed to do. A module may, of course, be added into a top form app as well as a _SCREEN-bound one.

Are these choices, as presented by the Application Builder, the only ways to mix and match these VFP features and the only possible application types in the framework? No, of course not. You can change the property assignments of the application object yourself and come up with other combinations. And other application types may be made visible in the Application Builder at some point, too.

NOTE: The minimal nature of this startup code is deliberate. Among the application types this framework will be able to support in the future, obviously the ActiveDoc is a desirable addition. ActiveDocs don't require a main program at all. They also do not require a READ EVENTS-type environment, which is one significant reason the VFP 6 framework has been engineered to work without requiring a READ EVENTS wait state.

[ 1 ] [ 2 ] [ 3 ] [ 4 ] [ 5 ] [ 6 ] [ 7] [ 8 ] [ 9 ]