]> git.lyx.org Git - lyx.git/blob - src/frontends/Dialogs.C
disable open dialogs if applying them is not allowed
[lyx.git] / src / frontends / Dialogs.C
1 /**
2  * \file frontends/Dialogs.C
3  * This file is part of LyX, the document processor.
4  * Licence details can be found in the file COPYING.
5  *
6  * \author Angus Leeming
7  *
8  * Full author contact details are available in file CREDITS.
9  *
10  * Common to all frontends' Dialogs
11  */
12
13 #include <config.h>
14
15 #include "Dialogs.h"
16
17 #include "controllers/Dialog.h"
18
19 #include <boost/signal.hpp>
20 #include <boost/bind.hpp>
21
22
23 using std::string;
24 using lyx::frontend::Dialog;
25
26
27 // Note that static boost signals break some compilers, so this wrapper
28 // initialises the signal dynamically when it is first invoked.
29 template<typename Signal>
30 class BugfixSignal {
31 public:
32         Signal & operator()() { return thesignal(); }
33         Signal const & operator()() const { return thesignal(); }
34
35 private:
36         Signal & thesignal() const
37         {
38                 if (!signal_.get())
39                         signal_.reset(new Signal);
40                 return *signal_;
41         }
42
43         mutable boost::scoped_ptr<Signal> signal_;
44 };
45
46
47 boost::signal<void()> & Dialogs::redrawGUI()
48 {
49         static BugfixSignal<boost::signal<void()> > thesignal;
50         return thesignal();
51 }
52
53
54 namespace {
55
56 BugfixSignal<boost::signal<void(string const &, InsetBase*)> > hideSignal;
57
58 }
59
60
61 void Dialogs::hide(string const & name, InsetBase* inset)
62 {
63         hideSignal()(name, inset);
64 }
65
66
67 Dialogs::Dialogs(LyXView & lyxview)
68         : lyxview_(lyxview), in_show_(false)
69 {
70         // Connect signals
71         redrawGUI().connect(boost::bind(&Dialogs::redraw, this));
72 }
73
74
75 Dialog * Dialogs::find_or_build(string const & name)
76 {
77         if (!isValidName(name))
78                 return 0;
79
80         std::map<string, DialogPtr>::iterator it =
81                 dialogs_.find(name);
82
83         if (it != dialogs_.end())
84                 return it->second.get();
85
86         dialogs_[name] = build(name);
87         return dialogs_[name].get();
88 }
89
90
91 void Dialogs::show(string const & name, string const & data)
92 {
93         if (in_show_) {
94                 return;
95         }
96         in_show_ = true;
97         Dialog * dialog = find_or_build(name);
98         if (dialog) {
99                 // FIXME! Should check that the dialog is NOT an inset dialog.
100                 dialog->show(data);
101         }       
102         in_show_ = false;
103 }
104
105
106 void Dialogs::show(string const & name, string const & data, InsetBase * inset)
107 {
108         if (in_show_) {
109                 return;
110         }
111         in_show_ = true;
112         Dialog * dialog = find_or_build(name);
113         if (dialog) {
114                 // FIXME! Should check that the dialog IS an inset dialog.
115                 dialog->show(data);
116                 open_insets_[name] = inset;
117         }
118         in_show_ = false;
119 }
120
121
122 bool Dialogs::visible(string const & name) const
123 {
124         std::map<string, DialogPtr>::const_iterator it =
125                 dialogs_.find(name);
126         if (it == dialogs_.end())
127                 return false;
128         return it->second.get()->isVisible();
129 }
130
131
132 void Dialogs::update(string const & name, string const & data)
133 {
134         std::map<string, DialogPtr>::const_iterator it =
135                 dialogs_.find(name);
136         if (it == dialogs_.end())
137                 return;
138
139         Dialog * const dialog = it->second.get();
140         if (dialog->isVisible())
141                 dialog->update(data);
142 }
143
144
145 void Dialogs::hideSlot(string const & name, InsetBase * inset)
146 {
147         std::map<string, DialogPtr>::const_iterator it =
148                 dialogs_.find(name);
149         if (it == dialogs_.end())
150                 return;
151
152         if (inset && inset != getOpenInset(name))
153                 return;
154
155         Dialog * const dialog = it->second.get();
156         if (dialog->isVisible())
157                 dialog->hide();
158         open_insets_[name] = 0;
159 }
160
161
162 void Dialogs::disconnect(string const & name)
163 {
164         if (!isValidName(name))
165                 return;
166
167         open_insets_[name] = 0;
168 }
169
170
171 InsetBase * Dialogs::getOpenInset(string const & name) const
172 {
173         if (!isValidName(name))
174                 return 0;
175
176         std::map<string, InsetBase *>::const_iterator it =
177                 open_insets_.find(name);
178         return it == open_insets_.end() ? 0 : it->second;
179 }
180
181
182 void Dialogs::hideAll() const
183 {
184         std::map<string, DialogPtr>::const_iterator it  = dialogs_.begin();
185         std::map<string, DialogPtr>::const_iterator end = dialogs_.end();
186
187         for(; it != end; ++it) {
188                 it->second->hide();
189         }
190 }
191
192
193 void Dialogs::hideBufferDependent() const
194 {
195         std::map<string, DialogPtr>::const_iterator it  = dialogs_.begin();
196         std::map<string, DialogPtr>::const_iterator end = dialogs_.end();
197
198         for(; it != end; ++it) {
199                 Dialog * dialog =  it->second.get();
200                 if (dialog->controller().isBufferDependent())
201                         dialog->hide();
202         }
203 }
204
205
206 void Dialogs::updateBufferDependent(bool switched) const
207 {
208         std::map<string, DialogPtr>::const_iterator it  = dialogs_.begin();
209         std::map<string, DialogPtr>::const_iterator end = dialogs_.end();
210
211         for(; it != end; ++it) {
212                 Dialog * dialog =  it->second.get();
213                 if (switched && dialog->controller().isBufferDependent()) {
214                         dialog->hide();
215                 } else {
216                         // A bit clunky, but the dialog will request
217                         // that the kernel provides it with the necessary
218                         // data.
219                         dialog->RestoreButton();
220                 }
221         }
222 }
223
224
225 void Dialogs::redraw() const
226 {
227         std::map<string, DialogPtr>::const_iterator it  = dialogs_.begin();
228         std::map<string, DialogPtr>::const_iterator end = dialogs_.end();
229
230         for(; it != end; ++it) {
231                 it->second->redraw();
232         }
233 }
234
235
236 void Dialogs::checkStatus()
237 {
238         std::map<string, DialogPtr>::const_iterator it  = dialogs_.begin();
239         std::map<string, DialogPtr>::const_iterator end = dialogs_.end();
240
241         for(; it != end; ++it) {
242                 Dialog * const dialog = it->second.get();
243                 if (dialog->isVisible())
244                         dialog->checkStatus();
245         }
246 }