~ubuntu-branches/ubuntu/precise/glom/precise-updates

« back to all changes in this revision

Viewing changes to glom/mode_design/relationships_overview/dialog_relationships_overview.cc

  • Committer: Bazaar Package Importer
  • Author(s): Chris Coulson
  • Date: 2009-10-09 16:50:36 UTC
  • mfrom: (1.1.42 upstream)
  • Revision ID: james.westby@ubuntu.com-20091009165036-orinvwmohk838xxl
Tags: 1.12.2-0ubuntu1
* New upstream version:
  - FFE LP: #391664
* debian/control:
  - Bump python-gnome2-extras-dev build-dep to >= 2.25.3.
  - Bump libgdamm3.0-dev build-dep to libgdamm4.0-dev >= 3.99.14.
  - Change libgda3-dev build-dep to libgda-4.0-dev.
  - Change libgda3-postgres dependency to libgda-4.0-postgres.
  - Bump libgtkmm-2.4-dev build-dep to >= 2.14.
  - Add build-dep on libgconfmm-2.6-dev.
  - Bump libgoocanvasmm-dev build-dep to >= 0.14.0.
  - Remove build-dep on libbakery-2.6-dev.
  - Bump postgresql-8.3 dependency to postgresql-8.4.
  - Change scrollkeeper build-dep to rarian-compat.
  - Rename libglom{0,-dev} -> libglom-1.12-{0,dev}. Upstream include
    APIVER in the library name now.
* debian/rules:
  - Update --with-postgres-utils configure flag to point to the new
    path.
  - Drop deprecated --disable-scrollkeeper configure flag.
  - Update DEB_SHLIBDEPS_INCLUDE with new libglom-1.12-0 package name.
  - Don't include /usr/share/cdbs/1/rules/simple-patchsys.mk - there
    are currently no patches.
* debian/libglom-1.12-0.install:
  - Updated for new version.
* debian/libglom-1.12-dev.install:
  - Install pc and header files.
* debian/glom-doc.install:
  - Updated for new version.
* debian/glom.install:
  - Updated for new version.
* Fix debian/watch.
* Dropped obsolete 10-distro-install-postgres-change.patch.
* Built against latest libgoocanvasmm (LP: #428445).
* Also closes LP: #230007, LP: #393229, LP: #393231, LP: #394507,
  LP: #394887, LP: #394894, LP: #397409, LP: #381563.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* Glom
 
2
 * 
 
3
 * Copyright (C) 2001-2004 Murray Cumming
 
4
 *
 
5
 * This program is free software; you can redistribute it and/or
 
6
 * modify it under the terms of the GNU General Public License as
 
7
 * published by the Free Software Foundation; either version 2 of the
 
8
 * License, or (at your option) any later version.
 
9
 *
 
10
 * This program is distributed in the hope that it will be useful, but
 
11
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 
13
 * General Public License for more details.
 
14
 *
 
15
 * You should have received a copy of the GNU General Public
 
16
 * License along with this program; if not, write to the
 
17
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 
18
 * Boston, MA 02111-1307, USA.
 
19
 */
 
20
 
 
21
#include "config.h"
 
22
#include "dialog_relationships_overview.h"
 
23
#include "glom/utility_widgets/canvas/canvas_line_movable.h"
 
24
#include "glom/utility_widgets/canvas/canvas_text_movable.h"
 
25
#include <glom/mode_design/layout/dialog_choose_relationship.h>
 
26
#include "printoperation_relationshipsoverview.h"
 
27
#include "glom/application.h"
 
28
#include <goocanvas.h>
 
29
#include <glibmm/i18n.h>
 
30
#include <algorithm>
 
31
 
 
32
namespace Glom
 
33
{
 
34
 
 
35
//static:
 
36
int Dialog_RelationshipsOverview::m_last_size_x = 0;
 
37
int Dialog_RelationshipsOverview::m_last_size_y = 0;
 
38
 
 
39
 
 
40
Dialog_RelationshipsOverview::Dialog_RelationshipsOverview(BaseObjectType* cobject, const Glib::RefPtr<Gtk::Builder>& builder)
 
41
  : Gtk::Dialog(cobject),
 
42
    m_menu(0),
 
43
    m_modified(false),
 
44
    m_scrolledwindow_canvas(0)
 
45
{
 
46
  m_refPageSetup = Gtk::PageSetup::create();
 
47
  m_refSettings = Gtk::PrintSettings::create();
 
48
 
 
49
  //Add a menu:
 
50
  Gtk::VBox* vbox = 0;
 
51
  builder->get_widget("vbox_placeholder_menubar", vbox);
 
52
 
 
53
  m_refActionGroup = Gtk::ActionGroup::create();
 
54
 
 
55
  m_refActionGroup->add(Gtk::Action::create("Overview_MainMenu_File", _("_File")) );
 
56
  m_refActionGroup->add(Gtk::Action::create("Overview_MainMenu_File_PageSetup", _("Page _Setup")),
 
57
    sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_menu_file_page_setup) );
 
58
  m_refActionGroup->add(Gtk::Action::create("Overview_MainMenu_File_Print", Gtk::Stock::PRINT),
 
59
    sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_menu_file_print) );
 
60
 
 
61
  m_refActionGroup->add(Gtk::Action::create("Overview_MainMenu_View", _("_View")) );
 
62
  m_action_showgrid = Gtk::ToggleAction::create("Overview_MainMenu_View_Grid", _("Show _Grid"));
 
63
  m_refActionGroup->add(m_action_showgrid,
 
64
    sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_menu_view_showgrid) );
 
65
 
 
66
  Glib::RefPtr<Gtk::UIManager> m_refUIManager = Gtk::UIManager::create();
 
67
 
 
68
  m_refUIManager->insert_action_group(m_refActionGroup);
 
69
 
 
70
  #ifdef GLIBMM_EXCEPTIONS_ENABLED
 
71
  try
 
72
  {
 
73
  #endif
 
74
    static const Glib::ustring ui_description =
 
75
    "<ui>"
 
76
#ifdef GLOM_ENABLE_MAEMO
 
77
    "  <popup name='Overview_MainMenu'>"
 
78
#else
 
79
    "  <menubar name='Overview_MainMenu'>"
 
80
#endif
 
81
    "    <menu action='Overview_MainMenu_File'>"
 
82
    "      <menuitem action='Overview_MainMenu_File_PageSetup' />"
 
83
    "      <menuitem action='Overview_MainMenu_File_Print' />"
 
84
    "    </menu>"
 
85
    "    <menu action='Overview_MainMenu_View'>"
 
86
    "      <menuitem action='Overview_MainMenu_View_Grid' />"
 
87
    "    </menu>"
 
88
#ifdef GLOM_ENABLE_MAEMO
 
89
    "  </popup>"
 
90
#else
 
91
    "  </menubar>"
 
92
#endif
 
93
    "</ui>";
 
94
 
 
95
  #ifdef GLIBMM_EXCEPTIONS_ENABLED
 
96
    m_refUIManager->add_ui_from_string(ui_description);
 
97
  }
 
98
  catch(const Glib::Error& ex)
 
99
  {
 
100
    std::cerr << "building menus failed: " <<  ex.what();
 
101
  }
 
102
  #else
 
103
  std::auto_ptr<Glib::Error> error;
 
104
  m_refUIManager->add_ui_from_string(ui_info, error);
 
105
  if(error.get() != NULL)
 
106
  {
 
107
    std::cerr << "building menus failed: " << error->what();
 
108
  }
 
109
  #endif
 
110
 
 
111
  //Get the menu:
 
112
  m_menu = dynamic_cast<Gtk::MenuBar*>( m_refUIManager->get_widget("/Overview_MainMenu") ); 
 
113
  if(!m_menu)
 
114
    g_warning("menu not found");
 
115
 
 
116
  vbox->pack_start(*m_menu, Gtk::PACK_SHRINK);
 
117
  m_menu->show();
 
118
 
 
119
 
 
120
  //Get the scolled window and add the canvas to it:
 
121
  m_scrolledwindow_canvas = 0;
 
122
  builder->get_widget("scrolledwindow_canvas", m_scrolledwindow_canvas);
 
123
  
 
124
  m_scrolledwindow_canvas->add(m_canvas);
 
125
  m_canvas.show();
 
126
  
 
127
  //Restore the previous window size, to avoid annoying the user:
 
128
  if(m_last_size_x != 0 && m_last_size_y != 0 )
 
129
  {
 
130
    set_default_size(m_last_size_x, m_last_size_y);
 
131
  }
 
132
 
 
133
  m_group_tables = Goocanvas::Group::create();
 
134
  m_canvas.add_item(m_group_tables);
 
135
  m_group_lines = Goocanvas::Group::create();
 
136
  m_canvas.add_item(m_group_lines);
 
137
  m_group_lines->lower(); //Make sure that the lines are below the tables.
 
138
 
 
139
  //Respond to changes of window size, 
 
140
  //so we always make the canvas bounds big enough: 
 
141
  m_scrolledwindow_canvas->get_hadjustment()->signal_changed().connect(
 
142
    sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_scroll_value_changed) );
 
143
  m_scrolledwindow_canvas->get_vadjustment()->signal_changed().connect(
 
144
    sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_scroll_value_changed) );
 
145
 
 
146
  setup_context_menu();
 
147
}
 
148
 
 
149
Dialog_RelationshipsOverview::~Dialog_RelationshipsOverview()
 
150
{
 
151
  get_size(m_last_size_x, m_last_size_y);
 
152
}
 
153
 
 
154
 
 
155
void Dialog_RelationshipsOverview::draw_tables()
 
156
{
 
157
  //Remove all current items:
 
158
  while(m_group_tables->get_n_children() > 0)
 
159
    m_group_tables->remove_child(0);
 
160
  
 
161
  Document* document = dynamic_cast<Document*>(get_document());
 
162
  if(document)
 
163
  {
 
164
    double max_table_height = 0;
 
165
    double sizex = 10;
 
166
    double sizey = 10;
 
167
 
 
168
    //Create tables canvas items, with lists of fields:
 
169
    Document::type_listTableInfo tables = document->get_tables();
 
170
    for(Document::type_listTableInfo::iterator iter = tables.begin(); iter != tables.end(); ++iter)
 
171
    {
 
172
      sharedptr<TableInfo> info = *iter;
 
173
      const Glib::ustring table_name = info->get_name();
 
174
     
 
175
      float table_x = 0;
 
176
      float table_y = 0;
 
177
      //Get the x and y position from the document:
 
178
      if(!document->get_table_overview_position(table_name, table_x, table_y))
 
179
      {
 
180
        table_x = sizex;
 
181
        table_y = sizey;
 
182
        document->set_table_overview_position(table_name, table_x, table_y);
 
183
        m_modified = true;
 
184
      }
 
185
 
 
186
      Document::type_vec_fields fields = document->get_table_fields(table_name);
 
187
 
 
188
      Glib::RefPtr<CanvasGroupDbTable> table_group = 
 
189
        CanvasGroupDbTable::create(info->get_name(), info->get_title_or_name(), fields, table_x, table_y);
 
190
      m_group_tables->add_child(table_group);
 
191
 
 
192
      table_group->signal_moved().connect( sigc::bind(
 
193
         sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_table_moved),
 
194
         table_group) );
 
195
      table_group->signal_show_context().connect( sigc::bind(
 
196
         sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_table_show_context),
 
197
         table_group) );
 
198
    
 
199
      //tv->x2 = tv->x1 + table_width;
 
200
      //tv->y2 = tv->y1 + table_height;
 
201
      
 
202
      sizex += table_group->get_table_width() + 10;
 
203
 
 
204
      max_table_height = std::max(max_table_height, table_group->get_table_height());
 
205
    }
 
206
 
 
207
    m_canvas.set_bounds(0, 0, sizex, max_table_height * tables.size());
 
208
  }
 
209
}
 
210
   
 
211
void Dialog_RelationshipsOverview::draw_lines()
 
212
{
 
213
  //Remove all current items:
 
214
  while(m_group_lines->get_n_children() > 0)
 
215
    m_group_lines->remove_child(0);
 
216
   
 
217
  Document* document = dynamic_cast<Document*>(get_document());
 
218
  if(document)
 
219
  { 
 
220
    //Create the lines linking tables to show relationships:
 
221
    Document::type_listTableInfo tables = document->get_tables();
 
222
    for(Document::type_listTableInfo::iterator iter = tables.begin(); iter != tables.end(); ++iter)
 
223
    {
 
224
      sharedptr<TableInfo> info = *iter;
 
225
      const Glib::ustring table_name = info->get_name();
 
226
 
 
227
      Document::type_vec_relationships m_relationships = document->get_relationships(table_name);
 
228
      Document::type_vec_fields fields = document->get_table_fields(table_name);
 
229
      
 
230
      for(Document::type_vec_relationships::const_iterator rit = m_relationships.begin(); rit != m_relationships.end(); rit++)
 
231
      {
 
232
        sharedptr<const Relationship> relationship = *rit;
 
233
        if(!relationship)
 
234
          continue;
 
235
 
 
236
        Glib::RefPtr<CanvasGroupDbTable> group_from = get_table_group(relationship->get_from_table());
 
237
 
 
238
        double from_field_x = 0.0;
 
239
        double from_field_y = 0.0;
 
240
 
 
241
        if(group_from)
 
242
        {
 
243
          double temp_x = 0.0;
 
244
          double temp_y = 0.0;
 
245
          group_from->get_xy(temp_x, temp_y);
 
246
        
 
247
          from_field_x = temp_x;
 
248
          from_field_y = temp_y + group_from->get_field_y(relationship->get_from_field());
 
249
        }
 
250
 
 
251
        //Only primary keys can be to fields:
 
252
        if(true) //document->get_field(relationship->get_to_table(), relationship->get_to_field())->get_primary_key())
 
253
        {
 
254
          Glib::RefPtr<CanvasGroupDbTable> group_to = get_table_group(relationship->get_to_table());
 
255
 
 
256
          double to_field_x = 0.0;
 
257
          double to_field_y = 0.0;
 
258
 
 
259
          if(group_to)
 
260
          {
 
261
            double temp_x = 0.0;
 
262
            double temp_y = 0.0;
 
263
            group_to->get_xy(temp_x, temp_y);
 
264
            to_field_x = temp_x;
 
265
            to_field_y = temp_y + group_to->get_field_y(relationship->get_to_field());
 
266
          }
 
267
 
 
268
          //Start the line from the right of the from table instead of the left, if the to table is to the right:
 
269
          double extra_line = 0; //An extra horizontal line before the real diagonal line starts. 
 
270
          if(to_field_x > from_field_x)
 
271
          {
 
272
            from_field_x += group_from->get_table_width();
 
273
            extra_line = 20;
 
274
          }
 
275
          else
 
276
          {
 
277
            to_field_x += group_to->get_table_width();
 
278
            extra_line = -20;
 
279
          }
 
280
 
 
281
          //Create the line:
 
282
          Glib::RefPtr<CanvasLineMovable> line = CanvasLineMovable::create();
 
283
          double points_coordinates[] = {from_field_x, from_field_y,
 
284
            from_field_x + extra_line, from_field_y,
 
285
            to_field_x - extra_line, to_field_y,
 
286
            to_field_x, to_field_y};
 
287
          Goocanvas::Points points(4, points_coordinates);
 
288
          line->property_points() = points;
 
289
          line->property_stroke_color() = "black";
 
290
          line->property_line_width() = 1.0;
 
291
          line->property_start_arrow() = false;
 
292
          line->property_end_arrow() = true;
 
293
          line->property_arrow_width() = 10.0;
 
294
          line->property_arrow_length() = 10.0;
 
295
          line->set_movement_allowed(false, false); //Don't let the user move this by dragging.
 
296
          m_group_lines->add_child(line);
 
297
 
 
298
          //Create a text item, showing the name of the relationship on the line:
 
299
          //
 
300
          //Raise or lower the text slightly to make it show above the line when horizontal, 
 
301
          //and to avoid overwriting a relationship in the other direction:
 
302
          //TODO: This is not very clear. Investigate how other systems show this.
 
303
          double y_offset = (from_field_x < to_field_x) ? -10 : +10; 
 
304
          if(from_field_x == to_field_x)
 
305
            y_offset = (from_field_y < to_field_y) ? -10 : +10; 
 
306
 
 
307
          const double text_x = (from_field_x + to_field_x) / 2;
 
308
          const double text_y = ((from_field_y + to_field_y) / 2) + y_offset;
 
309
          Glib::RefPtr<CanvasTextMovable> text = CanvasTextMovable::create(relationship->get_title_or_name(),
 
310
            text_x, text_y, -1, //TODO: Calc a suitable width.
 
311
            Gtk::ANCHOR_CENTER);
 
312
          text->property_font() = "sans 10";
 
313
          text->property_use_markup() = true;
 
314
          text->set_movement_allowed(false, false); //Move only as part of the parent group.
 
315
          m_group_lines->add_child(text);
 
316
        }
 
317
      }
 
318
    }
 
319
  }
 
320
  else
 
321
  {
 
322
    std::cout << "ERROR: Could not retrieve the Glom document." << std::endl;
 
323
  }
 
324
}
 
325
 
 
326
void Dialog_RelationshipsOverview::load_from_document()
 
327
{
 
328
  draw_tables();
 
329
  draw_lines();
 
330
}
 
331
 
 
332
void Dialog_RelationshipsOverview::on_response(int /* id */)
 
333
{
 
334
  if(m_modified && get_document())
 
335
    get_document()->set_modified();
 
336
    
 
337
  hide();
 
338
}
 
339
 
 
340
void Dialog_RelationshipsOverview::on_menu_file_print()
 
341
{
 
342
  print_or_preview(Gtk::PRINT_OPERATION_ACTION_PRINT_DIALOG);
 
343
}
 
344
 
 
345
void Dialog_RelationshipsOverview::on_menu_file_page_setup()
 
346
{
 
347
  //Show the page setup dialog, asking it to start with the existing settings:
 
348
  Glib::RefPtr<Gtk::PageSetup> new_page_setup =
 
349
      Gtk::run_page_setup_dialog(*this, m_refPageSetup, m_refSettings);
 
350
 
 
351
  //Save the chosen page setup dialog for use when printing, previewing, or
 
352
  //showing the page setup dialog again:
 
353
  m_refPageSetup = new_page_setup;
 
354
}
 
355
 
 
356
void Dialog_RelationshipsOverview::on_menu_view_showgrid()
 
357
{
 
358
  if(m_action_showgrid->get_active())
 
359
  {
 
360
    std::cout << "showing" << std::endl;
 
361
    m_canvas.set_grid_gap(40);
 
362
  }
 
363
  else
 
364
  {
 
365
    std::cout << "hiding" << std::endl;
 
366
    m_canvas.remove_grid();
 
367
  }
 
368
}
 
369
 
 
370
void Dialog_RelationshipsOverview::on_menu_file_save()
 
371
{
 
372
}
 
373
 
 
374
void Dialog_RelationshipsOverview::print_or_preview(Gtk::PrintOperationAction print_action)
 
375
{
 
376
  //Create a new PrintOperation with our PageSetup and PrintSettings:
 
377
  //(We use our derived PrintOperation class)
 
378
  Glib::RefPtr<PrintOperationRelationshipsOverview> print = PrintOperationRelationshipsOverview::create();
 
379
  print->set_canvas(&m_canvas);
 
380
 
 
381
  print->set_track_print_status();
 
382
  print->set_default_page_setup(m_refPageSetup);
 
383
  print->set_print_settings(m_refSettings);
 
384
 
 
385
  //print->signal_done().connect(sigc::bind(sigc::mem_fun(*this,
 
386
  //                &ExampleWindow::on_printoperation_done), print));
 
387
 
 
388
  try
 
389
  {
 
390
    print->run(print_action /* print or preview */, *this);
 
391
  }
 
392
  catch (const Gtk::PrintError& ex)
 
393
  {
 
394
    //See documentation for exact Gtk::PrintError error codes.
 
395
    std::cerr << "An error occurred while trying to run a print operation:"
 
396
        << ex.what() << std::endl;
 
397
  }
 
398
}
 
399
 
 
400
Glib::RefPtr<CanvasGroupDbTable> Dialog_RelationshipsOverview::get_table_group(const Glib::ustring& table_name)
 
401
{
 
402
  const int count = m_group_tables->get_n_children();
 
403
  for(int i = 0; i < count; ++i)
 
404
  {
 
405
    Glib::RefPtr<Goocanvas::Item> item = m_group_tables->get_child(i);
 
406
    Glib::RefPtr<CanvasGroupDbTable> table_item = Glib::RefPtr<CanvasGroupDbTable>::cast_dynamic(item);
 
407
    if(table_item && (table_item->get_table_name() == table_name))
 
408
    {
 
409
      return table_item;
 
410
    }
 
411
 
 
412
  }
 
413
 
 
414
  return Glib::RefPtr<CanvasGroupDbTable>();
 
415
}
 
416
 
 
417
void Dialog_RelationshipsOverview::on_table_moved(const Glib::RefPtr<CanvasGroupDbTable>& table)
 
418
{
 
419
  Document* document = dynamic_cast<Document*>(get_document());
 
420
  if(document && table)
 
421
  {
 
422
    //Save the new position in the document:
 
423
    double x = 0;
 
424
    double y = 0;
 
425
    table->get_xy(x, y);
 
426
    document->set_table_overview_position(table->get_table_name(), x, y);
 
427
  }
 
428
 
 
429
  //It is probably incredibly inefficient to recreate the lines repeatedly while dragging a table, 
 
430
  //but it seems to work OK, and it makes the code much simpler.
 
431
  //If this is a problem, we should just change the start/end coordinates of any lines connected to the moved table.
 
432
  draw_lines();
 
433
}
 
434
 
 
435
void Dialog_RelationshipsOverview::on_table_show_context(guint button, guint32 activate_time, const Glib::RefPtr<CanvasGroupDbTable>& table)
 
436
{
 
437
  if(m_action_edit_fields)
 
438
  {
 
439
    // Disconnect the previous handler, 
 
440
    // and connect a new one, with the correct table as a bound parameter:
 
441
    m_connection_edit_fields.disconnect();
 
442
    m_connection_edit_fields = m_action_edit_fields->signal_activate().connect( 
 
443
      sigc::bind( sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_context_menu_edit_fields), table ));
 
444
 
 
445
    m_connection_edit_relationships.disconnect();
 
446
    m_connection_edit_relationships = m_action_edit_relationships->signal_activate().connect( 
 
447
      sigc::bind( sigc::mem_fun(*this, &Dialog_RelationshipsOverview::on_context_menu_edit_relationships), table ));
 
448
  }
 
449
 
 
450
  if(m_context_menu)
 
451
    m_context_menu->popup(button, activate_time);
 
452
 
 
453
}
 
454
 
 
455
void Dialog_RelationshipsOverview::setup_context_menu()
 
456
{
 
457
  m_context_menu_action_group = Gtk::ActionGroup::create();
 
458
 
 
459
  m_context_menu_action_group->add(Gtk::Action::create("ContextMenu", "Context Menu") );
 
460
 
 
461
  m_action_edit_fields = Gtk::Action::create("ContextEditFields", _("Edit _Fields"));
 
462
  m_context_menu_action_group->add(m_action_edit_fields);
 
463
 
 
464
  m_action_edit_relationships = Gtk::Action::create("ContextEditRelationships", _("Edit _Relationships"));
 
465
  m_context_menu_action_group->add(m_action_edit_relationships);
 
466
 
 
467
  m_context_menu_uimanager = Gtk::UIManager::create();
 
468
  m_context_menu_uimanager->insert_action_group(m_context_menu_action_group);
 
469
 
 
470
  #ifdef GLIBMM_EXCEPTIONS_ENABLED
 
471
  try
 
472
  {
 
473
  #endif
 
474
    Glib::ustring ui_info = 
 
475
    "<ui>"
 
476
    "  <popup name='ContextMenu'>"
 
477
    "  <menuitem action='ContextEditFields'/>"
 
478
    "  <menuitem action='ContextEditRelationships'/>"
 
479
    "  </popup>"
 
480
    "</ui>";
 
481
 
 
482
  #ifdef GLIBMM_EXCEPTIONS_ENABLED
 
483
    m_context_menu_uimanager->add_ui_from_string(ui_info);
 
484
  }
 
485
  catch(const Glib::Error& ex)
 
486
  {
 
487
    std::cerr << "building menus failed: " <<  ex.what();
 
488
  }
 
489
  #else
 
490
  std::auto_ptr<Glib::Error> error;
 
491
  m_context_menu_uimanager->add_ui_from_string(ui_info, error);
 
492
  if(error.get() != NULL)
 
493
  {
 
494
    std::cerr << "building menus failed: " << error->what();
 
495
  }
 
496
  #endif
 
497
 
 
498
  //Get the menu:
 
499
  m_context_menu = dynamic_cast<Gtk::Menu*>( m_context_menu_uimanager->get_widget("/ContextMenu") ); 
 
500
}
 
501
 
 
502
void Dialog_RelationshipsOverview::on_context_menu_edit_fields(const Glib::RefPtr<CanvasGroupDbTable>& table)
 
503
{
 
504
  App_Glom* pApp = App_Glom::get_application();
 
505
  if(pApp && table)
 
506
  {
 
507
    pApp->do_menu_developer_fields(*this, table->get_table_name());
 
508
    //draw_tables();
 
509
    //draw_lines();
 
510
  }
 
511
}
 
512
 
 
513
void Dialog_RelationshipsOverview::on_context_menu_edit_relationships(const Glib::RefPtr<CanvasGroupDbTable>& table)
 
514
{
 
515
  App_Glom* pApp = App_Glom::get_application();
 
516
  if(pApp && table)
 
517
  {
 
518
    pApp->do_menu_developer_relationships(*this, table->get_table_name());
 
519
    //draw_tables();
 
520
    //draw_lines();
 
521
  }
 
522
}
 
523
 
 
524
 
 
525
void Dialog_RelationshipsOverview::on_scroll_value_changed()
 
526
{
 
527
  if(!m_scrolledwindow_canvas)
 
528
    return;
 
529
 
 
530
  double width = m_scrolledwindow_canvas->get_hadjustment()->get_page_size();
 
531
  double height = m_scrolledwindow_canvas->get_vadjustment()->get_page_size();
 
532
  //double x = m_scrolledwindow_canvas->get_hadjustment()->get_value();
 
533
  //double y = m_scrolledwindow_canvas->get_vadjustment()->get_value();
 
534
  
 
535
  //Make sure that the canvas bounds are as big as the scrollable area:
 
536
  double old_left = 0;
 
537
  double old_top = 0;
 
538
  double old_right = 0;
 
539
  double old_bottom = 0;
 
540
  m_canvas.get_bounds(old_left, old_top, old_right, old_bottom);
 
541
  
 
542
  const double old_height = old_bottom - old_top;
 
543
  const double old_width = old_right - old_left;
 
544
 
 
545
  if( (width > old_width) ||
 
546
      (height > old_height) )
 
547
  {
 
548
    m_canvas.set_bounds(0, 0, width, height);
 
549
  }
 
550
}
 
551
 
 
552
} //namespace Glom
 
553