hi,
the following problem:
i need to locate a child dataset on 2 fiels
so master value is 1 and child field1 could be 1 or field2 could be 1 or both
so i set up a devexpress quantumgrid with the given master and as detailkeyfieldnames field1 and field2
now this crashes in
procedure TDAMemoryDataset.InitMemLocateStruct(AStruct: PMemLocateStruct;
const KeyValues: Variant);
more specifically:
if AStruct^.lFields.Count = 1 then
AStruct^.lValues[i].Value := KeyValues
else
AStruct^.lValues[i].Value := KeyValues[i];
since i’m passing 2 fields it seems it expects a variant array with 2 field values…
this is not the case nor can i influence this cause it’s devexpress…
imho i should be able to locate 1 value in 2 tfields of this child dataset?
it depends on your code. you may have fetch details records only for one master row
check the All in one fetch article.
index take attention to M/D relation so it will work
you can create index after table is opened.
the easiest solution - create index in design-time via Object Inspector
all is done in code in our app, no RAD
i’ll modified your source
that will be more clear i guess
basically i need to display the childs of a given master depending wether child.F1 OR child.F2 equals the master.F1
and the devex grid tries to locate the detail on fields F1;F2 for 1 given master F1
b:=false;
for j := 1 to 5 do
begin
if b then
DAMemDataTable1.AddRecord(['f1'],[j]) //<<< this will create record with empty child_ID, like [j, NULL]
else
DAMemDataTable1.AddRecord(['f2'],[j]); //<<< this will create record with empty master_ID, like [NULL,j]
b := not b;
end;
DAMemDataTable2.Dataset.Locate('f1;f2',3,[]); //<<< master table has only `f1` field
ok hope this will clear things (see ro.rar)
in fact there is a granddad involved, so both tables in the demo are childs of a granddad
granddad in this case isn’t important
the damaster in the demo is in fact a union of 2 childs of the granddad, and thus they have a ‘childkey’ field and based on there is a marker which child it is, in this case called ‘isF1’
so here’s the deal
in devex i hook both damaster and dachild table in 1 grid, so the details are shown below each master
now devex lets me filter the childs that need to be hooked to the damaster, so i can filter out the recs that do not belong to the damaster based on ‘isF1’ in this case
apparently devex is doing this using locate, so it has to locate on both fields
like this
Accept := False;
AMasterRecord := ADataController.GetMasterRecordIndex;
AMasterDC := ADataController.GetMasterDataController;
if AMasterDC <> nil then
begin
AParentID := AMasterDC.Values[AMasterRecord, detprimkey.Index];
AType := AMasterDC.Values[AMasterRecord, verkooptype.Index];
if AType = 1 then
Accept := AParentID = ADataController.Values[ARecordIndex, dbAnnracvdpprimkey.Index];
if AType = 2 then
Accept := AParentID = ADataController.Values[ARecordIndex, dbAnnracvdmprimkey.Index];
end;
so my demo won’t be able to show the desired behaviour since i can’t filter out the detail data
it has to look at the master for which kind of detail it is and then select that key based on child F1 or F2
//DAchild.Filtered = True;
procedure TForm90.DADataSource2DataChange(Sender: TObject; Field: TField);
begin
if DAMaster.Fields[1].IsNull then begin
DAchild.Filter := '';
end
else begin
if DAMaster.Fields[2].AsBoolean then
DAchild.Filter := 'f1 = '+DAMaster.Fields[1].AsString
else
DAchild.Filter := 'f2 = '+DAMaster.Fields[1].AsString;
end;
end;
but it doesn’t reproduce original callstack
can you reproduce original error with TDAMemDataset.Locate?
doesn’t seem to work with devex
i still have to define the relation in devex to…
and nor tried both child fields as detail fields but then he tries to locate again on ([field1, field2],keyvalue)
and the RO code fails cause it expects an array of variant:
if AStruct^.lFields.Count = 1 then
AStruct^.lValues[i].Value := KeyValues
else
AStruct^.lValues[i].Value := KeyValues[i];