/[svn]/gigedit/trunk/src/gigedit/MacroEditor.cpp
ViewVC logotype

Diff of /gigedit/trunk/src/gigedit/MacroEditor.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 3151 by schoenebeck, Fri May 5 18:44:59 2017 UTC revision 3155 by schoenebeck, Sun May 7 15:32:43 2017 UTC
# Line 12  Line 12 
12  MacroEditor::MacroEditor() :  MacroEditor::MacroEditor() :
13      m_macroOriginal(NULL),      m_macroOriginal(NULL),
14      m_statusLabel("",  Gtk::ALIGN_START),      m_statusLabel("",  Gtk::ALIGN_START),
15        m_deleteButton(Glib::ustring(_("Delete")) + " " + UNICODE_PRIMARY_KEY_SYMBOL + UNICODE_ERASE_KEY_SYMBOL),
16        m_inverseDeleteButton(Glib::ustring(_("Inverse Delete")) + " " + UNICODE_ALT_KEY_SYMBOL + UNICODE_ERASE_KEY_SYMBOL),
17      m_applyButton(_("_Apply"), true),      m_applyButton(_("_Apply"), true),
18      m_cancelButton(_("_Cancel"), true)      m_cancelButton(_("_Cancel"), true),
19        m_altKeyDown(false)
20  {  {
21      add(m_vbox);      add(m_vbox);
22    
# Line 27  MacroEditor::MacroEditor() : Line 30  MacroEditor::MacroEditor() :
30      m_treeViewMacro.append_column(_("Key"), m_treeModelMacro.m_col_name);      m_treeViewMacro.append_column(_("Key"), m_treeModelMacro.m_col_name);
31      m_treeViewMacro.append_column(_("Type"), m_treeModelMacro.m_col_type);      m_treeViewMacro.append_column(_("Type"), m_treeModelMacro.m_col_type);
32      m_treeViewMacro.append_column_editable(_("Value"), m_treeModelMacro.m_col_value);      m_treeViewMacro.append_column_editable(_("Value"), m_treeModelMacro.m_col_value);
33        {
34            Gtk::TreeViewColumn* column = m_treeViewMacro.get_column(1);
35            Gtk::CellRendererText* cellrenderer =
36                dynamic_cast<Gtk::CellRendererText*>(column->get_first_cell());
37            cellrenderer->property_foreground().set_value("#bababa");
38        }
39      /*{      /*{
40          Gtk::TreeViewColumn* column = m_treeViewMacro.get_column(0);          Gtk::TreeViewColumn* column = m_treeViewMacro.get_column(0);
41          Gtk::CellRendererText* cellrenderer =          Gtk::CellRendererText* cellrenderer =
# Line 44  MacroEditor::MacroEditor() : Line 53  MacroEditor::MacroEditor() :
53          );          );
54      }*/      }*/
55      m_treeViewMacro.set_headers_visible(true);      m_treeViewMacro.set_headers_visible(true);
56      /*m_treeViewMacro.signal_button_press_event().connect_notify(      m_treeViewMacro.get_selection()->signal_changed().connect(
57          sigc::mem_fun(*this, &MainWindow::on_sample_treeview_button_release)          sigc::mem_fun(*this, &MacroEditor::onTreeViewSelectionChanged)
58      );*/      );
59      /*m_refSamplesTreeModel->signal_row_changed().connect(      m_treeViewMacro.signal_key_release_event().connect_notify(
60          sigc::mem_fun(*this, &MainWindow::sample_name_changed)          sigc::mem_fun(*this, &MacroEditor::onMacroTreeViewKeyRelease)
61      );*/      );
62        m_treeStoreMacro->signal_row_changed().connect(
63            sigc::mem_fun(*this, &MacroEditor::onMacroTreeViewRowValueChanged)
64        );
65        m_ignoreTreeViewValueChange = false;
66    
67      m_scrolledWindow.add(m_treeViewMacro);      m_scrolledWindow.add(m_treeViewMacro);
68      m_scrolledWindow.set_policy(Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC);      m_scrolledWindow.set_policy(Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC);
69      m_vbox.pack_start(m_scrolledWindow);      m_vbox.pack_start(m_scrolledWindow);
70    
71        m_buttonBoxL.set_layout(Gtk::BUTTONBOX_START);
72        m_buttonBoxL.pack_start(m_deleteButton);
73        m_buttonBoxL.pack_start(m_inverseDeleteButton);
74        m_deleteButton.set_sensitive(false);
75        m_inverseDeleteButton.set_sensitive(false);
76    
77      m_buttonBox.set_layout(Gtk::BUTTONBOX_END);      m_buttonBox.set_layout(Gtk::BUTTONBOX_END);
78      m_buttonBox.pack_start(m_applyButton);      m_buttonBox.pack_start(m_applyButton);
79      m_buttonBox.pack_start(m_cancelButton);      m_buttonBox.pack_start(m_cancelButton);
# Line 72  MacroEditor::MacroEditor() : Line 91  MacroEditor::MacroEditor() :
91      m_statusHBox.pack_start(m_statusLabel);      m_statusHBox.pack_start(m_statusLabel);
92      m_statusHBox.show_all_children();      m_statusHBox.show_all_children();
93    
94        m_footerHBox.pack_start(m_buttonBoxL, Gtk::PACK_SHRINK);
95      m_footerHBox.pack_start(m_statusHBox);      m_footerHBox.pack_start(m_statusHBox);
96      m_footerHBox.pack_start(m_buttonBox, Gtk::PACK_SHRINK);      m_footerHBox.pack_start(m_buttonBox, Gtk::PACK_SHRINK);
97    
# Line 85  MacroEditor::MacroEditor() : Line 105  MacroEditor::MacroEditor() :
105          sigc::mem_fun(*this, &MacroEditor::onButtonCancel)          sigc::mem_fun(*this, &MacroEditor::onButtonCancel)
106      );      );
107    
108        m_deleteButton.signal_clicked().connect(
109            sigc::mem_fun(*this, &MacroEditor::deleteSelectedRows)
110        );
111    
112        m_inverseDeleteButton.signal_clicked().connect(
113            sigc::mem_fun(*this, &MacroEditor::inverseDeleteSelectedRows)
114        );
115    
116      signal_hide().connect(      signal_hide().connect(
117          sigc::mem_fun(*this, &MacroEditor::onWindowHide)          sigc::mem_fun(*this, &MacroEditor::onWindowHide)
118      );      );
# Line 93  MacroEditor::MacroEditor() : Line 121  MacroEditor::MacroEditor() :
121          sigc::mem_fun(*this, &MacroEditor::onWindowDelete)          sigc::mem_fun(*this, &MacroEditor::onWindowDelete)
122      );      );
123    
124        signal_key_press_event().connect(
125            sigc::mem_fun(*this, &MacroEditor::onKeyPressed)
126        );
127        signal_key_release_event().connect(
128            sigc::mem_fun(*this, &MacroEditor::onKeyReleased)
129        );
130    
131      show_all_children();      show_all_children();
132      updateStatus();      updateStatus();
133  }  }
# Line 136  void MacroEditor::buildTreeView(const Gt Line 171  void MacroEditor::buildTreeView(const Gt
171  }  }
172    
173  void MacroEditor::reloadTreeView() {  void MacroEditor::reloadTreeView() {
174        m_ignoreTreeViewValueChange = true;
175    
176      m_treeStoreMacro->clear();      m_treeStoreMacro->clear();
177    
178      const Serialization::Object& rootObject = m_macro.rootObject();      const Serialization::Object& rootObject = m_macro.rootObject();
# Line 152  void MacroEditor::reloadTreeView() { Line 189  void MacroEditor::reloadTreeView() {
189      m_treeViewMacro.expand_all();      m_treeViewMacro.expand_all();
190    
191      updateStatus();      updateStatus();
192    
193        m_ignoreTreeViewValueChange = false;
194    }
195    
196    void MacroEditor::onTreeViewSelectionChanged() {
197        std::vector<Gtk::TreeModel::Path> v = m_treeViewMacro.get_selection()->get_selected_rows();
198        const bool bValidSelection = !v.empty();
199        m_deleteButton.set_sensitive(bValidSelection);
200        m_inverseDeleteButton.set_sensitive(bValidSelection);
201    }
202    
203    bool MacroEditor::onKeyPressed(GdkEventKey* key) {
204        //printf("key down 0x%x\n", key->keyval);
205        if (key->keyval == GDK_KEY_Alt_L || key->keyval == GDK_KEY_Alt_R)
206            m_altKeyDown = true;
207        return false;
208    }
209    
210    bool MacroEditor::onKeyReleased(GdkEventKey* key) {
211        //printf("key up 0x%x\n", key->keyval);
212        if (key->keyval == GDK_KEY_Alt_L || key->keyval == GDK_KEY_Alt_R)
213            m_altKeyDown = false;
214        return false;
215    }
216    
217    void MacroEditor::onMacroTreeViewKeyRelease(GdkEventKey* key) {
218        if (key->keyval == GDK_KEY_BackSpace || key->keyval == GDK_KEY_Delete) {
219            if (m_altKeyDown)
220                inverseDeleteSelectedRows();
221            else
222                deleteSelectedRows();
223        }
224    }
225    
226    void MacroEditor::onMacroTreeViewRowValueChanged(const Gtk::TreeModel::Path& path,
227                                                     const Gtk::TreeModel::iterator& iter)
228    {
229        if (m_ignoreTreeViewValueChange) return;
230        if (!iter) return;
231        Gtk::TreeModel::Row row = *iter;
232        Glib::ustring value    = row[m_treeModelMacro.m_col_value];
233        Serialization::UID uid = row[m_treeModelMacro.m_col_uid];
234        Serialization::String gigvalue(gig_from_utf8(value));
235        Serialization::Object& object = m_macro.objectByUID(uid);
236        std::string errorText;
237        try {
238            m_macro.setAutoValue(object, gigvalue);
239        } catch (Serialization::Exception e) {
240            errorText = e.Message;
241        } catch (...) {
242            errorText = _("Unknown exception during object value change");
243        }
244        if (!errorText.empty()) {
245            Glib::ustring txt = _("Couldn't change value:\n") + errorText;
246            Gtk::MessageDialog msg(*this, txt, false, Gtk::MESSAGE_ERROR);
247            msg.run();
248        }
249    }
250    
251    void MacroEditor::deleteSelectedRows() {
252        Glib::RefPtr<Gtk::TreeSelection> sel = m_treeViewMacro.get_selection();
253        std::vector<Gtk::TreeModel::Path> rows = sel->get_selected_rows();
254        deleteRows(rows);
255    }
256    
257    void MacroEditor::deleteRows(const std::vector<Gtk::TreeModel::Path>& rows) {
258        for (int r = rows.size() - 1; r >= 0; --r) {
259            Gtk::TreeModel::iterator it = m_treeStoreMacro->get_iter(rows[r]);
260            if (!it) continue;
261            Gtk::TreeModel::Row row = *it;
262            Serialization::UID uid = row[m_treeModelMacro.m_col_uid];
263            if (uid == m_macro.rootObject().uid()) continue; // prohibit deleting root object
264            Gtk::TreeModel::iterator itParent = row.parent();
265            if (!itParent) continue;
266            Gtk::TreeModel::Row rowParent = *itParent;
267            Serialization::UID uidParent = rowParent[m_treeModelMacro.m_col_uid];
268            //Serialization::Object& object = m_macro.objectByUID(uid);
269            Serialization::Object& parentObject = m_macro.objectByUID(uidParent);
270            const Serialization::Member& member = parentObject.memberByUID(uid);
271            m_macro.removeMember(parentObject, member);
272            //m_macro.remove(object);
273        }
274        reloadTreeView();
275    }
276    
277    static bool _onEachTreeRow(const Gtk::TreeModel::Path& input, std::vector<Gtk::TreeModel::Path>* output) {
278        output->push_back(input);
279        return false; // continue walking the tree
280    }
281    
282    void MacroEditor::inverseDeleteSelectedRows() {
283        // get all rows of tree view
284        std::vector<Gtk::TreeModel::Path> rows;
285        m_treeViewMacro.get_model()->foreach_path(
286            sigc::bind(
287                sigc::ptr_fun(&_onEachTreeRow),
288                &rows
289            )
290        );
291    
292        // erase all entries from "rows" which are currently selected
293        std::vector<Gtk::TreeModel::Path> vSelected = m_treeViewMacro.get_selection()->get_selected_rows();
294        for (int i = rows.size() - 1; i >= 0; --i) {
295            bool bIsSelected = std::find(vSelected.begin(), vSelected.end(),
296                                         rows[i]) != vSelected.end();
297            if (bIsSelected)
298                rows.erase(rows.begin() + i);
299        }
300    
301        // delete those 'inverse' selected rows
302        deleteRows(rows);
303  }  }
304    
305  void MacroEditor::updateStatus() {  void MacroEditor::updateStatus() {
# Line 214  void MacroEditor::onButtonCancel() { Line 362  void MacroEditor::onButtonCancel() {
362  }  }
363    
364  void MacroEditor::onButtonApply() {  void MacroEditor::onButtonApply() {
365      //m_macro.encode();      std::string errorText;
366      *m_macroOriginal = m_macro;      try {
367            // enforce re-encoding the abstract object model and resetting the
368            // 'modified' state
369            m_macro.rawData();
370            // replace actual effective Archive object which is effectively used
371            // for macro apply operations
372            *m_macroOriginal = m_macro;
373        } catch (Serialization::Exception e) {
374            errorText = e.Message;
375        } catch (...) {
376            errorText = _("Unknown exception while applying macro changes");
377        }
378        if (!errorText.empty()) {
379            Glib::ustring txt = _("Couldn't apply macro changes:\n") + errorText;
380            Gtk::MessageDialog msg(*this, txt, false, Gtk::MESSAGE_ERROR);
381            msg.run();
382        }
383        updateStatus();
384  }  }
385    
386  void MacroEditor::onWindowHide() {  void MacroEditor::onWindowHide() {

Legend:
Removed from v.3151  
changed lines
  Added in v.3155

  ViewVC Help
Powered by ViewVC