]> git.lyx.org Git - lyx.git/blob - src/frontends/gnome/FormToc.C
John's FormExternal patch, Edwin's Qt2 patch and Baruch's gnome patch.
[lyx.git] / src / frontends / gnome / FormToc.C
1 // -*- C++ -*-
2 /* This file is part of
3  * ====================================================== 
4  *
5  *           LyX, The Document Processor
6  *
7  *           Copyright 2000 The LyX Team.
8  *
9  * ======================================================
10  */
11
12 #include <config.h>
13 #include <vector>
14
15 #ifdef __GNUG__
16 #pragma implementation
17 #endif
18
19
20 #include "gettext.h"
21 #include "Dialogs.h"
22 #include "FormToc.h"
23 #include "LyXView.h"
24 #include "form_toc.h"
25 #include "lyxtext.h"
26 #include "lyxfunc.h"
27
28 extern "C" {
29 #include "diatoc_interface.h"
30 #include "support.h"
31 }
32
33 #include <gtk--/base.h>
34 #include <gtk--/button.h>
35 #include <gtk--/label.h>
36 #include <gtk--/scrolledwindow.h>
37 #include <gtk--/menu.h>
38 #include <gtk--/menuitem.h>
39
40 using SigC::bind;
41
42 FormToc::FormToc(LyXView * lv, Dialogs * d)
43   : lv_(lv), d_(d), inset_(0), u_(0), h_(0), ih_(0), dialog_(0), ignore_callback_(false)
44 {
45   // let the dialog be shown
46   // These are permanent connections so we won't bother
47   // storing a copy because we won't be disconnecting.
48   d->showTOC.connect(slot(this, &FormToc::showInset));
49   d->createTOC.connect(slot(this, &FormToc::createInset));
50 }
51
52
53 FormToc::~FormToc()
54 {
55   hide();
56 }
57
58 void FormToc::showInset( InsetCommand * const inset )
59 {
60   if( dialog_!=0 || inset == 0 ) return;
61   
62   inset_ = inset;
63   ih_ = inset_->hideDialog.connect(slot(this, &FormToc::hide));
64   
65   params = inset->params();
66   show();
67 }
68
69
70 void FormToc::createInset( string const & arg )
71 {
72   if( dialog_!=0 ) return;
73   
74   params.setFromString( arg );
75   show();
76 }
77
78
79 void FormToc::show()
80 {
81   Gtk::Button * b_refresh;
82   Gtk::Button * b_close;
83   Gtk::ScrolledWindow *scrolled_window;
84
85   if (!dialog_)
86     {
87       GtkWidget * pd = create_DiaToc();
88
89       dialog_ = Gtk::wrap( GNOME_DIALOG(pd) );
90       choice_ = Gtk::wrap( GTK_OPTION_MENU( lookup_widget(pd, "choice") ) );
91       scrolled_window = Gtk::wrap( GTK_SCROLLED_WINDOW( lookup_widget(pd, "scrolledwindow") ) );
92
93       list_ = manage( new Gtk::List() );
94       scrolled_window->add_with_viewport(*list_);
95
96       // fill choice
97       Gtk::MenuItem * e;
98
99       choice_->get_menu()->items().clear();
100       
101       e = manage( new Gtk::MenuItem(_("Table of Contents")) );
102       e->activate.connect(bind<Buffer::TocType>(slot(this, &FormToc::changeList), Buffer::TOC_TOC));
103       choice_->get_menu()->append( *e );
104
105       e = manage( new Gtk::MenuItem(_("List of Figures")) );
106       e->activate.connect(bind<Buffer::TocType>(slot(this, &FormToc::changeList), Buffer::TOC_LOF));
107       choice_->get_menu()->append( *e );
108
109       e = manage( new Gtk::MenuItem(_("List of Tables")) );
110       e->activate.connect(bind<Buffer::TocType>(slot(this, &FormToc::changeList), Buffer::TOC_LOT));
111       choice_->get_menu()->append( *e );
112
113       e = manage( new Gtk::MenuItem(_("List of Algorithms")) );
114       e->activate.connect(bind<Buffer::TocType>(slot(this, &FormToc::changeList), Buffer::TOC_LOA));
115       choice_->get_menu()->append( *e );
116
117       // wrap buttons and connect slots
118       b_refresh = Gtk::wrap( GTK_BUTTON( lookup_widget(pd, "button_refresh") ) );
119       b_close   = Gtk::wrap( GTK_BUTTON( lookup_widget(pd, "button_close") ) );
120       
121       b_refresh->clicked.connect(bind<bool>(slot(this, &FormToc::updateSlot),false));
122       b_close->clicked.connect(dialog_->destroy.slot());
123       dialog_->destroy.connect(slot(this, &FormToc::free));
124
125       u_ = d_->updateBufferDependent.connect(slot(this, &FormToc::updateSlot));
126       h_ = d_->hideBufferDependent.connect(slot(this, &FormToc::hide));
127
128       if (!dialog_->is_visible()) dialog_->show_all();
129
130       updateSlot();  // make sure its up-to-date
131     }
132   else
133     {
134       Gdk_Window dialog_win(dialog_->get_window());
135       dialog_win.raise();
136     }
137 }
138
139
140 // we can safely ignore the parameter because we can always update
141 void FormToc::updateSlot(bool)
142 {
143   Buffer::TocType type;
144   string wintitle;
145
146   if (dialog_ != 0 &&
147       !lv_->view()->available())
148     {
149       wintitle = _( "*** No Document ***");
150       dialog_->set_title(wintitle);
151       list_->items().clear();
152
153       Gtk::ListItem * l = manage( new Gtk::ListItem(wintitle) );
154       list_->items().push_back( *l );
155       return;
156     }
157   
158   
159   if (dialog_ != 0 &&
160       lv_->view()->available())
161     {
162
163       int selection = 0;
164       
165       if( params.getCmdName() == "tableofcontents" )
166         {
167           type = Buffer::TOC_TOC;
168           wintitle = _("Table of Contents");
169           selection = 0;
170         }
171       else if( params.getCmdName() == "listoffigures" )
172         {
173           type = Buffer::TOC_LOF;
174           wintitle = _("List of Figures");
175           selection = 1;
176         }
177       else if( params.getCmdName() == "listofalgorithms" )
178         {
179           type = Buffer::TOC_LOA;
180           wintitle = _("List of Algorithms");
181           selection = 3;
182         }
183       else
184         {
185           type = Buffer::TOC_LOT;
186           wintitle = _("List of Tables");
187           selection = 2;
188         }
189
190       ignore_callback_ = true;
191       choice_->set_history(selection);
192       ignore_callback_ = false;
193       
194       list_->items().clear();
195
196       dialog_->set_title(wintitle);
197
198       vector<Buffer::TocItem> toclist = (lv_->view()->buffer()->getTocList())[type];
199
200       Gtk::ListItem * item;
201
202       vector<Buffer::TocItem>::const_iterator end = toclist.end();
203       for (vector<Buffer::TocItem>::const_iterator it = toclist.begin();
204            it != end; ++it)
205         {
206           item = manage( new Gtk::ListItem(string(4*(*it).depth,' ')+(*it).str) );
207           item->select.connect(bind<Buffer::TocItem>(slot(this,&FormToc::apply), (*it)));
208           list_->add( *item );
209         }
210     }
211
212   dialog_->show_all();
213 }
214
215 void FormToc::apply(Buffer::TocItem tg)
216 {
217 #if 0  
218   // Doesn't compile anymore...
219   if (!lv_->view()->available()) return;
220
221   lv_->view()->beforeChange();
222   lv_->view()->text->SetCursor( lv_->view(), tg.par, 0 );
223   lv_->view()->text->sel_cursor = lv_->view()->text->cursor;
224   lv_->view()->update(BufferView::SELECT|BufferView::FITCUR);
225 #endif
226
227   string const str = tg.str;
228   lv_->getLyXFunc()->Dispatch(LFUN_GOTO_PARAGRAPH, str);
229 }
230
231 void FormToc::changeList(Buffer::TocType type)
232 {
233         if (!ignore_callback_) {
234                 switch (type) {
235                 case Buffer::TOC_TOC :
236                         params.setCmdName("tableofcontents");
237                         break;
238                 case Buffer::TOC_LOF :
239                         params.setCmdName("listoffigures");
240                         break;
241                 case Buffer::TOC_LOT :
242                         params.setCmdName("listoftabels");
243                         break;
244                 case Buffer::TOC_LOA :
245                         params.setCmdName("listofalgorithms");
246                         break;
247                 };
248
249                 updateSlot();
250         }
251 }
252
253 void FormToc::hide()
254 {
255   if (dialog_!=0) dialog_->destroy();
256 }
257
258 void FormToc::free()
259 {
260   if (dialog_!=0)
261     {
262       dialog_ = 0;
263       u_.disconnect();
264       h_.disconnect();
265       inset_ = 0;
266       ih_.disconnect();
267     }
268 }
269