]> git.lyx.org Git - lyx.git/blob - src/frontends/kde/FormCitation.C
More preference work from Angus
[lyx.git] / src / frontends / kde / FormCitation.C
1 /*
2  * FormCitation.C
3  * (C) 2000 LyX Team
4  * John Levon, moz@compsoc.man.ac.uk
5  */
6
7 /***************************************************************************
8  *                                                                         *
9  *   This program is free software; you can redistribute it and/or modify  *
10  *   it under the terms of the GNU General Public License as published by  *
11  *   the Free Software Foundation; either version 2 of the License, or     *
12  *   (at your option) any later version.                                   *
13  *                                                                         *
14  ***************************************************************************/
15
16 #include <config.h>
17
18 #include <algorithm> 
19
20 #include "Dialogs.h"
21 #include "FormCitation.h"
22 #include "gettext.h"
23 #include "buffer.h"
24 #include "LyXView.h"
25 #include "lyxfunc.h"
26 #include "citationdlg.h"
27  
28 using std::vector;
29 using std::pair;
30 using std::find;
31  
32 FormCitation::FormCitation(LyXView *v, Dialogs *d)
33         : dialog_(0), lv_(v), d_(d), inset_(0), h_(0), u_(0), ih_(0), 
34         keys(0), chosenkeys(0)
35 {
36         // let the dialog be shown
37         // This is a permanent connection so we won't bother
38         // storing a copy because we won't be disconnecting.
39         d->showCitation.connect(slot(this, &FormCitation::showCitation));
40         d->createCitation.connect(slot(this, &FormCitation::createCitation));
41 }
42
43 FormCitation::~FormCitation()
44 {
45         delete dialog_;
46 }
47
48 void FormCitation::showCitation(InsetCommand * const inset)
49 {
50         // FIXME: when could inset be 0 here ?
51         if (inset==0)
52                 return;
53
54         inset_ = inset;
55         readonly = lv_->buffer()->isReadonly();
56         ih_ = inset_->hide.connect(slot(this,&FormCitation::hide));
57         params = inset->params();
58         
59         show();
60 }
61
62 void FormCitation::createCitation(string const & arg)
63 {
64         // we could already be showing stuff, clear it out
65         if (inset_)
66                 close();
67
68         readonly = lv_->buffer()->isReadonly();
69         params.setFromString(arg);
70         show();
71 }
72
73 void FormCitation::updateButtons()
74
75         if (readonly) {
76                 dialog_->add->setEnabled(false);
77                 dialog_->remove->setEnabled(false);
78                 dialog_->up->setEnabled(false);
79                 dialog_->down->setEnabled(false);
80                 return;
81         }
82
83         bool ischosenkey = !selectedChosenKey.empty();
84  
85         vector<string>::const_iterator iter = 
86                 find(chosenkeys.begin(), chosenkeys.end(), selectedKey);
87
88         dialog_->add->setEnabled(!selectedKey.empty() && iter == chosenkeys.end());
89         dialog_->remove->setEnabled(ischosenkey);
90         dialog_->up->setEnabled(ischosenkey);
91         dialog_->down->setEnabled(ischosenkey);
92 }
93  
94 void FormCitation::updateChosenList()
95 {
96         dialog_->chosen->setAutoUpdate(false);
97         dialog_->chosen->clear();
98
99         for (vector< string >::const_iterator iter = chosenkeys.begin();
100                 iter != chosenkeys.end(); ++iter) {
101                 dialog_->chosen->insertItem(iter->c_str());
102         }
103         dialog_->chosen->setAutoUpdate(true);
104         dialog_->chosen->update();
105 }
106
107 void FormCitation::updateAvailableList()
108 {
109         dialog_->keys->setAutoUpdate(false);
110         dialog_->keys->clear();
111
112         for (vector< pair<string,string> >::const_iterator iter = keys.begin();
113                 iter != keys.end(); ++iter) {
114                 dialog_->keys->insertItem(iter->first.c_str());
115         }
116         dialog_->keys->setAutoUpdate(true);
117         dialog_->keys->update();
118 }
119  
120
121 // we can safely ignore the parameter because we can always update
122 void FormCitation::update(bool)
123 {
124         keys.clear();
125  
126         vector < pair<string,string> > ckeys = lv_->buffer()->getBibkeyList(); 
127
128         for (vector< pair<string,string> >::const_iterator iter = ckeys.begin();
129                 iter != ckeys.end(); ++iter) {
130                 keys.push_back(*iter);
131         }
132  
133         updateAvailableList();
134         selectedKey.erase();
135  
136         chosenkeys.clear();
137  
138         string tmp, paramkeys(params.getContents());
139         paramkeys = frontStrip(split(paramkeys, tmp, ','));
140
141         while (!tmp.empty()) {
142                 chosenkeys.push_back(tmp);
143                 paramkeys = frontStrip(split(paramkeys, tmp, ','));
144         }
145
146         updateChosenList();
147         selectedChosenKey.erase();
148  
149         dialog_->entry->setText("");
150
151         dialog_->after->setText(params.getOptions().c_str());
152
153         updateButtons();
154  
155         if (readonly) {
156                 dialog_->keys->setFocusPolicy(QWidget::NoFocus);
157                 dialog_->chosen->setFocusPolicy(QWidget::NoFocus);
158                 dialog_->after->setFocusPolicy(QWidget::NoFocus);
159                 dialog_->buttonOk->setEnabled(false);
160                 dialog_->buttonCancel->setText(_("&Close"));
161         } else {
162                 dialog_->keys->setFocusPolicy(QWidget::StrongFocus);
163                 dialog_->chosen->setFocusPolicy(QWidget::StrongFocus);
164                 dialog_->after->setFocusPolicy(QWidget::StrongFocus);
165                 dialog_->buttonOk->setEnabled(true);
166                 dialog_->buttonCancel->setText(_("&Cancel"));
167         }
168 }
169
170 void FormCitation::apply()
171 {
172         if (readonly)
173                 return;
174
175         string contents;
176
177         for (vector< string >::const_iterator iter = chosenkeys.begin();
178                 iter != chosenkeys.end(); ++iter) {
179                 if (iter != chosenkeys.begin())
180                         contents += ", ";
181                 contents += *iter;
182         }
183                 
184         params.setContents(contents);
185         params.setOptions(dialog_->after->text());
186          
187         if (inset_ != 0) {
188                 if (params != inset_->params()) {
189                         inset_->setParams(params);
190                         lv_->view()->updateInset(inset_, true);
191                 }
192         } else
193                 lv_->getLyXFunc()->Dispatch(LFUN_CITATION_INSERT, params.getAsString().c_str());
194 }
195
196 void FormCitation::show()
197 {
198         if (!dialog_)
199                 dialog_ = new CitationDialog(this, 0, _("LyX: Citation Reference"), false);
200
201         if (!dialog_->isVisible()) {
202                 h_ = d_->hideBufferDependent.connect(slot(this, &FormCitation::hide));
203                 u_ = d_->updateBufferDependent.connect(slot(this, &FormCitation::update));
204         }
205
206         dialog_->raise();
207         dialog_->setActiveWindow();
208
209         update();
210         dialog_->show();
211 }
212
213 void FormCitation::close()
214 {
215         h_.disconnect();
216         u_.disconnect();
217         ih_.disconnect();
218         inset_ = 0;
219 }
220
221 void FormCitation::hide()
222 {
223         dialog_->hide();
224         close();
225 }
226
227 void FormCitation::selectChosen()
228 {
229         for (unsigned int i=0; i < dialog_->chosen->count(); ++i) {
230                 if (dialog_->chosen->text(i)==selectedChosenKey) {
231                         dialog_->chosen->setSelected(i,true);
232                         dialog_->chosen->setTopItem(i);
233                         break;
234                 }
235         }
236 }
237  
238 void FormCitation::add()
239 {
240         if (selectedKey.empty())
241                 return;
242
243         for (vector< pair<string,string> >::const_iterator iter = keys.begin(); 
244                 iter != keys.end(); ++iter) {
245                 if (iter->first == selectedKey) {
246                         chosenkeys.push_back(iter->first);
247                         break; 
248                 }
249         }
250                  
251         selectedChosenKey.erase();
252         updateChosenList();
253         updateButtons();
254 }
255
256 void FormCitation::remove()
257 {
258         if (selectedChosenKey.empty())
259                 return; 
260
261         for (vector< string >::iterator iter = chosenkeys.begin();
262                 iter != chosenkeys.end(); ++iter) {
263                 if (*iter==selectedChosenKey) {
264                         chosenkeys.erase(iter);
265                         break;
266                 }
267         }
268         selectedChosenKey.erase();
269         updateChosenList();
270         updateButtons();
271 }
272
273 void FormCitation::up()
274 {
275         if (selectedChosenKey.empty())
276                 return;
277
278         // Qt will select the first one on redo, so we need this 
279         string tmp = selectedChosenKey;
280  
281         vector< string >::iterator iter = chosenkeys.begin();
282
283         for (; iter != chosenkeys.end(); ++iter) {
284                 if (*iter==selectedChosenKey && iter!=chosenkeys.begin()) {
285                         string tmp = *iter;
286                         chosenkeys.erase(iter);
287                         chosenkeys.insert(iter-1,tmp);
288                         break;
289                 }
290         }
291         if (iter==chosenkeys.end())
292                 return;
293  
294         updateChosenList();
295         selectedChosenKey=tmp;
296         selectChosen();
297 }
298
299 void FormCitation::down()
300 {
301         if (selectedChosenKey.empty())
302                 return;
303
304         // Qt will select the first one on redo, so we need this 
305         string tmp = selectedChosenKey;
306  
307         vector< string >::iterator iter = chosenkeys.begin();
308
309         for (; iter != chosenkeys.end(); ++iter) {
310                 if (*iter==selectedChosenKey && (iter+1)!=chosenkeys.end()) {
311                         string tmp = *iter;
312                         chosenkeys.erase(iter);
313                         chosenkeys.insert(iter+1, tmp);
314                         break;
315                 }
316         }
317         if (iter==chosenkeys.end())
318                 return;
319  
320         updateChosenList();
321         selectedChosenKey=tmp;
322         selectChosen();
323 }
324  
325 void FormCitation::select_key(const char *key)
326 {
327         if (readonly)
328                 return;
329
330         vector<string>::const_iterator iter = 
331                 find(chosenkeys.begin(), chosenkeys.end(), key);
332
333         if (iter!=chosenkeys.end())
334                 return;
335
336         selectedKey.erase();
337         selectedKey = key;
338
339         add();
340 }
341  
342 void FormCitation::highlight_key(const char *key)
343 {
344         if (readonly)
345                 return;
346
347         selectedKey.erase();
348         selectedKey = key;
349
350         for (unsigned int i=0; i < keys.size(); i++) {
351                 if (keys[i].first==key) {
352                         dialog_->entry->setText(keys[i].second.c_str());
353                         dialog_->chosen->clearFocus();
354                         dialog_->chosen->clearSelection();
355                         selectedChosenKey.erase();
356                         break;
357                 }
358         }
359
360         updateButtons();
361 }
362
363 void FormCitation::highlight_chosen(const char *key)
364 {
365         selectedChosenKey.erase();
366         selectedChosenKey = key;
367  
368         unsigned int i;
369
370         for (i=0; i < keys.size(); i++) {
371                 if (keys[i].first==key) {
372                         if (keys[i].second.compare(dialog_->entry->text()))
373                                 dialog_->entry->setText(keys[i].second.c_str());
374                         dialog_->keys->clearFocus();
375                         dialog_->keys->clearSelection();
376                         selectedKey.erase();
377                         break;
378                 }
379         }
380
381         if (i==keys.size())
382                 dialog_->entry->setText(_("Key not found in references."));
383  
384         updateButtons();
385 }