Skip to content

Class: cCJGridDataSource

Properties | Events | Methods | Index of Classes

Provides data storage and data management capabilities for a cCJGrid.

Hierarchy

Library: Windows Application Class Library
Package: cCJGridDataSource.pkg

Description

A datasource object provides all data services to the grid. It either provides the data storage or provides access to the data. It also handles all data manipulation requirements, such as adding rows, removing rows, and editing cells.

The grid object itself actually knows nothing about the data it displays. The cCJGrid relies on its datasource object, cCJGridDataSource, to provide and manage its data. It relies on its grid column objects (cCJGridColumn) to provide column-related data processing services.

When a grid object is created, it creates an appropriate datasource object for the grid class. A cCJGrid creates a cCJGridDataSource object; a cDbCJGrid creates a cDbCJGridDataSource object. Access to this datasource object is accessed via the grid's phoDataSource property.

The datasource abstract interface

A set of abstracted interfaces is defined to handle all communication between the datasource object and the grid. As long as this interface is supported, the datasource object can manage and store its data in any way it wants. For example, the cCJGridDataSource class used by the cCJGrid loads all data into the datasource. The data is maintained in a tDataSourceRow array, and all changes are kept local to this array. The cDbCJGridDataSource class used by the cDbCJGridClass has a far more sophisticated and complicated data manipulation capability. Data can be partially loaded with parts of the data being cached in and out as needed. Data is loaded by using a DataDictionary object (DDO). Changes made to the data are made through this DDO. Although these two datasource classes are very different, the grid object knows nothing about these differences and uses the same interface to access either datasource.

You will never use or augment most of the messages documented in this class. The grid class already uses these interfaces as needed, and there will be little need to call them yourself. In fact, calling the wrong method at the wrong time can do more harm than good. These interfaces can be augmented, but this should also be done very carefully. Before making any changes, you are encouraged to review the existing code in the packages.

If desired, you could extend a set of grid, column, and datasource classes to handle a completely different type of data. This would be considered advanced use. Extending the datasource class might involve extending the grid and column classes as well. If you do this, you will probably want to extend from the static classes (cCJGrid, cCJGridColumn, and cCJGridDataSource).

The communication between a grid and a datasource object is one-way. The grid sends messages to the datasource, while the datasource never directly sends messages to the grid. A DataDictionary-enabled datasource will send messages to its DDO, which may send messages to the grid. The DDO never sends messages directly to the datasource. The grid column objects send messages to the datasource, and the datasource has a limited set of messages, which it sends to the grid column object (actually, it sends it to the grid column object's column-datasource object).

Unless you are planning on building your own datasource subclass, most of this information can all be considered to be internal implementation detail.

The Interfaces you are likely to use

There are a few messages that you might use in your object code. The most important are:

  • SelectedRow: Use this to determine which row is selected. Selecting a row is handled by the grid through either user navigation or a move-to-row message such as MoveToRow.
  • DataSource: If your grid is static, you are likely to use DataSource to return your datasource's tDataSourceRow array for further processing. Loading a static datasource is handled by the grid object's InitializeData method.

Other messages you might use are:
- AllDataIsLoaded
- CreateDatasourceRow
- DataIsStatic
- IsSelectedRowChanged
- IsSelectedRowNew
- ShouldSaveSelectedRow

How to assign a new datasource to a grid

If you create a new datasource class, you can bind it to your grid subclass with the grid's CreateDataSource function. This ensures that all instances of this grid subclass will use the datasource subclass. This technique can only be used at the class level.

Class cMyCJGrid is a cCJGrid
    :
    Function CreateDataSource Returns Handle
        Handle hoDataSource
        Get Create (RefClass(cMyCJGridDataSource)) to hoDataSource
        Function_Return hoDataSource
    End_Procedure
    :
End_Class  

If you wish to create a custom datasource instance at the grid object level, you may create the datasource object in your grid object and bind it to the grid by setting the phoDataSource property. You should rarely need to do this, as most required customizations are handled at the grid object level without needing to change the datasource.

In this example, we will change the rule for determining if a new, unchanged row should be considered savable. This will determine if navigating away from a new, unchanged row should save the row (the default for cCJGrid) or remove the row (the default for cDbCJGrid). If we wanted to change the cCJGrid behavior, we could do this:

Object oCJGrid is a cCJGrid
    :
    Object oDatasource is a cCJGridDataSource
        Delegate Set phoDataSource to Self

        Function ShouldSaveSelectedRow Returns Boolean
            Boolean bChanged
            Get IsSelectedRowChanged to bChanged
            Function_Return (bChanged)
        End_Function
    End_Object
    :
End_Object