Обрабатывать копирование компонента из одной формы в другую в Delphi - PullRequest
0 голосов
/ 29 февраля 2020

Написание собственного Delphi компонента VCL, унаследованного от TComponent, со множеством свойств, которые должны быть уникальными для формы владельца компонента. Когда я копирую компонент из одной формы в другую (с помощью простых Ctrl + C, Ctrl-V), все свойства также копируются. Любые идеи о том, где (или как) я могу обработать копирование или вставку компонента в форму и очистить скопированные значения (или установить их по умолчанию)? На данный момент у меня появилась идея сохранить имя формы владельца компонента (или другое уникальное свойство) в специальном свойстве компонента и сравнить его с фактическим именем владельца в методе Loaded компонента. Может быть, есть более элегантный или более простой способ?

1 Ответ

0 голосов
/ 03 марта 2020

Нашел решение сам. Это своего рода хак, но тем не менее это работает.

Прежде всего, когда мы копируем компонент, Delphi копирует только опубликованные свойства - они записываются в файл dfm. Правильнее будет сказать, что Delphi скопирует реализацию компонента в формате dfm. Вы можете легко проверить это, скопировав компонент и вставив его в Блокнот. Так что теперь мы можем использовать буфер обмена, чтобы проанализировать его во вновь вставленном экземпляре нашего компонента и решить, очищать ли свойства или нет (или делать что-то еще).

Небольшой пример такой проверки - процедура который анализирует значения в буфере обмена на соответствие текущему компоненту:

function CheckClipboard:boolean;
begin
 try
  if (pos('object', Clipboard.AsText) <> 0)
    and (pos('object', Clipboard.AsText) < pos('TComponent', Clipboard.AsText))
    and (pos('TComponent', Clipboard.AsText) < pos(#13#10, Clipboard.AsText))
    and (pos(#13#10, Clipboard.AsText) < pos('end', Clipboard.AsText))
    and (TForm(Owner).Showing) then //This is for the function to not execute when the owner form is created or opened
       Result:=true
  else
    Result := false;
 except
  on E : Exception do
  begin
   MessageDlg('Clipboard error: '+E.Message, mtError, mbOKCancel, 0);
   Result := false;
  end;
 end;
end;

Возвращает true, если в буфере обмена содержится такой компонент, и false, если нет. Я использую его в методе Loaded моего компонента.

...