PageRenderTime 36ms CodeModel.GetById 14ms app.highlight 10ms RepoModel.GetById 2ms app.codeStats 0ms

/ideintf/oifavouriteproperties.pas

http://github.com/graemeg/lazarus
Pascal | 664 lines | 540 code | 61 blank | 63 comment | 59 complexity | 96b7b4a68cf5ac2eadc06a21772aa470 MD5 | raw file
  1{ $Id: oifavouriteproperties.pas 17395 2008-11-15 03:53:22Z paul $}
  2{
  3 *****************************************************************************
  4 *                                                                           *
  5 *  See the file COPYING.modifiedLGPL.txt, included in this distribution,    *
  6 *  for details about the copyright.                                         *
  7 *                                                                           *
  8 *  This program is distributed in the hope that it will be useful,          *
  9 *  but WITHOUT ANY WARRANTY; without even the implied warranty of           *
 10 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.                     *
 11 *                                                                           *
 12 *****************************************************************************
 13}
 14unit OIFavouriteProperties;
 15
 16{$MODE OBJFPC}{$H+}
 17
 18interface
 19
 20uses
 21  // FCL
 22  SysUtils, Classes,
 23  // LCL
 24  LCLProc, InterfaceBase, LazConfigStorage, PropEdits;
 25
 26type
 27  TWidgetSetRestrictionsArray = array [TLCLPlatform] of Integer;
 28
 29  { TOIFavouriteProperty
 30    BaseClassName }
 31  TOIFavouriteProperty = class
 32  protected
 33    BaseClass: TPersistentClass;
 34    BaseClassname: string;
 35    PropertyName: string;
 36    Include: boolean; // include or exclude
 37  public
 38    constructor Create(ABaseClass: TPersistentClass;
 39                       const APropertyName: string; TheInclude: boolean);
 40    function Constrains(AnItem: TOIFavouriteProperty): boolean;
 41    function IsFavourite(AClass: TPersistentClass;
 42                         const APropertyName: string): boolean;
 43    function Compare(AFavourite: TOIFavouriteProperty): integer;
 44    procedure SaveToConfig(ConfigStore: TConfigStorage; const Path: string);
 45    procedure Assign(Src: TOIFavouriteProperty); virtual;
 46    function CreateCopy: TOIFavouriteProperty;
 47    function DebugReportAsString: string;
 48  end;
 49
 50  { TOIRestrictedProperty}
 51  TOIRestrictedProperty = class(TOIFavouriteProperty)
 52  protected
 53    FWidgetSets: TLCLPlatforms;
 54  public
 55
 56    function IsRestricted(AClass: TPersistentClass;
 57                          const APropertyName: string): TLCLPlatforms;
 58    procedure CheckRestrictions(
 59      AClass: TClass; var ARestrictions: TWidgetSetRestrictionsArray);
 60
 61    property WidgetSets: TLCLPlatforms read FWidgetSets write FWidgetSets;
 62  end;
 63
 64  { TOIFavouriteProperties }
 65
 66  TOIFavouriteProperties = class
 67  private
 68    FItems: TFPList; // list of TOIFavouriteProperty
 69    FModified: Boolean;
 70    FSorted: Boolean;
 71    FDoublesDeleted: Boolean;
 72  protected
 73    function GetCount: integer; virtual;
 74    function GetItems(Index: integer): TOIFavouriteProperty; virtual;
 75  public
 76    constructor Create;
 77    destructor Destroy; override;
 78    procedure Clear; virtual;
 79    procedure Assign(Src: TOIFavouriteProperties); virtual;
 80    function CreateCopy: TOIFavouriteProperties;
 81    function Contains(AnItem: TOIFavouriteProperty): Boolean; virtual;
 82    procedure Add(NewItem: TOIFavouriteProperty); virtual;
 83    procedure AddNew(NewItem: TOIFavouriteProperty);
 84    procedure Remove(AnItem: TOIFavouriteProperty); virtual;
 85    procedure DeleteConstraints(AnItem: TOIFavouriteProperty); virtual;
 86    function IsFavourite(
 87      AClass: TPersistentClass; const PropertyName: string): boolean;
 88    function AreFavourites(
 89      Selection: TPersistentSelectionList; const PropertyName: string): boolean;
 90    procedure LoadFromConfig(ConfigStore: TConfigStorage; const Path: string);
 91    procedure SaveToConfig(ConfigStore: TConfigStorage; const Path: string);
 92    procedure MergeConfig(ConfigStore: TConfigStorage; const Path: string);
 93    procedure SaveNewItemsToConfig(
 94      ConfigStore: TConfigStorage;
 95      const Path: string; BaseFavourites: TOIFavouriteProperties);
 96    procedure Sort; virtual;
 97    procedure DeleteDoubles; virtual;
 98    function IsEqual(TheFavourites: TOIFavouriteProperties): boolean;
 99    function GetSubtractList(FavouritesToSubtract: TOIFavouriteProperties): TList;
100    procedure WriteDebugReport;
101  public
102    property Items[Index: integer]: TOIFavouriteProperty read GetItems; default;
103    property Count: integer read GetCount;
104    property Modified: Boolean read FModified write FModified;
105    property Sorted: Boolean read FSorted;
106    property DoublesDeleted: boolean read FDoublesDeleted;
107  end;
108  TOIFavouritePropertiesClass = class of TOIFavouriteProperties;
109
110  { TOIRestrictedProperties }
111
112  TOIRestrictedProperties = class(TOIFavouriteProperties)
113  protected
114    FWidgetSetRestrictions: TWidgetSetRestrictionsArray;
115  public
116    constructor Create;
117
118    function IsRestricted(AClass: TPersistentClass;
119                          const PropertyName: string): TLCLPlatforms;
120    function AreRestricted(Selection: TPersistentSelectionList;
121                           const PropertyName: string): TLCLPlatforms;
122    property WidgetSetRestrictions: TWidgetSetRestrictionsArray
123      read FWidgetSetRestrictions;
124  end;
125
126implementation
127
128function CompareOIFavouriteProperties(Data1, Data2: Pointer): integer;
129var
130  Favourite1: TOIFavouriteProperty;
131  Favourite2: TOIFavouriteProperty;
132begin
133  Favourite1:=TOIFavouriteProperty(Data1);
134  Favourite2:=TOIFavouriteProperty(Data2);
135  Result:=Favourite1.Compare(Favourite2)
136end;
137
138{ TOIFavouriteProperties }
139
140function TOIFavouriteProperties.GetCount: integer;
141begin
142  Result:=FItems.Count;
143end;
144
145function TOIFavouriteProperties.GetItems(Index: integer): TOIFavouriteProperty;
146begin
147  Result:=TOIFavouriteProperty(FItems[Index]);
148end;
149
150constructor TOIFavouriteProperties.Create;
151begin
152  FItems:=TFPList.Create;
153end;
154
155destructor TOIFavouriteProperties.Destroy;
156begin
157  Clear;
158  FreeAndNil(FItems);
159  inherited Destroy;
160end;
161
162procedure TOIFavouriteProperties.Clear;
163var
164  i: Integer;
165begin
166  for i:=0 to FItems.Count-1 do
167    TObject(FItems[i]).Free;
168  FItems.Clear;
169  FSorted:=true;
170end;
171
172procedure TOIFavouriteProperties.Assign(Src: TOIFavouriteProperties);
173var
174  i: Integer;
175begin
176  Clear;
177  for i:=0 to Src.Count-1 do
178    FItems.Add(Src[i].CreateCopy);
179  FModified:=Src.Modified;
180  FDoublesDeleted:=Src.DoublesDeleted;
181  FSorted:=Src.Sorted;
182end;
183
184function TOIFavouriteProperties.CreateCopy: TOIFavouriteProperties;
185begin
186  Result:=TOIFavouriteProperties.Create;
187  Result.Assign(Self);
188end;
189
190function TOIFavouriteProperties.Contains(AnItem: TOIFavouriteProperty
191  ): Boolean;
192var
193  i: Integer;
194begin
195  for i:=Count-1 downto 0 do begin
196    if Items[i].Compare(AnItem)=0 then begin
197      Result:=true;
198      exit;
199    end;
200  end;
201  Result:=false;
202end;
203
204procedure TOIFavouriteProperties.Add(NewItem: TOIFavouriteProperty);
205begin
206  FItems.Add(NewItem);
207  FSorted:=(Count<=1)
208           or (FSorted and (Items[Count-1].Compare(Items[Count-2])<0));
209  FDoublesDeleted:=FSorted
210             and ((Count<=1) or (Items[Count-1].Compare(Items[Count-2])<>0));
211  Modified:=true;
212end;
213
214procedure TOIFavouriteProperties.AddNew(NewItem: TOIFavouriteProperty);
215begin
216  if Contains(NewItem) then
217    NewItem.Free
218  else
219    Add(NewItem);
220end;
221
222procedure TOIFavouriteProperties.Remove(AnItem: TOIFavouriteProperty);
223begin
224  Modified:=FItems.Remove(AnItem)>=0;
225end;
226
227procedure TOIFavouriteProperties.DeleteConstraints(
228  AnItem: TOIFavouriteProperty);
229// delete all items, that would constrain AnItem
230var
231  i: Integer;
232  CurItem: TOIFavouriteProperty;
233begin
234  for i:=Count-1 downto 0 do begin
235    CurItem:=Items[i];
236    if CurItem.Constrains(AnItem) then begin
237      FItems.Delete(i);
238      Modified:=true;
239      CurItem.Free;
240    end;
241  end;
242end;
243
244function TOIFavouriteProperties.IsFavourite(AClass: TPersistentClass;
245  const PropertyName: string): boolean;
246var
247  i: Integer;
248  CurItem: TOIFavouriteProperty;
249  BestItem: TOIFavouriteProperty;
250begin
251  if (AClass=nil) or (PropertyName='') then begin
252    Result:=false;
253    exit;
254  end;
255  BestItem:=nil;
256  for i:=0 to Count-1 do begin
257    CurItem:=Items[i];
258    if not CurItem.IsFavourite(AClass,PropertyName) then continue;
259    if (BestItem=nil)
260    or (AClass.InheritsFrom(BestItem.BaseClass)) then begin
261      //debugln('TOIFavouriteProperties.IsFavourite ',AClass.ClassName,' ',PropertyName);
262      BestItem:=CurItem;
263    end;
264  end;
265  Result:=(BestItem<>nil) and BestItem.Include;
266end;
267
268function TOIFavouriteProperties.AreFavourites(
269  Selection: TPersistentSelectionList; const PropertyName: string): boolean;
270var
271  i: Integer;
272begin
273  Result:=(Selection<>nil) and (Selection.Count>0);
274  if not Result then exit;
275  for i:=0 to Selection.Count-1 do begin
276    if not IsFavourite(TPersistentClass(Selection[i].ClassType),PropertyName)
277    then begin
278      Result:=false;
279      exit;
280    end;
281  end;
282end;
283
284procedure TOIFavouriteProperties.LoadFromConfig(ConfigStore: TConfigStorage;
285  const Path: string);
286var
287  NewCount: LongInt;
288  i: Integer;
289  NewItem: TOIFavouriteProperty;
290  p: String;
291  NewPropertyName: String;
292  NewInclude: Boolean;
293  NewBaseClassname: String;
294  NewBaseClass: TPersistentClass;
295begin
296  Clear;
297  NewCount:=ConfigStore.GetValue(Path+'Count',0);
298  for i:=0 to NewCount-1 do begin
299    p:=Path+'Item'+IntToStr(i)+'/';
300    NewPropertyName:=ConfigStore.GetValue(p+'PropertyName','');
301    if (NewPropertyName='') or (not IsValidIdent(NewPropertyName)) then
302      continue;
303    NewInclude:=ConfigStore.GetValue(p+'Include',true);
304    NewBaseClassname:=ConfigStore.GetValue(p+'BaseClass','');
305    if (NewBaseClassname='') or (not IsValidIdent(NewBaseClassname))  then
306      continue;
307    NewBaseClass:=GetClass(NewBaseClassname);
308    NewItem:=TOIFavouriteProperty.Create(NewBaseClass,NewPropertyName,
309                                         NewInclude);
310    NewItem.BaseClassName:=NewBaseClassname;
311    Add(NewItem);
312  end;
313  {$IFDEF DebugFavouriteroperties}
314  debugln('TOIFavouriteProperties.LoadFromConfig END');
315  WriteDebugReport;
316  {$ENDIF}
317end;
318
319procedure TOIFavouriteProperties.SaveToConfig(ConfigStore: TConfigStorage;
320  const Path: string);
321var
322  i: Integer;
323begin
324  ConfigStore.SetDeleteValue(Path+'Count',Count,0);
325  for i:=0 to Count-1 do
326    Items[i].SaveToConfig(ConfigStore,Path+'Item'+IntToStr(i)+'/');
327end;
328
329procedure TOIFavouriteProperties.MergeConfig(ConfigStore: TConfigStorage;
330  const Path: string);
331var
332  NewFavourites: TOIFavouriteProperties;
333  OldItem: TOIFavouriteProperty;
334  NewItem: TOIFavouriteProperty;
335  cmp: LongInt;
336  NewIndex: Integer;
337  OldIndex: Integer;
338begin
339  NewFavourites:=TOIFavouritePropertiesClass(ClassType).Create;
340  {$IFDEF DebugFavouriteroperties}
341  debugln('TOIFavouriteProperties.MergeConfig ',dbgsName(NewFavourites),' ',dbgsName(NewFavourites.FItems));
342  {$ENDIF}
343  try
344    // load config
345    NewFavourites.LoadFromConfig(ConfigStore,Path);
346    // sort both to see the differences
347    NewFavourites.DeleteDoubles; // descending
348    DeleteDoubles;               // descending
349    // add all new things from NewFavourites
350    NewIndex:=0;
351    OldIndex:=0;
352    while (NewIndex<NewFavourites.Count) do begin
353      NewItem:=NewFavourites[NewIndex];
354      if OldIndex>=Count then begin
355        // item only exists in config -> move to this list
356        NewFavourites.FItems[NewIndex]:=nil;
357        inc(NewIndex);
358        FItems.Insert(OldIndex,NewItem);
359        inc(OldIndex);
360      end else begin
361        OldItem:=Items[OldIndex];
362        cmp:=OldItem.Compare(NewItem);
363        //debugln('TOIFavouriteProperties.MergeConfig cmp=',dbgs(cmp),' OldItem=[',OldItem.DebugReportAsString,'] NewItem=[',NewItem.DebugReportAsString,']');
364        if cmp=0 then begin
365          // item already exists in this list
366          inc(NewIndex);
367          inc(OldIndex);
368        end else if cmp<0 then begin
369          // item exists only in old favourites
370          // -> next old
371          inc(OldIndex);
372        end else begin
373          // item only exists in config -> move to this list
374          NewFavourites.FItems[NewIndex]:=nil;
375          inc(NewIndex);
376          FItems.Insert(OldIndex,NewItem);
377          inc(OldIndex);
378        end;
379      end;
380    end;
381  finally
382    NewFavourites.Free;
383  end;
384  {$IFDEF DebugFavouriteroperties}
385  debugln('TOIFavouriteProperties.MergeConfig END');
386  WriteDebugReport;
387  {$ENDIF}
388end;
389
390procedure TOIFavouriteProperties.SaveNewItemsToConfig(
391  ConfigStore: TConfigStorage; const Path: string;
392  BaseFavourites: TOIFavouriteProperties);
393// Save all items, that are in this list and not in BaseFavourites
394// It does not save, if an item in BaseFavourites is missing in this list
395var
396  SubtractList: TList;
397  i: Integer;
398  CurItem: TOIFavouriteProperty;
399begin
400  SubtractList:=GetSubtractList(BaseFavourites);
401  try
402    ConfigStore.SetDeleteValue(Path+'Count',SubtractList.Count,0);
403    {$IFDEF DebugFavouriteroperties}
404    debugln('TOIFavouriteProperties.SaveNewItemsToConfig A Count=',dbgs(SubtractList.Count));
405    {$ENDIF}
406    for i:=0 to SubtractList.Count-1 do begin
407      CurItem:=TOIFavouriteProperty(SubtractList[i]);
408      CurItem.SaveToConfig(ConfigStore,Path+'Item'+IntToStr(i)+'/');
409      {$IFDEF DebugFavouriteroperties}
410      debugln(' i=',dbgs(i),' ',CurItem.DebugReportAsString);
411      {$ENDIF}
412    end;
413  finally
414    SubtractList.Free;
415  end;
416end;
417
418procedure TOIFavouriteProperties.Sort;
419begin
420  if FSorted then exit;
421  FItems.Sort(@CompareOIFavouriteProperties);
422end;
423
424procedure TOIFavouriteProperties.DeleteDoubles;
425// This also sorts
426var
427  i: Integer;
428begin
429  if FDoublesDeleted then exit;
430  Sort;
431  for i:=Count-1 downto 1 do begin
432    if Items[i].Compare(Items[i-1])=0 then begin
433      Items[i].Free;
434      FItems.Delete(i);
435    end;
436  end;
437  FDoublesDeleted:=true;
438end;
439
440function TOIFavouriteProperties.IsEqual(TheFavourites: TOIFavouriteProperties
441  ): boolean;
442var
443  i: Integer;
444begin
445  Result:=false;
446  DeleteDoubles;
447  TheFavourites.DeleteDoubles;
448  if Count<>TheFavourites.Count then exit;
449  for i:=Count-1 downto 1 do
450    if Items[i].Compare(TheFavourites.Items[i])<>0 then exit;
451  Result:=true;
452end;
453
454function TOIFavouriteProperties.GetSubtractList(
455  FavouritesToSubtract: TOIFavouriteProperties): TList;
456// create a list of TOIFavouriteProperty of all items in this list
457// and not in FavouritesToSubtract
458var
459  SelfIndex: Integer;
460  SubtractIndex: Integer;
461  CurItem: TOIFavouriteProperty;
462  cmp: LongInt;
463begin
464  Result:=TList.Create;
465  DeleteDoubles; // this also sorts descending
466  FavouritesToSubtract.DeleteDoubles; // this also sorts descending
467  SelfIndex:=0;
468  SubtractIndex:=0;
469  while SelfIndex<Count do begin
470    CurItem:=Items[SelfIndex];
471    if SubtractIndex>=FavouritesToSubtract.Count then begin
472      // item does not exist in SubtractIndex -> add it
473      Result.Add(CurItem);
474      inc(SelfIndex);
475    end else begin
476      cmp:=CurItem.Compare(FavouritesToSubtract[SubtractIndex]);
477      //debugln('TOIFavouriteProperties.GetSubtractList cmp=',dbgs(cmp),' CurItem=[',CurItem.DebugReportAsString,'] SubtractItem=[',FavouritesToSubtract[SubtractIndex].DebugReportAsString,']');
478      if cmp=0 then begin
479        // item exists in SubtractIndex -> skip
480        inc(SubtractIndex);
481        inc(SelfIndex);
482      end else if cmp>0 then begin
483        // item does not exist in FavouritesToSubtract -> add it
484        Result.Add(CurItem);
485        inc(SelfIndex);
486      end else begin
487        // item exists only in FavouritesToSubtract -> skip
488        inc(SubtractIndex);
489      end;
490    end;
491  end;
492end;
493
494procedure TOIFavouriteProperties.WriteDebugReport;
495var
496  i: Integer;
497begin
498  debugln('TOIFavouriteProperties.WriteDebugReport Count=',dbgs(Count));
499  for i:=0 to Count-1 do
500    debugln('  i=',dbgs(i),' ',Items[i].DebugReportAsString);
501end;
502
503{ TOIFavouriteProperty }
504
505constructor TOIFavouriteProperty.Create(ABaseClass: TPersistentClass;
506  const APropertyName: string; TheInclude: boolean);
507begin
508  BaseClass:=ABaseClass;
509  PropertyName:=APropertyName;
510  Include:=TheInclude;
511end;
512
513function TOIFavouriteProperty.Constrains(AnItem: TOIFavouriteProperty
514  ): boolean;
515// true if this item constrains AnItem
516// This item constrains AnItem, if this is the opposite (Include) and
517// AnItem has the same or greater scope
518begin
519  Result:=(Include<>AnItem.Include)
520          and (CompareText(PropertyName,AnItem.PropertyName)=0)
521          and (BaseClass.InheritsFrom(AnItem.BaseClass));
522end;
523
524function TOIFavouriteProperty.IsFavourite(AClass: TPersistentClass;
525  const APropertyName: string): boolean;
526begin
527  Result:=(CompareText(PropertyName,APropertyName)=0)
528          and (AClass.InheritsFrom(BaseClass));
529end;
530
531function TOIFavouriteProperty.Compare(AFavourite: TOIFavouriteProperty
532  ): integer;
533
534  function CompareBaseClass: integer;
535  begin
536    if BaseClass<>nil then begin
537      if AFavourite.BaseClass<>nil then
538        Result:=ComparePointers(BaseClass,AFavourite.BaseClass)
539      else
540        Result:=CompareText(BaseClass.ClassName,AFavourite.BaseClassName);
541    end else begin
542      if AFavourite.BaseClass<>nil then
543        Result:=CompareText(BaseClassName,AFavourite.BaseClass.ClassName)
544      else
545        Result:=CompareText(BaseClassName,AFavourite.BaseClassName);
546    end;
547  end;
548
549begin
550  // first compare PropertyName
551  Result:=CompareText(PropertyName,AFavourite.PropertyName);
552  if Result<>0 then exit;
553  // then compare Include
554  if Include<>AFavourite.Include then begin
555    if Include then
556      Result:=1
557    else
558      Result:=-1;
559    exit;
560  end;
561  // then compare BaseClass and BaseClassName
562  Result:=CompareBaseClass;
563end;
564
565procedure TOIFavouriteProperty.SaveToConfig(ConfigStore: TConfigStorage;
566  const Path: string);
567begin
568  if BaseClass<>nil then
569    ConfigStore.SetDeleteValue(Path+'BaseClass',BaseClass.ClassName,'')
570  else
571    ConfigStore.SetDeleteValue(Path+'BaseClass',BaseClassName,'');
572  ConfigStore.SetDeleteValue(Path+'PropertyName',PropertyName,'');
573  ConfigStore.SetDeleteValue(Path+'Include',Include,true);
574end;
575
576procedure TOIFavouriteProperty.Assign(Src: TOIFavouriteProperty);
577begin
578  BaseClassName:=Src.BaseClassName;
579  BaseClass:=Src.BaseClass;
580  PropertyName:=Src.PropertyName;
581  Include:=Src.Include;
582end;
583
584function TOIFavouriteProperty.CreateCopy: TOIFavouriteProperty;
585begin
586  Result:=TOIFavouriteProperty.Create(BaseClass,PropertyName,Include);
587  Result.BaseClass:=BaseClass;
588end;
589
590function TOIFavouriteProperty.DebugReportAsString: string;
591begin
592  Result:='PropertyName="'+PropertyName+'"'
593      +' Include='+dbgs(Include)
594      +' BaseClassName="'+BaseClassName+'"'
595      +' BaseClass='+dbgsName(BaseClass);
596end;
597
598{ TOIRestrictedProperty }
599
600procedure TOIRestrictedProperty.CheckRestrictions(
601  AClass: TClass; var ARestrictions: TWidgetSetRestrictionsArray);
602var
603  lclPlatform: TLCLPlatform;
604begin
605  if AClass.InheritsFrom(BaseClass) and (PropertyName = '') then
606    for lclPlatform := Low(TLCLPlatform) to High(TLCLPlatform) do
607      if lclPlatform in WidgetSets then
608        Inc(ARestrictions[lclPlatform]);
609end;
610
611function TOIRestrictedProperty.IsRestricted(AClass: TPersistentClass;
612  const APropertyName: string): TLCLPlatforms;
613begin
614  //DebugLn('IsRestricted ', AClass.ClassName, ' ?= ', BaseClass.ClassName, ' ', APropertyName, ' ?= ', PropertyName);
615  Result := [];
616  if (CompareText(PropertyName,APropertyName) = 0)
617    and (AClass.InheritsFrom(BaseClass)) then Result := WidgetSets;
618end;
619
620
621{ TOIRestrictedProperties }
622
623constructor TOIRestrictedProperties.Create;
624var
625  P: TLCLPlatform;
626begin
627  inherited Create;
628
629  for P := Low(TLCLPlatform) to High(TLCLPlatform) do
630    FWidgetSetRestrictions[P] := 0;
631end;
632
633function TOIRestrictedProperties.IsRestricted(AClass: TPersistentClass;
634  const PropertyName: string): TLCLPlatforms;
635var
636  I: Integer;
637  CurItem: TOIRestrictedProperty;
638begin
639  Result := [];
640  if (AClass=nil) or (PropertyName='') then Exit;
641  for I := 0 to Count - 1 do
642  begin
643    if not (Items[I] is TOIRestrictedProperty) then Continue;
644    CurItem:=Items[I] as TOIRestrictedProperty;
645    Result := Result + CurItem.IsRestricted(AClass,PropertyName);
646  end;
647end;
648
649function TOIRestrictedProperties.AreRestricted(
650  Selection: TPersistentSelectionList;
651  const PropertyName: string): TLCLPlatforms;
652var
653  I: Integer;
654begin
655  Result := [];
656  if Selection = nil then Exit;
657  for i:=0 to Selection.Count-1 do
658  begin
659    Result := Result + IsRestricted(TPersistentClass(Selection[i].ClassType), PropertyName);
660  end;
661end;
662
663end.
664