MgCommand* MgCmdManagerImpl::findCommand(const char* name) { CMDS::iterator it = _cmds.find(name); if (it == _cmds.end() && *name) { MgCommand* cmd = NULL; Factories::iterator itf = _factories.find(name); if (itf != _factories.end() && itf->second) { cmd = (itf->second)(); } if (!cmd && strcmp(name, "select") == 0) { cmd = MgCmdSelect::Create(); } if (cmd) { _cmds[name] = cmd; it = _cmds.find(name); } } return it != _cmds.end() ? it->second : NULL; }
PrefsDialog::PrefsDialog (wxWindow * parent, const wxString &titlePrefix, Factories &factories) : wxDialogWrapper(parent, wxID_ANY, wxString(_("Audacity Preferences")), wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER) , mFactories(factories) , mTitlePrefix(titlePrefix) { wxASSERT(factories.size() > 0); const bool uniquePage = (factories.size() == 1); ShuttleGui S(this, eIsCreating); S.StartVerticalLay(true); { wxASSERT(factories.size() > 0); if (!uniquePage) { mCategories = safenew wxTreebookExt(this, wxID_ANY, mTitlePrefix); S.StartHorizontalLay(wxALIGN_LEFT | wxEXPAND, true); { S.Prop(1); S.AddWindow(mCategories, wxEXPAND); { typedef std::pair<int, int> IntPair; std::vector<IntPair> stack; int iPage = 0; for (Factories::const_iterator it = factories.begin(), end = factories.end(); it != end; ++it, ++iPage) { const PrefsNode &node = *it; PrefsPanelFactory &factory = *node.pFactory; wxWindow *const w = factory.Create(mCategories); if (stack.empty()) // Parameters are: AddPage(page, name, IsSelected, imageId). mCategories->AddPage(w, w->GetName(), false, 0); else { IntPair &top = *stack.rbegin(); mCategories->InsertSubPage(top.first, w, w->GetName(), false, 0); if (--top.second == 0) { // Expand all nodes before the layout calculation mCategories->ExpandNode(top.first, true); stack.pop_back(); } } if (node.nChildren > 0) stack.push_back(IntPair(iPage, node.nChildren)); } } } S.EndHorizontalLay(); } else { // Unique page, don't show the factory const PrefsNode &node = factories[0]; PrefsPanelFactory &factory = *node.pFactory; mUniquePage = factory.Create(this); S.AddWindow(mUniquePage, wxEXPAND); } } S.EndVerticalLay(); S.AddStandardButtons(eOkButton | eCancelButton | eApplyButton); static_cast<wxButton*>(wxWindow::FindWindowById(wxID_OK, this))->SetDefault(); if (mUniquePage && !mUniquePage->ShowsApplyButton()) { wxWindow *const applyButton = wxWindow::FindWindowById(wxID_APPLY, GetParent()); applyButton->Show(false); } #if defined(__WXGTK__) if (mCategories) mCategories->GetTreeCtrl()->EnsureVisible(mCategories->GetTreeCtrl()->GetRootItem()); #endif // mCategories->SetSizeHints(-1, -1, 790, 600); // 790 = 800 - (border * 2) Layout(); Fit(); wxSize sz = GetSize(); // Collapse nodes only after layout so the tree is wide enough if (mCategories) { int iPage = 0; for (Factories::const_iterator it = factories.begin(), end = factories.end(); it != end; ++it, ++iPage) mCategories->ExpandNode(iPage, it->expanded); } // This ASSERT used to limit us to 800 x 600. // However, we think screens have got bigger now, and that was a bit too restrictive. // The impetus for increasing the limit (before we ASSERT) was that this ASSERT // was firing with wxWidgets 3.0, which has slightly different sizer behaviour. wxASSERT_MSG(sz.x <= 1000 && sz.y <= 750, wxT("Preferences dialog exceeds max size")); if (sz.x > 800) { sz.x = 800; } if (sz.y > 600) { sz.y = 600; } // Set the minimum height to be slightly bigger than default, as fix for bug 161. // The magic number 7 was determined by Ed's experimentation. // Frankly, this is a hack to work around a bug in wxTreebook, and // will have to be revisited if we add another category to mCategories. // JKC later added a category and 20 onto the 7. sz.y += 7 + 20; SetSize(sz); SetMinSize(sz); // Center after all that resizing, but make sure it doesn't end up // off-screen CentreOnParent(); }
void add_factory(const char* name) { assert(factories.find(name) == factories.end()); factories[name] = std::unique_ptr<AbstractObjectFactory>(new ConcreteObjectFactory<C>()); }