|
|
 |
 |
|
Join the Discussion
|
"Post your views, comments, questions and doubts to this article."
Discuss!
|
|
 |
 |
|
|
 |
 |
 |
While Delphi provides handful of data-aware controls (located on the "Data Controls" tab of the Component Palette) you can use in database applications, you might sometimes want to make an "ordinary" control data-aware. Being data-aware means that a control can automatically display the values associated with field components.
How to make a control data-aware?
Every data-aware control is connected to a data source using the DataSource property. This connection between a control and a data source is called a data link and is controlled by a TDataLink object. In general, to make a non-data-aware control data-aware, you need to equip it with a TDataLink - "provider" of the DataSource and DataField properties (and some other). You then handle an event or two ... and you have your own data-aware version of an ordinary control.
Creating a data-aware button control
While this may sound like a crazy idea, a data-aware TButton control can turn to be quite usable. A TDBButton is, by default, a read-only data-aware control. It can only display data from a data source (much like the TDBText control), but can also react on a user click-action.
Here's the full source code to the TDBButton control - the one that displays the value of a field
in a caption of a button.
The TDBButton derives from a standard TButton control and adds several properties of a TFieldDataLink object (DataSource, Field, DataField). The most important code is in the DataChange procedure - the one that handles the OnDataChange event of the data-link. This code gets executed each time when the contents of the associated field changes. If the field value is NULL we disable the button, otherwise we use the AsString method of the TField object to display the value in the Button's Caption property.
unit DBButton;
interface
uses
DB, DBCtrls, SysUtils, Classes,
Controls, StdCtrls;
type
TDBButton = class(TButton)
private
FDataLink : TFieldDataLink;
function GetDataField: string;
function GetDataSource: TDataSource;
function GetField: TField;
procedure SetDataField(const Value: string);
procedure SetDataSource(const Value: TDataSource);
protected
procedure DataChange(Sender : TObject);
public
constructor Create(AOwner : TComponent);
override;
destructor Destroy; override;
property Field : TField read GetField;
published
property DataSource : TDataSource
read GetDataSource
write SetDataSource;
property DataField : string
read GetDataField
write SetDataField;
end;
procedure Register;
implementation
procedure Register;
begin
RegisterComponents('delphi.about.com',
[TDBButton]);
end;
constructor TDBButton.Create(AOwner: TComponent);
begin
inherited Create(AOwner);
FDataLink := TFieldDataLink.Create;
FDataLink.Control := self;
FDataLink.OnDataChange := DataChange;
end;
destructor TDBButton.Destroy;
begin
FDataLink.Free;
FDataLink := nil;
inherited;
end;
procedure TDBButton.DataChange(
Sender: TObject);
begin
Caption := FDataLink.Field.AsString;
Enabled := NOT FDataLink.Field.IsNull;
end;
function TDBButton.GetField: TField;
begin
result := FDataLink.Field;
end;
function TDBButton.GetDataField: string;
begin
result := FDataLink.FieldName;
end;
procedure TDBButton.SetDataField(
const Value: string);
begin
FDataLink.FieldName := value;
end;
function TDBButton.GetDataSource: TDataSource;
begin
result := FDataLink.DataSource;
end;
procedure TDBButton.SetDataSource(
const Value: TDataSource);
begin
FDataLink.DataSource := Value;
end;
end. //DBButton
|
Once TDBButton is connected to a datasource, when you move through the dataset, the Caption of the TDBButton reflects the value of the field object specified by the DataField property.
Installing into the Component palette
First, download the component. The TDBButton comes as a single unit file (.pas extension). You'll need to add the component into an existing package. Here's "How to Install Custom Component in Delphi (into Existing Package)"
Questions? Comments? Extensions? Exceptions?!
That's it. If you find this component practical and if you extend it by adding more properties, please send your source and make it available to other developers.
As always if there are any questions or comments please post them on the Delphi Programming Forum.
|