Прежде всего, это не компилятор, жалующийся, но IDE.
Компилятор все равно, если у вас есть формы или другие типы - с тем же именем, если они находятся в разных единицах. Известным примером из VCL было наличие двух типов TBitmap, один в Графика другая в Windows. Если вам когда-либо понадобится быть явным в отношении того, какой тип вы имеете в виду, вы просто квалифицируете имя типа в коде и компилятор делает, как сказано.
bmpA: Graphics.TBitmap; // bmpA is a TBitmap as defined in the Graphics unit
bmpB: Windows.TBitmap; // bmpB is a TBitmap as defined in the Windows unit
Проблем нет.
Однако рамки сохранения в Delphi делает помощи, если у вас есть постоянных классов с таким же именем, так как структура живучести определяет типы только их неквалифицированного имени.
Именно поэтому каждая сторонняя структура компонента для Delphi использует префикс для своих имен классов. Это не просто тщеславие или мода. Это гарантирует, что компонент в одной библиотеке нельзя путать (с помощью механизмов сохранения Delphi) с другим из другой библиотеки, если обе библиотеки используются в одном проекте.
Итог: Придерживайтесь уникальных имен для ваших форм и найдите другой способ различать или переключаться между ними, если это необходимо.
Точно, как тогда можно управлять ссылкой на какую конкретную форму, сложно предложить без дополнительной информации о вашем проекте. Вы можете получить как общий базовый класс, так и вы можете определить интерфейс для каждого из них.
Например (и это только иллюстративный эскиз, не является рекомендацией или полностью работал раствор):
// Define the interface that your Receiver implementations
// must satisfy. This might include returning a reference to the implementing form.
//
// e.g. in a unit "uiReceiver"
type
IReceiver = interface
function Form: TForm; // returns the form using the common base type, not the specific implementation class
end;
// in unit uSDR
TfrmSDRReceiver = class(TForm, IReceiver)
..implements IReceiver as well as your SDR specific needs
end;
// in unit u7000
TfrmR7000SerialReceiver = class(TForm, IReceiver)
..implements IReceiver as well as your R7000 Serial specific needs
end;
// In uReceiver (some unit to "resolve" the receiver)
interface
uses
uSDR,
uR7000;
type
TReceiver = class
class function GetReceiver: IReceiver;
end;
implementation
class function TReceiver.GetReceiver: IReceiver;
begin
{$ifdef SDR}
result := frmSDRReceiver;
{$endif}
{$ifdef R7000}
result := frmR7000SerialReceiver;
{$endif}
end;
end.
Ваш код приложения затем использует uReceiver блок (и uiReceiver если вы хотите обратиться к типу интерфейса, например, в объявлении переменной) и обращается к конкретному приемнику через статический класс, например:
uses
uReceiver;
implementation
uses
uiReceiver;
..
var
rcvr: IReceiver;
begin
rcvr := TReceiver.GetReceiver;
rcvr.... // work with your receiver through the methods/properties on the interface
// You can also work with the receiver form, accessing all aspects
// common to any TForm via the Form function on the interface (assuming
// you chose to provide one):
rcvr.Form.Show;
..
end;
Дайте им разные названия –
...и если они иначе предназначены для взаимодействия аналогичным образом, формализуйте это с помощью интерфейса. –
Вы просто создаете проблему для себя, пытаясь использовать две формы с тем же именем. Хотя вы могли бы использовать IFDEF свой код в блоке sanme, вы не сможете сделать это с помощью своих файлов DFM. – MartynA