I've been having a problem with some code which is supposed to process a TClientDataSet's Delta, which I've boiled down to the following test case.
I have two ClientDataSets, cdsData and cdsDelta, both with a DataSource, DBGrid and DBNavigator, and a TTreeView for displaying the Delta's Old- and NewValues.
In cdsDatas AfterPost, I call the DisplayDelta procedure below.
When I run the app, I change and save the value of one field in csdData from, say, 'PrevValue' to 'UpdatedValue'. My problem is that both the OldValue and NewValue nodes in the Treeview display 'UpdatedValue' and there is no sign of 'PrevValue'. So, how do I get the OldValue correctly?
procedure TDeltaTestForm.DisplayDelta;
var
Delta : OleVariant;
begin
Delta := cdsData.Delta;
if not VarIsClear(Delta) then begin
cdsDelta.Data := Delta;
end;
if cdsData.Modified then
Caption := 'modified'
else
Caption := '';
Caption := Caption + '/' + IntToStr(cdsData.ChangeCount);
BuildDeltaTree;
end;
procedure TDeltaTestForm.BuildDeltaTree;
var
NewNode,
ChildNode : TTreeNode;
i,
ID : Integer;
Field : TField;
Value : String;
function ChildValue(ALabel : String; FieldValue : Variant) : String;
begin
Result := ALabel;
if VarIsClear(FieldValue) then
Result := Result + '(empty)'
else
if VarIsNull(FieldValue) then
Result := Result + '(null)'
else
Result := Result + VarToStr(FieldValue);
end;
begin
{ Find the current row in the delta dataset }
ID := cdsData.FieldByName('ID').AsInteger;
if not cdsDelta.Locate('ID', ID, []) then
raise Exception.CreateFmt('ID: %d not found in Delta', [ID]);
TreeView1.Items.BeginUpdate;
try
Treeview1.Items.Clear;
for i:= 0 to cdsDelta.FieldCount - 1 do begin
Field := cdsDelta.Fields[i];
NewNode := TreeView1.Items.AddChild(Nil, Field.FieldName);
ChildNode := TreeView1.Items.AddChild(NewNode, ChildValue('Old: ', Field.OldValue));
ChildNode := TreeView1.Items.AddChild(NewNode, ChildValue('New: ', Field.NewValue));
ChildNode := TreeView1.Items.AddChild(NewNode, ChildValue('Cur: ', Field.CurValue));
end;
TreeView1.FullExpand;
finally
TreeView1.Items.EndUpdate;
end;
end;