On 9/25/18 8:03 PM, mohamed hamza wrote:
> I believed that filter  has been set somewhere by a module of lib and set 
> filtred  to true also. I find that I am wrong ?
> 
AFAIK TSQLQuery.Filter will be added to TSQLQuery.SQL text:
"
Function TSQLQuery.AddFilter(SQLstr : msestring) : msestring;

begin
  if FWhereStartPos = 0 then
    SQLstr := SQLstr + ' where (' + msestring(Filter) + ')'
  else if FWhereStopPos > 0 then
    system.insert(' and ('+msestring(Filter)+') ',SQLstr,FWhereStopPos+1)
  else
    system.insert(' where ('+msestring(Filter)+') ',SQLstr,FWhereStartPos);
  Result := SQLstr;
end;
"
which filters the result set on server if "Filtered" is true. I never
used that functionality. The dbfilter2 demo uses "onfilterrecord" in
order to filter records locally:
"
procedure tmainfo.onfilterrecordev(dataset: tdataset; var accept: boolean);
//slow! in order to improve performance use
//local copies of the filter values, don't use variants
begin
 accept:= tmsebufdataset(dataset).checkfiltervalues();
end;
"

which checks the set filter values:

"
function tmsebufdataset.checkfiltervalue(const afield: tfield;
                       const akind: filtereditkindty = fek_filter;
                           const acaseinsensitive: boolean = true): boolean;
var
 i1: int32;
 p1: precheaderty;
 v1: variant;
 b1: boolean;
begin
 if afield.dataset <> self then begin
  databaseerror('Invalid field "'+afield.name+'"',self);
 end;
 result:= true; //default
 i1:= afield.fieldno-1;
 p1:= @ffilterbuffer[akind]^.header;
 if i1 >= 0 then begin //data field
  b1:= not getfieldflag(p1^.fielddata.nullmask,i1);
 end
 else begin //calc field
  i1:= -2 - i1;
  if i1 >= 0 then begin //calc field
   b1:= not getfieldflag(pointer(p1)+frecordsize,i1);
  end
  else begin
   exit;//invalid field
  end;
 end;
 if not b1 then begin //filter not null
  b1:= afield.isnull;
  v1:= fieldfiltervalue(afield,akind);
  if afield.datatype = ftstring then begin
   if acaseinsensitive then begin
    i1:= unicodecomparetext(afield.asmsestring,unicodestring(v1));
   end
   else begin
    i1:= unicodecomparestr(afield.asmsestring,unicodestring(v1));
   end;
   case akind of
    fek_filtermin: begin
     result:= not b1 and (i1 >= 0);
    end;
    fek_filter: begin
     result:= i1 = 0;
    end;
    fek_filtermax: begin
     result:= b1 or (i1 <= 0);
    end;
   end;
  end
  else begin
   case akind of
    fek_filtermin: begin
     result:= not b1 and (afield.value >= v1);
    end;
    fek_filter: begin
     result:= afield.value = v1;
    end;
    fek_filtermax: begin
     result:= b1 or (afield.value <= v1);
    end;
   end;
  end;
 end;
end;

function tmsebufdataset.checkfiltervalues(const afield: tfield;
                           const acaseinsensitive: boolean = true): boolean;
        //calls checkfiltervalue() for all filtereditkinds
var
 f1: filtereditkindty;
begin
 for f1:= low(f1) to fek_filtermax do begin
  result:= checkfiltervalue(afield,f1,acaseinsensitive);
  if not result then begin
   break;
  end;
 end;
end;

function tmsebufdataset.checkfiltervalues(
                          const acaseinsensitive: boolean = true): boolean;
        //calls checkfiltervalue() for all fields and all filtereditkinds
var
 i1: int32;
begin
 result:= true;
 for i1:= 0 to fields.count-1 do begin
  result:= checkfiltervalues(fields[i1],acaseinsensitive);
  if not result then begin
   break;
  end;
 end;
end;
"

> Concerning the second point I can not see why dbfilter2  will run normally  
> with bdo_local option and a database will not ?
> 
With the same fields and field types?

> I used the same event manager than dbfilter2. Are there other methods to 
> manage filter ?
> 
There can be any code executed in onfilterrecord in order to define if a
record should be visible.

Martin


_______________________________________________
mseide-msegui-talk mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/mseide-msegui-talk

Reply via email to