У меня есть пользовательский элемент управления, который должен получить доступ к высоте основной формы, в которой он находится. Так как этот элемент управления обычно вкладывается в серию панелей, я написал этот код, чтобы попытаться привести меня к основной форме:
TControl * control = this;
while( control->HasParent() )
{
control = control->ParentControl;
ShowMessage( control->Name );
}
С использованием ShowMessage
оператор для отслеживания моего прогресса, когда я шагаю по коду, я дохожу до «BasePanel», который в этом случае является последним элементом управления вверх по лестнице перед «MainForm». Тем не менее, когда звонок ShowMessage
происходит то, что должно быть «MainForm», я получаю нарушение прав доступа.
Есть ли какая-то причина, по которой я не могу получить доступ к основной форме элемента управления таким образом? Есть ли лучший способ получить доступ к основной форме элемента управления?
Вы не проверяете, если ParentControl
возвращает нулевой указатель перед чтением его Name
, когда HasParent()
возвращает истину, ParentControl
является НЕ гарантированно будет действительным. Дело в точке — TForm
является НЕ TControl
потомок в FireMonkey, поэтому он не может быть возвращен ParentControl
,
Цель HasParent()
должен сообщить, есть ли у компонента родительский или нет. TFmxObject
Переопределение HasParent()
сообщить, является ли TFmxObject.Parent
свойство равно NULL и переопределяет GetParentComponent()
вернуть соответствующий TComponent
для этого родителя. TFmxObject.Parent
возвращает TFmxObject
поскольку родительские и дочерние отношения не должны быть визуальными в FireMonkey, как в VCL, Parent
а также GetParentComponent()
может на самом деле возвращать разные объекты время от времени.
Вы должны использовать GetParentComponent()
вместо ParentControl
как документация говорит:
Вызов HasParent определить, есть ли у конкретного компонента родительский элемент.
Производные классы переопределяют этот метод для реализации правильной обработки родительских функций.
использование GetParentComponent чтобы получить ссылку на компонент.
Например:
TComponent * comp = this;
while( comp->HasParent() )
{
comp = comp->GetParentComponent();
ShowMessage( comp->Name );
}
Однако, если вы хотите найти родителя TForm
в частности, используйте ваш контроль Root
свойство вместо:
TCommonCustomForm *form = dynamic_cast<TCommonCustomForm*>(this->Root->GetObject());