我先发布我的代码然后解释我的问题:
std::list<Widget::Ptr> m_widgets;
std::list<Widget::Ptr>::iterator findObject(const std::string& id)
{
for (auto iter = m_widgets.begin(); iter != m_widgets.end(); ++iter)
{
if ((*iter)->getId() == id)
return iter;
}
return m_widgets.end();
}
template <class T> void pushWidget(std::shared_ptr<T> widget)
{
auto iter = findObject(widget->getId());
if (iter != m_widgets.end())
return;
m_widgets.push_back(std::dynamic_pointer_cast<Widget>(widget));
}
template <class T> std::shared_ptr<T> getWidget(const std::string& id)
{
auto iter = findObject(id);
if (iter != m_widgets.end())
return std::dynamic_pointer_cast<T>(*iter);
return nullptr;
}
const std::type_index& getType(const std::string& id)
{
auto iter = findObject(id);
if (iter != m_widgets.end())
return typeid(*iter);
}
Widget :: Ptr是std :: shared_ptr的typedef顺便说一下。无论如何,我遇到的问题是如何告诉getWidget()小部件是什么类型的小部件。 Widget是其他小部件继承的基类,例如Label,Editbox等。对于我的主GUI管理器,我尽可能地缩短我的代码以使更新/绘图尽可能干净。现在,菜单是我在这种情况下尝试使用的一种小部件:
auto type = SceneManager::getCurrentScene().m_gui.getType(widgetId);
SceneManager::getCurrentScene().m_gui.getWidget<typeid(type)>(widgetId)->attachToMenu(getId());
但是,这不起作用,我从编译器中收到这些错误:
error: no matching function for call to 'SE::GUI::getWidget(const string&)'|
note: candidate is:|
note: template<class T> std::shared_ptr<_Tp> SE::GUI::getWidget(const string&)|
note: template argument deduction/substitution failed:|
我可以提供所需的更多详细信息,并感谢您的帮助!
答案 0 :(得分:1)
typeid(type)
不返回表达式type
的类型,但返回有关类型(RTTI)的运行时信息。你想要的是decltype()
,它返回一个表达式的类型:
SceneManager::getCurrentScene().m_gui.getWidget<decltype(type)>(widgetId)->attachToMenu(getId());