fpc/fcl/db/datasource.inc

554 lines
9.5 KiB
PHP

{ ---------------------------------------------------------------------
TDatalink
---------------------------------------------------------------------}
Constructor TDataLink.Create;
begin
Inherited Create;
FBufferCount:=1;
FDatasourceFixed:=False;
end;
Destructor TDataLink.Destroy;
begin
Factive:=False;
FEditing:=False;
FDataSourceFixed:=False;
DataSource:=Nil;
Inherited Destroy;
end;
Procedure TDataLink.ActiveChanged;
begin
end;
Procedure TDataLink.CheckActiveAndEditing;
Var
B : Boolean;
begin
B:=Assigned(DataSource) and (DataSource.State<>dsInactive);
If B<>FActive then
begin
FActive:=B;
ActiveChanged;
end;
B:=Assigned(DataSource) and (DataSource.State in dsEditModes) and Not FReadOnly;
If B<>FEditing Then
begin
FEditing:=B;
EditingChanged;
end;
end;
Procedure TDataLink.CheckBrowseMode;
begin
end;
Function TDataLink.CalcFirstRecord(Index : Integer) : Integer;
{ recalculates index of first record in buffer,
and returns number of record scrolled.}
Var
A, // Index of active record in buffer
F, // Index of current first record in buffer
L : Integer; // index of Last (for us) record in buffer;
begin
Result:=0;
A:=DataSource.DataSet.FActiveRecord;
F:=FFirstRecord+Index;
L:=F+FBufferCount-1;
If A>L Then
Result:=A-L
else If A<F Then
Result:=A-F;
FFirstRecord:=F+Result;
{$IfDef dsDebug}
WriteLn('CalcFirstRecord: FFirstRecord=',FFirstRecord,' Scrolled=',Result);
{$Endif}
end;
Procedure TDataLink.CalcRange;
var
aMax, aMin: integer;
begin
aMin:= DataSet.FActiveRecord - FBufferCount + 1;
If aMin < 0 Then aMin:= 0;
aMax:= Dataset.FBufferCount - FBufferCount;
If aMax < 0 then aMax:= 0;
If aMax>DataSet.FActiveRecord Then aMax:=DataSet.FActiveRecord;
If FFirstRecord < aMin Then FFirstRecord:= aMin;
If FFirstrecord > aMax Then FFirstRecord:= aMax;
If (FfirstRecord<>0) And
(DataSet.FActiveRecord - FFirstRecord < FBufferCount -1) Then
Dec(FFirstRecord, 1);
end;
Procedure TDataLink.DataEvent(Event: TDataEvent; Info: Ptrint);
begin
Case Event of
deFieldChange,
deRecordChange :
If Not FUpdatingRecord then
RecordChanged(TField(Info));
deDataSetChange:
begin
SetActive(DataSource.DataSet.Active);
CalcFirstRecord(Info);
DatasetChanged;
end;
deDataSetScroll:
DatasetScrolled(CalcFirstRecord(Info));
deLayoutChange:
begin
CalcFirstRecord(Info);
LayoutChanged;
end;
deUpdateRecord:
UpdateRecord;
deUpdateState:
CheckActiveAndEditing;
deCheckBrowseMode:
CheckBrowseMode;
deFocusControl:
FocusControl(TFieldRef(Info));
end;
end;
Procedure TDataLink.DataSetChanged;
begin
RecordChanged(Nil);
end;
Procedure TDataLink.DataSetScrolled(Distance: Integer);
begin
DataSetChanged;
end;
Procedure TDataLink.EditingChanged;
begin
end;
Procedure TDataLink.FocusControl(Field: TFieldRef);
begin
end;
Function TDataLink.GetActiveRecord: Integer;
begin
Result:=Dataset.FActiveRecord - FFirstRecord;
end;
Function TDatalink.GetDataSet : TDataset;
begin
Result:=FDataSource.DataSet
end;
Function TDataLink.GetBOF: Boolean;
begin
Result:=DataSet.BOF
end;
Function TDataLink.GetBufferCount: Integer;
begin
Result:=FBufferCount;
end;
Function TDataLink.GetEOF: Boolean;
begin
Result:=DataSet.EOF
end;
Function TDataLink.GetRecordCount: Integer;
Var D : TDataSet;
begin
Result:=Dataset.FRecordCount;
If Result>BufferCount then
Result:=BufferCount;
end;
Procedure TDataLink.LayoutChanged;
begin
DataSetChanged;
end;
Function TDataLink.MoveBy(Distance: Integer): Integer;
begin
Result:=DataSet.MoveBy(Distance);
end;
Procedure TDataLink.RecordChanged(Field: TField);
begin
end;
Procedure TDataLink.SetActiveRecord(Value: Integer);
begin
{$ifdef dsdebug}
Writeln('Datalink. Setting active record to ',Value,' with firstrecord ',ffirstrecord);
{$endif}
Dataset.FActiveRecord:=Value + FFirstRecord;
end;
Procedure TDataLink.SetBufferCount(Value: Integer);
begin
If FBufferCount<>Value then
begin
FBufferCount:=Value;
if Active then begin
DataSet.RecalcBufListSize;
CalcRange;
end;
end;
end;
procedure TDataLink.SetActive(AActive: Boolean);
begin
if Active <> AActive then
begin
FActive := AActive;
// !!!: Set internal state
ActiveChanged;
end;
end;
Procedure TDataLink.SetDataSource(Value : TDatasource);
begin
if not FDataSourceFixed then
begin
if Assigned(DataSource) then
Begin
DataSource.UnregisterDatalink(Self);
FDataSource := nil;
CheckActiveAndEditing;
End;
FDataSource := Value;
if Assigned(DataSource) then
begin
DataSource.RegisterDatalink(Self);
CheckActiveAndEditing;
End;
end;
end;
Procedure TDatalink.SetReadOnly(Value : Boolean);
begin
If FReadOnly<>Value then
begin
FReadOnly:=Value;
CheckActiveAndEditing;
end;
end;
Procedure TDataLink.UpdateData;
begin
end;
Function TDataLink.Edit: Boolean;
begin
If Not FReadOnly then
DataSource.Edit;
// Triggered event will set FEditing
Result:=FEditing;
end;
Procedure TDataLink.UpdateRecord;
begin
FUpdatingRecord:=True;
Try
UpdateData;
finally
FUpdatingRecord:=False;
end;
end;
{ ---------------------------------------------------------------------
TDetailDataLink
---------------------------------------------------------------------}
Function TDetailDataLink.GetDetailDataSet: TDataSet;
begin
end;
{ ---------------------------------------------------------------------
TMasterDataLink
---------------------------------------------------------------------}
constructor TMasterDataLink.Create(ADataSet: TDataSet);
begin
end;
destructor TMasterDataLink.Destroy;
begin
inherited Destroy;
end;
Procedure TMasterDataLink.ActiveChanged;
begin
end;
Procedure TMasterDataLink.CheckBrowseMode;
begin
end;
Function TMasterDataLink.GetDetailDataSet: TDataSet;
begin
end;
Procedure TMasterDataLink.LayoutChanged;
begin
end;
Procedure TMasterDataLink.RecordChanged(Field: TField);
begin
end;
procedure TMasterDatalink.SetFieldNames(const Value: string);
begin
end;
{ ---------------------------------------------------------------------
TDatasource
---------------------------------------------------------------------}
Constructor TDataSource.Create(AOwner: TComponent);
begin
Inherited Create(AOwner);
FDatalinks:=TList.Create;
FEnabled:=True;
FAutoEdit:=True;
end;
Destructor TDataSource.Destroy;
begin
FOnStateCHange:=Nil;
Dataset:=Nil;
With FDataLinks do
While Count>0 do
TDatalink(Items[Count - 1]).DataSource:=Nil;
FDatalinks.Free;
inherited Destroy;
end;
Procedure TDatasource.Edit;
begin
If (State=dsBrowse) and AutoEdit Then
Dataset.Edit;
end;
Function TDataSource.IsLinkedTo(ADataSet: TDataSet): Boolean;
begin
Result:=False;
end;
procedure TDatasource.DistributeEvent(Event: TDataEvent; Info: Ptrint);
Var
i : Longint;
begin
With FDatalinks do
begin
For I:=0 to Count-1 do
With TDatalink(Items[i]) do
If Not VisualControl Then
DataEvent(Event,Info);
For I:=0 to Count-1 do
With TDatalink(Items[i]) do
If VisualControl Then
DataEvent(Event,Info);
end;
end;
procedure TDatasource.RegisterDataLink(DataLink: TDataLink);
begin
FDatalinks.Add(DataLink);
if Assigned(DataSet) then
DataSet.RecalcBufListSize;
end;
procedure TDatasource.SetDataSet(ADataSet: TDataSet);
begin
If FDataset<>Nil Then
Begin
FDataset.UnRegisterDataSource(Self);
FDataSet:=nil;
ProcessEvent(deUpdateState,0);
End;
If ADataset<>Nil Then
begin
ADataset.RegisterDatasource(Self);
FDataSet:=ADataset;
ProcessEvent(deUpdateState,0);
End;
end;
procedure TDatasource.SetEnabled(Value: Boolean);
begin
FEnabled:=Value;
end;
Procedure TDatasource.DoDataChange (Info : Pointer);
begin
If Assigned(OnDataChange) Then
OnDataChange(Self,TField(Info));
end;
Procedure TDatasource.DoStateChange;
begin
If Assigned(OnStateChange) Then
OnStateChange(Self);
end;
Procedure TDatasource.DoUpdateData;
begin
If Assigned(OnUpdateData) Then
OnUpdateData(Self);
end;
procedure TDatasource.UnregisterDataLink(DataLink: TDataLink);
begin
FDatalinks.Remove(Datalink);
If Dataset<>Nil then
DataSet.RecalcBufListSize;
//Dataset.SetBufListSize(DataLink.BufferCount);
end;
procedure TDataSource.ProcessEvent(Event : TDataEvent; Info : Ptrint);
Const
OnDataChangeEvents = [deRecordChange, deDataSetChange,
deDataSetScroll,
deLayoutChange,deUpdateState];
Var
NeedDataChange : Boolean;
FLastState : TdataSetState;
begin
// Special UpdateState handling.
If Event=deUpdateState then
begin
NeedDataChange:=(FState=dsInactive);
FLastState:=FState;
If Assigned(Dataset) then
FState:=Dataset.State
else
FState:=dsInactive;
// Don't do events if nothing changed.
If FState=FlastState then
exit;
end
else
NeedDataChange:=True;
DistributeEvent(Event,Info);
// Extra handlers
If Not (csDestroying in ComponentState) then
begin
If (Event=deUpdateState) then
DoStateChange;
If (Event in OnDataChangeEvents) and
NeedDataChange Then
DoDataChange(Nil);
If (Event = deFieldChange) Then
DoDataCHange(Pointer(Info));
If (Event=deUpdateRecord) then
DoUpdateData;
end;
end;