2013-12-06 6 views
0

Приветствую всех!класс структура для заметок приложение

Я пишу небольшое приложение для хранения разных заметок (memos) и имеет структуру классов, которые мне не нравятся. У меня есть core: MemoInterface и core: MemoBuilder классы в ядре (реализация не важна). Тогда в GUI у меня есть некоторые реальные классов мемо (например: SimpleMemo, TodoMemo, и т.д ...), которые знают, как сделать себя и производные от гуя :: MemoInterace и гуя :: TabsBuilder который создает новую вкладку в окне и запрашивает каждую заметку, чтобы нарисовать себя на вновь созданной вкладке.

В моей РЕАЛИЗАЦИЯ гуй :: TabsBuilder :: Build() вызовы GUI :: MemoBuilder :: Build() и попытаться использовать dynamic_cast, чтобы понять, что MemoInterface от GUI. На самом деле это момент, который мне не нравится, и вопрос : Как улучшить или переписать структуру, где core: MemoBuilder ничего не знает о графическом интерфейсе, но может запросить каждую заметку для рисования.

Извините, если это не очень понятно. Следующий код может сделать его более понятным.

namespace core { 
class MemoInterface { 
}; 

class MemoStorage { ... }; 

class MemoBuilder { 
public: 
    ... some code ... 
    virtual MemoInterface* Build(); 
private: 
    MemoStorage& storage_; // put here all created MemoInterface objects 
}; 
} // namespace 

namespace gui { 
class MemoInterface : public core::MemoInterface { 
public: 
    virtual void Draw(SomeWindowClass* dst) = 0; 
}; 
class SimpleMemo : public MemoInterface { // draw implementation }; 
class TodoMemo : public MemoInterface { }; 

class TabsBuilder : public core::MemoBuilder { 
public: 
    ... some code ... 

    virtual core::MemoInterface* Build() { 
     // I don't like dynamic_cast, think that it's not a good oop way 
     gui::MemoInterface* memo = dynamic_cast<gui::MemoInterface*>core::MemoBuilder::Build(); 

     if (!memo) 
      throw std::exception(); 

     memo->Draw(wnd_); // or Draw(wnd_->createNestedTab()->window()) it doesn't matter 

     return memo; 
    } 

private: 
    SomeWindowClass* wnd_; 
}; 

} // namespace gui 
+0

Just FYI: То, что вы называете 'реализация', называется' реализация' – Paranaix

+0

. Пожалуйста, не могли бы вы точно уточнить свой вопрос? –

+0

@Paranaix, thx - исправлено – Peter

ответ

0

Я предполагаю, что параметр шаблона к dynamic_cast является графический интерфейс :: MemoInterface *, а не ядро ​​:: MemoInterface * поскольку ядро ​​:: MemoBuilder :: Build() уже возвращает ядро ​​:: MemoInterface *.

Из кода, который у вас есть, кажется, что единственная разница между SimpleMemo и TodoMemo является визуальной, поскольку они оба являются подклассами одной и той же базы. Есть ли какие-то данные элемента в core :: MemoInterface, который отличает SimpleMemo от TodoMemo?

Похоже, у меня есть больше вопросов/предположений, чем ответов, поэтому вот предложение: Сделать связь между SimpleMemo и ядром :: MemoInterface a HAS-A (сдерживание). Вы все равно можете получить SimpleMemo из gui :: MemoInterface, если хотите. Сделайте то же самое для TodoMemo. Затем определите фабричный метод, который принимает в качестве параметра ядро ​​:: MemoInterface *. Это создает соответствующий тип памятки (SimpleMemo или TodoMemo) на основе информации, содержащейся в поставляемом ядре :: MemoInterface *:

class GuiMemoCreator 
{ 
public: 
    static gui::MemoInterface* CreateGuiMemo(core::MemoInterface* pMemo) 
    { 
     gui::MemoInterface* pGuiMemo = NULL; 
     if (pMemo->_id == SIMPLE) 
     { 
      pGuiMemo = new SimpleMemo(pMemo); 
     } 
     else if (pMemo->_id == TODO) 
     { 
      pGuiMemo = new TodoMemo(pMemo); 
     } 
     return pGuiMemo; 
    } 
}; 

Тогда ваша функция TabsBuilder :: Build() может вызвать GuiMemoCreator :: CreateMemo() чтобы построить объекты, которые вы хотите рисовать.

Смежные вопросы