blob: 6b3442cd07f209906ea04c4a95333cd4a4cc2697 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
2 * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
3 * Released under the terms of the GNU GPL v2.0.
4 */
5
Alexander Stein133c5f72010-08-31 17:34:37 +02006#include <qglobal.h>
7
Boris Barbulovskib1f8a452015-09-22 11:36:02 -07008#include <QMainWindow>
Boris Barbulovski041fbdc2015-09-22 11:36:05 -07009#include <QList>
Boris Barbulovski924bbb52015-09-22 11:36:06 -070010#include <qtextbrowser.h>
Boris Barbulovski85eaf282015-09-22 11:36:03 -070011#include <QAction>
Boris Barbulovskibea00772015-09-22 11:36:04 -070012#include <QFileDialog>
Boris Barbulovski76bede82015-09-22 11:36:07 -070013#include <QMenu>
Alexander Stein133c5f72010-08-31 17:34:37 +020014
15#include <qapplication.h>
Markus Heidelberg8d90c972009-05-18 01:36:52 +020016#include <qdesktopwidget.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070017#include <qtoolbar.h>
Roman Zippel43bf6122006-06-08 22:12:45 -070018#include <qlayout.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070019#include <qsplitter.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070020#include <qlineedit.h>
Roman Zippel43bf6122006-06-08 22:12:45 -070021#include <qlabel.h>
22#include <qpushbutton.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070023#include <qmenubar.h>
24#include <qmessagebox.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070025#include <qregexp.h>
Alexander Stein133c5f72010-08-31 17:34:37 +020026#include <qevent.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070027
28#include <stdlib.h>
29
30#include "lkc.h"
31#include "qconf.h"
32
33#include "qconf.moc"
34#include "images.c"
35
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -070036#ifdef _
37# undef _
38# define _ qgettext
39#endif
40
Linus Torvalds1da177e2005-04-16 15:20:36 -070041static QApplication *configApp;
Roman Zippel7fc925f2006-06-08 22:12:46 -070042static ConfigSettings *configSettings;
Linus Torvalds1da177e2005-04-16 15:20:36 -070043
Boris Barbulovski85eaf282015-09-22 11:36:03 -070044QAction *ConfigMainWindow::saveAction;
Karsten Wiese3b354c52006-12-13 00:34:08 -080045
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -070046static inline QString qgettext(const char* str)
47{
Roman Zippel43bf6122006-06-08 22:12:45 -070048 return QString::fromLocal8Bit(gettext(str));
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -070049}
50
51static inline QString qgettext(const QString& str)
52{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070053 return QString::fromLocal8Bit(gettext(str.toLatin1()));
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -070054}
55
Ben Hutchings00d4f8f2013-10-06 19:21:31 +010056ConfigSettings::ConfigSettings()
57 : QSettings("kernel.org", "qconf")
58{
59}
60
Linus Torvalds1da177e2005-04-16 15:20:36 -070061/**
62 * Reads a list of integer values from the application settings.
63 */
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070064QList<int> ConfigSettings::readSizes(const QString& key, bool *ok)
Linus Torvalds1da177e2005-04-16 15:20:36 -070065{
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070066 QList<int> result;
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070067 QStringList entryList = value(key).toStringList();
Li Zefanc1f96f02010-05-07 13:58:04 +080068 QStringList::Iterator it;
69
70 for (it = entryList.begin(); it != entryList.end(); ++it)
71 result.push_back((*it).toInt());
Linus Torvalds1da177e2005-04-16 15:20:36 -070072
73 return result;
74}
75
76/**
77 * Writes a list of integer values to the application settings.
78 */
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070079bool ConfigSettings::writeSizes(const QString& key, const QList<int>& value)
Linus Torvalds1da177e2005-04-16 15:20:36 -070080{
81 QStringList stringList;
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070082 QList<int>::ConstIterator it;
Linus Torvalds1da177e2005-04-16 15:20:36 -070083
84 for (it = value.begin(); it != value.end(); ++it)
85 stringList.push_back(QString::number(*it));
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070086 setValue(key, stringList);
Boris Barbulovski59e56442015-09-22 11:36:18 -070087
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070088 return true;
Linus Torvalds1da177e2005-04-16 15:20:36 -070089}
Linus Torvalds1da177e2005-04-16 15:20:36 -070090
Boris Barbulovski59e56442015-09-22 11:36:18 -070091
92/*
93 * set the new data
94 * TODO check the value
95 */
96void ConfigItem::okRename(int col)
97{
98}
99
100/*
101 * update the displayed of a menu entry
102 */
103void ConfigItem::updateMenu(void)
104{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700105 ConfigList* list;
106 struct symbol* sym;
107 struct property *prop;
108 QString prompt;
109 int type;
110 tristate expr;
111
112 list = listView();
113 if (goParent) {
114 setPixmap(promptColIdx, list->menuBackPix);
115 prompt = "..";
116 goto set_prompt;
117 }
118
119 sym = menu->sym;
120 prop = menu->prompt;
121 prompt = _(menu_get_prompt(menu));
122
123 if (prop) switch (prop->type) {
124 case P_MENU:
125 if (list->mode == singleMode || list->mode == symbolMode) {
126 /* a menuconfig entry is displayed differently
127 * depending whether it's at the view root or a child.
128 */
129 if (sym && list->rootEntry == menu)
130 break;
131 setPixmap(promptColIdx, list->menuPix);
132 } else {
133 if (sym)
134 break;
135 setPixmap(promptColIdx, QIcon());
136 }
137 goto set_prompt;
138 case P_COMMENT:
139 setPixmap(promptColIdx, QIcon());
140 goto set_prompt;
141 default:
142 ;
143 }
144 if (!sym)
145 goto set_prompt;
146
147 setText(nameColIdx, QString::fromLocal8Bit(sym->name));
148
149 type = sym_get_type(sym);
150 switch (type) {
151 case S_BOOLEAN:
152 case S_TRISTATE:
153 char ch;
154
155 if (!sym_is_changable(sym) && list->optMode == normalOpt) {
156 setPixmap(promptColIdx, QIcon());
157 setText(noColIdx, QString::null);
158 setText(modColIdx, QString::null);
159 setText(yesColIdx, QString::null);
160 break;
161 }
162 expr = sym_get_tristate_value(sym);
163 switch (expr) {
164 case yes:
165 if (sym_is_choice_value(sym) && type == S_BOOLEAN)
166 setPixmap(promptColIdx, list->choiceYesPix);
167 else
168 setPixmap(promptColIdx, list->symbolYesPix);
169 setText(yesColIdx, "Y");
170 ch = 'Y';
171 break;
172 case mod:
173 setPixmap(promptColIdx, list->symbolModPix);
174 setText(modColIdx, "M");
175 ch = 'M';
176 break;
177 default:
178 if (sym_is_choice_value(sym) && type == S_BOOLEAN)
179 setPixmap(promptColIdx, list->choiceNoPix);
180 else
181 setPixmap(promptColIdx, list->symbolNoPix);
182 setText(noColIdx, "N");
183 ch = 'N';
184 break;
185 }
186 if (expr != no)
187 setText(noColIdx, sym_tristate_within_range(sym, no) ? "_" : 0);
188 if (expr != mod)
189 setText(modColIdx, sym_tristate_within_range(sym, mod) ? "_" : 0);
190 if (expr != yes)
191 setText(yesColIdx, sym_tristate_within_range(sym, yes) ? "_" : 0);
192
193 setText(dataColIdx, QChar(ch));
194 break;
195 case S_INT:
196 case S_HEX:
197 case S_STRING:
198 const char* data;
199
200 data = sym_get_string_value(sym);
201
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700202 setText(dataColIdx, data);
203 if (type == S_STRING)
204 prompt = QString("%1: %2").arg(prompt).arg(data);
205 else
206 prompt = QString("(%2) %1").arg(prompt).arg(data);
207 break;
208 }
209 if (!sym_has_value(sym) && visible)
210 prompt += _(" (NEW)");
211set_prompt:
212 setText(promptColIdx, prompt);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700213}
214
215void ConfigItem::testUpdateMenu(bool v)
216{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700217 ConfigItem* i;
218
219 visible = v;
220 if (!menu)
221 return;
222
223 sym_calc_value(menu->sym);
224 if (menu->flags & MENU_CHANGED) {
225 /* the menu entry changed, so update all list items */
226 menu->flags &= ~MENU_CHANGED;
227 for (i = (ConfigItem*)menu->data; i; i = i->nextItem)
228 i->updateMenu();
229 } else if (listView()->updateAll)
230 updateMenu();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700231}
232
233
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700234/*
235 * construct a menu entry
236 */
237void ConfigItem::init(void)
238{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700239 if (menu) {
240 ConfigList* list = listView();
241 nextItem = (ConfigItem*)menu->data;
242 menu->data = this;
243
244 if (list->mode != fullMode)
245 setExpanded(true);
246 sym_calc_value(menu->sym);
247 }
248 updateMenu();
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700249}
250
251/*
252 * destruct a menu entry
253 */
254ConfigItem::~ConfigItem(void)
255{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700256 if (menu) {
257 ConfigItem** ip = (ConfigItem**)&menu->data;
258 for (; *ip; ip = &(*ip)->nextItem) {
259 if (*ip == this) {
260 *ip = nextItem;
261 break;
262 }
263 }
264 }
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700265}
266
Roman Zippel43bf6122006-06-08 22:12:45 -0700267ConfigLineEdit::ConfigLineEdit(ConfigView* parent)
268 : Parent(parent)
269{
Boris Barbulovskic14fa5e2015-09-22 11:36:21 -0700270 connect(this, SIGNAL(editingFinished()), SLOT(hide()));
Roman Zippel43bf6122006-06-08 22:12:45 -0700271}
272
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700273void ConfigLineEdit::show(ConfigItem* i)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700274{
275 item = i;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700276 if (sym_get_string_value(item->menu->sym))
277 setText(QString::fromLocal8Bit(sym_get_string_value(item->menu->sym)));
278 else
279 setText(QString::null);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700280 Parent::show();
281 setFocus();
282}
283
284void ConfigLineEdit::keyPressEvent(QKeyEvent* e)
285{
286 switch (e->key()) {
Markus Heidelbergfbb86372009-05-18 01:36:51 +0200287 case Qt::Key_Escape:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700288 break;
Markus Heidelbergfbb86372009-05-18 01:36:51 +0200289 case Qt::Key_Return:
290 case Qt::Key_Enter:
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700291 sym_set_string_value(item->menu->sym, text().toLatin1());
Linus Torvalds1da177e2005-04-16 15:20:36 -0700292 parent()->updateList(item);
293 break;
294 default:
295 Parent::keyPressEvent(e);
296 return;
297 }
298 e->accept();
299 parent()->list->setFocus();
300 hide();
301}
302
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700303ConfigList::ConfigList(ConfigView* p, const char *name)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700304 : Parent(p),
305 updateAll(false),
306 symbolYesPix(xpm_symbol_yes), symbolModPix(xpm_symbol_mod), symbolNoPix(xpm_symbol_no),
307 choiceYesPix(xpm_choice_yes), choiceNoPix(xpm_choice_no),
308 menuPix(xpm_menu), menuInvPix(xpm_menu_inv), menuBackPix(xpm_menuback), voidPix(xpm_void),
Boris Barbulovskidbf62932015-09-22 11:36:26 -0700309 showName(false), showRange(false), showData(false), mode(singleMode), optMode(normalOpt),
Boris Barbulovski59e56442015-09-22 11:36:18 -0700310 rootEntry(0), headerPopup(0)
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700311{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700312 int i;
313
314 setObjectName(name);
Boris Barbulovskia5225e92015-09-22 11:36:29 -0700315 setSortingEnabled(false);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700316 setRootIsDecorated(true);
317
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700318 setVerticalScrollMode(ScrollPerPixel);
319 setHorizontalScrollMode(ScrollPerPixel);
320
Boris Barbulovskia52cb322015-09-22 11:36:24 -0700321 setHeaderLabels(QStringList() << _("Option") << _("Name") << "N" << "M" << "Y" << _("Value"));
322
Boris Barbulovskic14fa5e2015-09-22 11:36:21 -0700323 connect(this, SIGNAL(itemSelectionChanged(void)),
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700324 SLOT(updateSelection(void)));
325
326 if (name) {
327 configSettings->beginGroup(name);
328 showName = configSettings->value("/showName", false).toBool();
329 showRange = configSettings->value("/showRange", false).toBool();
330 showData = configSettings->value("/showData", false).toBool();
331 optMode = (enum optionMode)configSettings->value("/optionMode", 0).toInt();
332 configSettings->endGroup();
333 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
334 }
335
336 addColumn(promptColIdx);
337
338 reinit();
339}
340
341bool ConfigList::menuSkip(struct menu *menu)
342{
343 if (optMode == normalOpt && menu_is_visible(menu))
344 return false;
345 if (optMode == promptOpt && menu_has_prompt(menu))
346 return false;
347 if (optMode == allOpt)
348 return false;
349 return true;
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700350}
Boris Barbulovski59e56442015-09-22 11:36:18 -0700351
352void ConfigList::reinit(void)
353{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700354 removeColumn(dataColIdx);
355 removeColumn(yesColIdx);
356 removeColumn(modColIdx);
357 removeColumn(noColIdx);
358 removeColumn(nameColIdx);
359
360 if (showName)
361 addColumn(nameColIdx);
362 if (showRange) {
363 addColumn(noColIdx);
364 addColumn(modColIdx);
365 addColumn(yesColIdx);
366 }
367 if (showData)
368 addColumn(dataColIdx);
369
370 updateListAll();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700371}
372
373void ConfigList::saveSettings(void)
374{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700375 if (!objectName().isEmpty()) {
376 configSettings->beginGroup(objectName());
377 configSettings->setValue("/showName", showName);
378 configSettings->setValue("/showRange", showRange);
379 configSettings->setValue("/showData", showData);
380 configSettings->setValue("/optionMode", (int)optMode);
381 configSettings->endGroup();
382 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700383}
384
385ConfigItem* ConfigList::findConfigItem(struct menu *menu)
386{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700387 ConfigItem* item = (ConfigItem*)menu->data;
388
389 for (; item; item = item->nextItem) {
390 if (this == item->listView())
391 break;
392 }
393
394 return item;
Boris Barbulovski59e56442015-09-22 11:36:18 -0700395}
396
397void ConfigList::updateSelection(void)
398{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700399 struct menu *menu;
400 enum prop_type type;
401
402 ConfigItem* item = (ConfigItem*)selectedItems().first();
403 if (!item)
404 return;
405
406 menu = item->menu;
407 emit menuChanged(menu);
408 if (!menu)
409 return;
410 type = menu->prompt ? menu->prompt->type : P_UNKNOWN;
411 if (mode == menuMode && type == P_MENU)
412 emit menuSelected(menu);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700413}
414
415void ConfigList::updateList(ConfigItem* item)
416{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700417 ConfigItem* last = 0;
418
419 if (!rootEntry) {
420 if (mode != listMode)
421 goto update;
422 QTreeWidgetItemIterator it(this);
423 ConfigItem* item;
424
425 while (*it) {
426 item = (ConfigItem*)(*it);
427 if (!item->menu)
428 continue;
429 item->testUpdateMenu(menu_is_visible(item->menu));
430
431 ++it;
432 }
433 return;
434 }
435
436 if (rootEntry != &rootmenu && (mode == singleMode ||
437 (mode == symbolMode && rootEntry->parent != &rootmenu))) {
438 item = firstChild();
439 if (!item)
440 item = new ConfigItem(this, 0, true);
441 last = item;
442 }
443 if ((mode == singleMode || (mode == symbolMode && !(rootEntry->flags & MENU_ROOT))) &&
444 rootEntry->sym && rootEntry->prompt) {
445 item = last ? last->nextSibling() : firstChild();
446 if (!item)
447 item = new ConfigItem(this, last, rootEntry, true);
448 else
449 item->testUpdateMenu(true);
450
451 updateMenuList(item, rootEntry);
452 update();
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700453 resizeColumnToContents(0);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700454 return;
455 }
456update:
457 updateMenuList(this, rootEntry);
458 update();
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700459 resizeColumnToContents(0);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700460}
461
462void ConfigList::setValue(ConfigItem* item, tristate val)
463{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700464 struct symbol* sym;
465 int type;
466 tristate oldval;
467
468 sym = item->menu ? item->menu->sym : 0;
469 if (!sym)
470 return;
471
472 type = sym_get_type(sym);
473 switch (type) {
474 case S_BOOLEAN:
475 case S_TRISTATE:
476 oldval = sym_get_tristate_value(sym);
477
478 if (!sym_set_tristate_value(sym, val))
479 return;
480 if (oldval == no && item->menu->list)
481 item->setExpanded(true);
482 parent()->updateList(item);
483 break;
484 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700485}
486
487void ConfigList::changeValue(ConfigItem* item)
488{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700489 struct symbol* sym;
490 struct menu* menu;
491 int type, oldexpr, newexpr;
492
493 menu = item->menu;
494 if (!menu)
495 return;
496 sym = menu->sym;
497 if (!sym) {
498 if (item->menu->list)
499 item->setExpanded(!item->isExpanded());
500 return;
501 }
502
503 type = sym_get_type(sym);
504 switch (type) {
505 case S_BOOLEAN:
506 case S_TRISTATE:
507 oldexpr = sym_get_tristate_value(sym);
508 newexpr = sym_toggle_tristate_value(sym);
509 if (item->menu->list) {
510 if (oldexpr == newexpr)
511 item->setExpanded(!item->isExpanded());
512 else if (oldexpr == no)
513 item->setExpanded(true);
514 }
515 if (oldexpr != newexpr)
516 parent()->updateList(item);
517 break;
518 case S_INT:
519 case S_HEX:
520 case S_STRING:
521 break;
522 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700523}
524
525void ConfigList::setRootMenu(struct menu *menu)
526{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700527 enum prop_type type;
528
529 if (rootEntry == menu)
530 return;
531 type = menu && menu->prompt ? menu->prompt->type : P_UNKNOWN;
532 if (type != P_MENU)
533 return;
534 updateMenuList(this, 0);
535 rootEntry = menu;
536 updateListAll();
537 if (currentItem()) {
538 currentItem()->setSelected(hasFocus());
539 scrollToItem(currentItem());
540 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700541}
542
543void ConfigList::setParentMenu(void)
544{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700545 ConfigItem* item;
546 struct menu *oldroot;
547
548 oldroot = rootEntry;
549 if (rootEntry == &rootmenu)
550 return;
551 setRootMenu(menu_get_parent_menu(rootEntry->parent));
552
553 QTreeWidgetItemIterator it(this);
554 while (*it) {
555 item = (ConfigItem *)(*it);
556 if (item->menu == oldroot) {
557 setCurrentItem(item);
558 scrollToItem(item);
559 break;
560 }
561
562 ++it;
563 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700564}
565
566/*
567 * update all the children of a menu entry
568 * removes/adds the entries from the parent widget as necessary
569 *
570 * parent: either the menu list widget or a menu entry widget
571 * menu: entry to be updated
572 */
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700573void ConfigList::updateMenuList(ConfigItem *parent, struct menu* menu)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700574{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700575 struct menu* child;
576 ConfigItem* item;
577 ConfigItem* last;
578 bool visible;
579 enum prop_type type;
580
581 if (!menu) {
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700582 while (parent->childCount() > 0)
583 {
584 delete parent->takeChild(0);
585 }
586
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700587 return;
588 }
589
590 last = parent->firstChild();
591 if (last && !last->goParent)
592 last = 0;
593 for (child = menu->list; child; child = child->next) {
594 item = last ? last->nextSibling() : parent->firstChild();
595 type = child->prompt ? child->prompt->type : P_UNKNOWN;
596
597 switch (mode) {
598 case menuMode:
599 if (!(child->flags & MENU_ROOT))
600 goto hide;
601 break;
602 case symbolMode:
603 if (child->flags & MENU_ROOT)
604 goto hide;
605 break;
606 default:
607 break;
608 }
609
610 visible = menu_is_visible(child);
611 if (!menuSkip(child)) {
612 if (!child->sym && !child->list && !child->prompt)
613 continue;
614 if (!item || item->menu != child)
615 item = new ConfigItem(parent, last, child, visible);
616 else
617 item->testUpdateMenu(visible);
618
619 if (mode == fullMode || mode == menuMode || type != P_MENU)
620 updateMenuList(item, child);
621 else
622 updateMenuList(item, 0);
623 last = item;
624 continue;
625 }
626 hide:
627 if (item && item->menu == child) {
628 last = parent->firstChild();
629 if (last == item)
630 last = 0;
631 else while (last->nextSibling() != item)
632 last = last->nextSibling();
633 delete item;
634 }
635 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700636}
637
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700638void ConfigList::updateMenuList(ConfigList *parent, struct menu* menu)
639{
640 struct menu* child;
641 ConfigItem* item;
642 ConfigItem* last;
643 bool visible;
644 enum prop_type type;
645
646 if (!menu) {
647 while (parent->topLevelItemCount() > 0)
648 {
649 delete parent->takeTopLevelItem(0);
650 }
651
652 return;
653 }
654
655 last = (ConfigItem*)parent->topLevelItem(0);
656 if (last && !last->goParent)
657 last = 0;
658 for (child = menu->list; child; child = child->next) {
659 item = last ? last->nextSibling() : (ConfigItem*)parent->topLevelItem(0);
660 type = child->prompt ? child->prompt->type : P_UNKNOWN;
661
662 switch (mode) {
663 case menuMode:
664 if (!(child->flags & MENU_ROOT))
665 goto hide;
666 break;
667 case symbolMode:
668 if (child->flags & MENU_ROOT)
669 goto hide;
670 break;
671 default:
672 break;
673 }
674
675 visible = menu_is_visible(child);
676 if (!menuSkip(child)) {
677 if (!child->sym && !child->list && !child->prompt)
678 continue;
679 if (!item || item->menu != child)
680 item = new ConfigItem(parent, last, child, visible);
681 else
682 item->testUpdateMenu(visible);
683
684 if (mode == fullMode || mode == menuMode || type != P_MENU)
685 updateMenuList(item, child);
686 else
687 updateMenuList(item, 0);
688 last = item;
689 continue;
690 }
691 hide:
692 if (item && item->menu == child) {
693 last = (ConfigItem*)parent->topLevelItem(0);
694 if (last == item)
695 last = 0;
696 else while (last->nextSibling() != item)
697 last = last->nextSibling();
698 delete item;
699 }
700 }
701}
702
Boris Barbulovski59e56442015-09-22 11:36:18 -0700703void ConfigList::keyPressEvent(QKeyEvent* ev)
704{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700705 QTreeWidgetItem* i = currentItem();
706 ConfigItem* item;
707 struct menu *menu;
708 enum prop_type type;
709
710 if (ev->key() == Qt::Key_Escape && mode != fullMode && mode != listMode) {
711 emit parentSelected();
712 ev->accept();
713 return;
714 }
715
716 if (!i) {
717 Parent::keyPressEvent(ev);
718 return;
719 }
720 item = (ConfigItem*)i;
721
722 switch (ev->key()) {
723 case Qt::Key_Return:
724 case Qt::Key_Enter:
725 if (item->goParent) {
726 emit parentSelected();
727 break;
728 }
729 menu = item->menu;
730 if (!menu)
731 break;
732 type = menu->prompt ? menu->prompt->type : P_UNKNOWN;
733 if (type == P_MENU && rootEntry != menu &&
734 mode != fullMode && mode != menuMode) {
735 emit menuSelected(menu);
736 break;
737 }
738 case Qt::Key_Space:
739 changeValue(item);
740 break;
741 case Qt::Key_N:
742 setValue(item, no);
743 break;
744 case Qt::Key_M:
745 setValue(item, mod);
746 break;
747 case Qt::Key_Y:
748 setValue(item, yes);
749 break;
750 default:
751 Parent::keyPressEvent(ev);
752 return;
753 }
754 ev->accept();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700755}
756
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700757void ConfigList::mousePressEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700758{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700759 //QPoint p(contentsToViewport(e->pos()));
760 //printf("contentsMousePressEvent: %d,%d\n", p.x(), p.y());
761 Parent::mousePressEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700762}
763
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700764void ConfigList::mouseReleaseEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700765{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700766 QPoint p = e->pos();
767 ConfigItem* item = (ConfigItem*)itemAt(p);
768 struct menu *menu;
769 enum prop_type ptype;
770 QIcon icon;
771 int idx, x;
772
773 if (!item)
774 goto skip;
775
776 menu = item->menu;
777 x = header()->offset() + p.x();
778 idx = header()->sectionPosition(x);
779 switch (idx) {
780 case promptColIdx:
781 icon = item->pixmap(promptColIdx);
782 break;
783 case noColIdx:
784 setValue(item, no);
785 break;
786 case modColIdx:
787 setValue(item, mod);
788 break;
789 case yesColIdx:
790 setValue(item, yes);
791 break;
792 case dataColIdx:
793 changeValue(item);
794 break;
795 }
796
797skip:
798 //printf("contentsMouseReleaseEvent: %d,%d\n", p.x(), p.y());
799 Parent::mouseReleaseEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700800}
801
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700802void ConfigList::mouseMoveEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700803{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700804 //QPoint p(contentsToViewport(e->pos()));
805 //printf("contentsMouseMoveEvent: %d,%d\n", p.x(), p.y());
806 Parent::mouseMoveEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700807}
808
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700809void ConfigList::mouseDoubleClickEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700810{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700811 QPoint p = e->pos(); // TODO: Check if this works(was contentsToViewport).
812 ConfigItem* item = (ConfigItem*)itemAt(p);
813 struct menu *menu;
814 enum prop_type ptype;
815
816 if (!item)
817 goto skip;
818 if (item->goParent) {
819 emit parentSelected();
820 goto skip;
821 }
822 menu = item->menu;
823 if (!menu)
824 goto skip;
825 ptype = menu->prompt ? menu->prompt->type : P_UNKNOWN;
826 if (ptype == P_MENU && (mode == singleMode || mode == symbolMode))
827 emit menuSelected(menu);
828 else if (menu->sym)
829 changeValue(item);
830
831skip:
832 //printf("contentsMouseDoubleClickEvent: %d,%d\n", p.x(), p.y());
833 Parent::mouseDoubleClickEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700834}
835
836void ConfigList::focusInEvent(QFocusEvent *e)
837{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700838 struct menu *menu = NULL;
839
840 Parent::focusInEvent(e);
841
842 ConfigItem* item = (ConfigItem *)currentItem();
843 if (item) {
844 item->setSelected(true);
845 menu = item->menu;
846 }
847 emit gotFocus(menu);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700848}
849
850void ConfigList::contextMenuEvent(QContextMenuEvent *e)
851{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700852 if (e->y() <= header()->geometry().bottom()) {
853 if (!headerPopup) {
854 QAction *action;
855
856 headerPopup = new QMenu(this);
857 action = new QAction(_("Show Name"), this);
858 action->setCheckable(true);
859 connect(action, SIGNAL(toggled(bool)),
860 parent(), SLOT(setShowName(bool)));
861 connect(parent(), SIGNAL(showNameChanged(bool)),
862 action, SLOT(setOn(bool)));
863 action->setChecked(showName);
864 headerPopup->addAction(action);
865 action = new QAction(_("Show Range"), this);
866 action->setCheckable(true);
867 connect(action, SIGNAL(toggled(bool)),
868 parent(), SLOT(setShowRange(bool)));
869 connect(parent(), SIGNAL(showRangeChanged(bool)),
870 action, SLOT(setOn(bool)));
871 action->setChecked(showRange);
872 headerPopup->addAction(action);
873 action = new QAction(_("Show Data"), this);
874 action->setCheckable(true);
875 connect(action, SIGNAL(toggled(bool)),
876 parent(), SLOT(setShowData(bool)));
877 connect(parent(), SIGNAL(showDataChanged(bool)),
878 action, SLOT(setOn(bool)));
879 action->setChecked(showData);
880 headerPopup->addAction(action);
881 }
882 headerPopup->exec(e->globalPos());
883 e->accept();
884 } else
885 e->ignore();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700886}
887
Li Zefan39a48972010-05-10 16:33:41 +0800888ConfigView*ConfigView::viewList;
889QAction *ConfigView::showNormalAction;
890QAction *ConfigView::showAllAction;
891QAction *ConfigView::showPromptAction;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700892
Roman Zippel7fc925f2006-06-08 22:12:46 -0700893ConfigView::ConfigView(QWidget* parent, const char *name)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -0700894 : Parent(parent)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700895{
Boris Barbulovski9bd36ed2015-09-22 11:36:22 -0700896 setObjectName(name);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700897 QVBoxLayout *verticalLayout = new QVBoxLayout(this);
Boris Barbulovski92298b42015-09-22 11:36:11 -0700898 verticalLayout->setContentsMargins(0, 0, 0, 0);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700899
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700900 list = new ConfigList(this);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700901 verticalLayout->addWidget(list);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700902 lineEdit = new ConfigLineEdit(this);
903 lineEdit->hide();
Boris Barbulovski29a70162015-09-22 11:36:10 -0700904 verticalLayout->addWidget(lineEdit);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700905
906 this->nextView = viewList;
907 viewList = this;
908}
909
910ConfigView::~ConfigView(void)
911{
912 ConfigView** vp;
913
914 for (vp = &viewList; *vp; vp = &(*vp)->nextView) {
915 if (*vp == this) {
916 *vp = nextView;
917 break;
918 }
919 }
920}
921
Li Zefan39a48972010-05-10 16:33:41 +0800922void ConfigView::setOptionMode(QAction *act)
Roman Zippel7fc925f2006-06-08 22:12:46 -0700923{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700924 if (act == showNormalAction)
925 list->optMode = normalOpt;
926 else if (act == showAllAction)
927 list->optMode = allOpt;
928 else
929 list->optMode = promptOpt;
930
931 list->updateListAll();
Roman Zippel7fc925f2006-06-08 22:12:46 -0700932}
933
934void ConfigView::setShowName(bool b)
935{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700936 if (list->showName != b) {
937 list->showName = b;
938 list->reinit();
939 emit showNameChanged(b);
940 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700941}
942
943void ConfigView::setShowRange(bool b)
944{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700945 if (list->showRange != b) {
946 list->showRange = b;
947 list->reinit();
948 emit showRangeChanged(b);
949 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700950}
951
952void ConfigView::setShowData(bool b)
953{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700954 if (list->showData != b) {
955 list->showData = b;
956 list->reinit();
957 emit showDataChanged(b);
958 }
959}
960
961void ConfigList::setAllOpen(bool open)
962{
963 QTreeWidgetItemIterator it(this);
964
965 while (*it) {
966 (*it)->setExpanded(open);
967
968 ++it;
969 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700970}
971
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700972void ConfigView::updateList(ConfigItem* item)
Roman Zippel7fc925f2006-06-08 22:12:46 -0700973{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700974 ConfigView* v;
975
976 for (v = viewList; v; v = v->nextView)
977 v->list->updateList(item);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700978}
979
980void ConfigView::updateListAll(void)
981{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700982 ConfigView* v;
983
984 for (v = viewList; v; v = v->nextView)
985 v->list->updateListAll();
Linus Torvalds1da177e2005-04-16 15:20:36 -0700986}
987
Roman Zippel43bf6122006-06-08 22:12:45 -0700988ConfigInfoView::ConfigInfoView(QWidget* parent, const char *name)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -0700989 : Parent(parent), sym(0), _menu(0)
Roman Zippel43bf6122006-06-08 22:12:45 -0700990{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700991 setObjectName(name);
992
993
994 if (!objectName().isEmpty()) {
995 configSettings->beginGroup(objectName());
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -0700996 _showDebug = configSettings->value("/showDebug", false).toBool();
Roman Zippel7fc925f2006-06-08 22:12:46 -0700997 configSettings->endGroup();
998 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
999 }
1000}
1001
1002void ConfigInfoView::saveSettings(void)
1003{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001004 if (!objectName().isEmpty()) {
1005 configSettings->beginGroup(objectName());
1006 configSettings->setValue("/showDebug", showDebug());
1007 configSettings->endGroup();
1008 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001009}
1010
1011void ConfigInfoView::setShowDebug(bool b)
1012{
1013 if (_showDebug != b) {
1014 _showDebug = b;
Alexander Stein133c5f72010-08-31 17:34:37 +02001015 if (_menu)
Roman Zippel43bf6122006-06-08 22:12:45 -07001016 menuInfo();
Roman Zippelab45d192006-06-08 22:12:47 -07001017 else if (sym)
1018 symbolInfo();
Roman Zippel43bf6122006-06-08 22:12:45 -07001019 emit showDebugChanged(b);
1020 }
1021}
1022
1023void ConfigInfoView::setInfo(struct menu *m)
1024{
Alexander Stein133c5f72010-08-31 17:34:37 +02001025 if (_menu == m)
Roman Zippelb65a47e2006-06-08 22:12:47 -07001026 return;
Alexander Stein133c5f72010-08-31 17:34:37 +02001027 _menu = m;
Roman Zippel6fa1da82007-01-10 23:15:31 -08001028 sym = NULL;
Alexander Stein133c5f72010-08-31 17:34:37 +02001029 if (!_menu)
Roman Zippel43bf6122006-06-08 22:12:45 -07001030 clear();
Roman Zippel6fa1da82007-01-10 23:15:31 -08001031 else
Roman Zippel43bf6122006-06-08 22:12:45 -07001032 menuInfo();
1033}
1034
Roman Zippelab45d192006-06-08 22:12:47 -07001035void ConfigInfoView::symbolInfo(void)
1036{
1037 QString str;
1038
1039 str += "<big>Symbol: <b>";
1040 str += print_filter(sym->name);
1041 str += "</b></big><br><br>value: ";
1042 str += print_filter(sym_get_string_value(sym));
1043 str += "<br>visibility: ";
1044 str += sym->visible == yes ? "y" : sym->visible == mod ? "m" : "n";
1045 str += "<br>";
1046 str += debug_info(sym);
1047
1048 setText(str);
1049}
1050
Roman Zippel43bf6122006-06-08 22:12:45 -07001051void ConfigInfoView::menuInfo(void)
1052{
1053 struct symbol* sym;
1054 QString head, debug, help;
1055
Alexander Stein133c5f72010-08-31 17:34:37 +02001056 sym = _menu->sym;
Roman Zippel43bf6122006-06-08 22:12:45 -07001057 if (sym) {
Alexander Stein133c5f72010-08-31 17:34:37 +02001058 if (_menu->prompt) {
Roman Zippel43bf6122006-06-08 22:12:45 -07001059 head += "<big><b>";
Alexander Stein133c5f72010-08-31 17:34:37 +02001060 head += print_filter(_(_menu->prompt->text));
Roman Zippel43bf6122006-06-08 22:12:45 -07001061 head += "</b></big>";
1062 if (sym->name) {
1063 head += " (";
Roman Zippelab45d192006-06-08 22:12:47 -07001064 if (showDebug())
1065 head += QString().sprintf("<a href=\"s%p\">", sym);
Roman Zippel43bf6122006-06-08 22:12:45 -07001066 head += print_filter(sym->name);
Roman Zippelab45d192006-06-08 22:12:47 -07001067 if (showDebug())
1068 head += "</a>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001069 head += ")";
1070 }
1071 } else if (sym->name) {
1072 head += "<big><b>";
Roman Zippelab45d192006-06-08 22:12:47 -07001073 if (showDebug())
1074 head += QString().sprintf("<a href=\"s%p\">", sym);
Roman Zippel43bf6122006-06-08 22:12:45 -07001075 head += print_filter(sym->name);
Roman Zippelab45d192006-06-08 22:12:47 -07001076 if (showDebug())
1077 head += "</a>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001078 head += "</b></big>";
1079 }
1080 head += "<br><br>";
1081
1082 if (showDebug())
1083 debug = debug_info(sym);
1084
Cheng Renquand74c15f2009-07-12 16:11:47 +08001085 struct gstr help_gstr = str_new();
Alexander Stein133c5f72010-08-31 17:34:37 +02001086 menu_get_ext_help(_menu, &help_gstr);
Cheng Renquand74c15f2009-07-12 16:11:47 +08001087 help = print_filter(str_get(&help_gstr));
1088 str_free(&help_gstr);
Alexander Stein133c5f72010-08-31 17:34:37 +02001089 } else if (_menu->prompt) {
Roman Zippel43bf6122006-06-08 22:12:45 -07001090 head += "<big><b>";
Alexander Stein133c5f72010-08-31 17:34:37 +02001091 head += print_filter(_(_menu->prompt->text));
Roman Zippel43bf6122006-06-08 22:12:45 -07001092 head += "</b></big><br><br>";
1093 if (showDebug()) {
Alexander Stein133c5f72010-08-31 17:34:37 +02001094 if (_menu->prompt->visible.expr) {
Roman Zippel43bf6122006-06-08 22:12:45 -07001095 debug += "&nbsp;&nbsp;dep: ";
Alexander Stein133c5f72010-08-31 17:34:37 +02001096 expr_print(_menu->prompt->visible.expr, expr_print_help, &debug, E_NONE);
Roman Zippel43bf6122006-06-08 22:12:45 -07001097 debug += "<br><br>";
1098 }
1099 }
1100 }
1101 if (showDebug())
Alexander Stein133c5f72010-08-31 17:34:37 +02001102 debug += QString().sprintf("defined at %s:%d<br><br>", _menu->file->name, _menu->lineno);
Roman Zippel43bf6122006-06-08 22:12:45 -07001103
1104 setText(head + debug + help);
1105}
1106
1107QString ConfigInfoView::debug_info(struct symbol *sym)
1108{
1109 QString debug;
1110
1111 debug += "type: ";
1112 debug += print_filter(sym_type_name(sym->type));
1113 if (sym_is_choice(sym))
1114 debug += " (choice)";
1115 debug += "<br>";
1116 if (sym->rev_dep.expr) {
1117 debug += "reverse dep: ";
1118 expr_print(sym->rev_dep.expr, expr_print_help, &debug, E_NONE);
1119 debug += "<br>";
1120 }
1121 for (struct property *prop = sym->prop; prop; prop = prop->next) {
1122 switch (prop->type) {
1123 case P_PROMPT:
1124 case P_MENU:
Roman Zippelab45d192006-06-08 22:12:47 -07001125 debug += QString().sprintf("prompt: <a href=\"m%p\">", prop->menu);
Roman Zippel43bf6122006-06-08 22:12:45 -07001126 debug += print_filter(_(prop->text));
Roman Zippelab45d192006-06-08 22:12:47 -07001127 debug += "</a><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001128 break;
1129 case P_DEFAULT:
Roman Zippel93449082008-01-14 04:50:54 +01001130 case P_SELECT:
1131 case P_RANGE:
1132 case P_ENV:
1133 debug += prop_get_type_name(prop->type);
1134 debug += ": ";
Roman Zippel43bf6122006-06-08 22:12:45 -07001135 expr_print(prop->expr, expr_print_help, &debug, E_NONE);
1136 debug += "<br>";
1137 break;
1138 case P_CHOICE:
1139 if (sym_is_choice(sym)) {
1140 debug += "choice: ";
1141 expr_print(prop->expr, expr_print_help, &debug, E_NONE);
1142 debug += "<br>";
1143 }
1144 break;
Roman Zippel43bf6122006-06-08 22:12:45 -07001145 default:
1146 debug += "unknown property: ";
1147 debug += prop_get_type_name(prop->type);
1148 debug += "<br>";
1149 }
1150 if (prop->visible.expr) {
1151 debug += "&nbsp;&nbsp;&nbsp;&nbsp;dep: ";
1152 expr_print(prop->visible.expr, expr_print_help, &debug, E_NONE);
1153 debug += "<br>";
1154 }
1155 }
1156 debug += "<br>";
1157
1158 return debug;
1159}
1160
1161QString ConfigInfoView::print_filter(const QString &str)
1162{
1163 QRegExp re("[<>&\"\\n]");
1164 QString res = str;
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001165 for (int i = 0; (i = res.indexOf(re, i)) >= 0;) {
1166 switch (res[i].toLatin1()) {
Roman Zippel43bf6122006-06-08 22:12:45 -07001167 case '<':
1168 res.replace(i, 1, "&lt;");
1169 i += 4;
1170 break;
1171 case '>':
1172 res.replace(i, 1, "&gt;");
1173 i += 4;
1174 break;
1175 case '&':
1176 res.replace(i, 1, "&amp;");
1177 i += 5;
1178 break;
1179 case '"':
1180 res.replace(i, 1, "&quot;");
1181 i += 6;
1182 break;
1183 case '\n':
1184 res.replace(i, 1, "<br>");
1185 i += 4;
1186 break;
1187 }
1188 }
1189 return res;
1190}
1191
Roman Zippelab45d192006-06-08 22:12:47 -07001192void ConfigInfoView::expr_print_help(void *data, struct symbol *sym, const char *str)
Roman Zippel43bf6122006-06-08 22:12:45 -07001193{
Roman Zippelab45d192006-06-08 22:12:47 -07001194 QString* text = reinterpret_cast<QString*>(data);
1195 QString str2 = print_filter(str);
1196
1197 if (sym && sym->name && !(sym->flags & SYMBOL_CONST)) {
1198 *text += QString().sprintf("<a href=\"s%p\">", sym);
1199 *text += str2;
1200 *text += "</a>";
1201 } else
1202 *text += str2;
Roman Zippel43bf6122006-06-08 22:12:45 -07001203}
1204
Boris Barbulovski924bbb52015-09-22 11:36:06 -07001205QMenu* ConfigInfoView::createStandardContextMenu(const QPoint & pos)
Roman Zippel7fc925f2006-06-08 22:12:46 -07001206{
Boris Barbulovski924bbb52015-09-22 11:36:06 -07001207 QMenu* popup = Parent::createStandardContextMenu(pos);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001208 QAction* action = new QAction(_("Show Debug Info"), popup);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001209 action->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001210 connect(action, SIGNAL(toggled(bool)), SLOT(setShowDebug(bool)));
1211 connect(this, SIGNAL(showDebugChanged(bool)), action, SLOT(setOn(bool)));
Boris Barbulovski9c862352015-09-22 11:36:12 -07001212 action->setChecked(showDebug());
Boris Barbulovski924bbb52015-09-22 11:36:06 -07001213 popup->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001214 popup->addAction(action);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001215 return popup;
1216}
1217
Boris Barbulovski924bbb52015-09-22 11:36:06 -07001218void ConfigInfoView::contextMenuEvent(QContextMenuEvent *e)
Roman Zippel7fc925f2006-06-08 22:12:46 -07001219{
Boris Barbulovski924bbb52015-09-22 11:36:06 -07001220 Parent::contextMenuEvent(e);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001221}
1222
Marco Costalba63431e72006-10-05 19:12:59 +02001223ConfigSearchWindow::ConfigSearchWindow(ConfigMainWindow* parent, const char *name)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001224 : Parent(parent), result(NULL)
Roman Zippel43bf6122006-06-08 22:12:45 -07001225{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001226 setObjectName(name);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001227 setWindowTitle("Search Config");
Roman Zippel43bf6122006-06-08 22:12:45 -07001228
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001229 QVBoxLayout* layout1 = new QVBoxLayout(this);
1230 layout1->setContentsMargins(11, 11, 11, 11);
1231 layout1->setSpacing(6);
1232 QHBoxLayout* layout2 = new QHBoxLayout(0);
1233 layout2->setContentsMargins(0, 0, 0, 0);
1234 layout2->setSpacing(6);
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001235 layout2->addWidget(new QLabel(_("Find:"), this));
Roman Zippel43bf6122006-06-08 22:12:45 -07001236 editField = new QLineEdit(this);
1237 connect(editField, SIGNAL(returnPressed()), SLOT(search()));
1238 layout2->addWidget(editField);
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001239 searchButton = new QPushButton(_("Search"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001240 searchButton->setAutoDefault(false);
Roman Zippel43bf6122006-06-08 22:12:45 -07001241 connect(searchButton, SIGNAL(clicked()), SLOT(search()));
1242 layout2->addWidget(searchButton);
1243 layout1->addLayout(layout2);
1244
Roman Zippel7fc925f2006-06-08 22:12:46 -07001245 split = new QSplitter(this);
Markus Heidelberg7298b932009-05-18 01:36:50 +02001246 split->setOrientation(Qt::Vertical);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001247 list = new ConfigView(split, name);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001248 list->list->mode = listMode;
Roman Zippel7fc925f2006-06-08 22:12:46 -07001249 info = new ConfigInfoView(split, name);
Roman Zippel43bf6122006-06-08 22:12:45 -07001250 connect(list->list, SIGNAL(menuChanged(struct menu *)),
1251 info, SLOT(setInfo(struct menu *)));
Marco Costalba63431e72006-10-05 19:12:59 +02001252 connect(list->list, SIGNAL(menuChanged(struct menu *)),
1253 parent, SLOT(setMenuLink(struct menu *)));
1254
Roman Zippel43bf6122006-06-08 22:12:45 -07001255 layout1->addWidget(split);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001256
1257 if (name) {
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001258 QVariant x, y;
1259 int width, height;
Roman Zippel7fc925f2006-06-08 22:12:46 -07001260 bool ok;
1261
1262 configSettings->beginGroup(name);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001263 width = configSettings->value("/window width", parent->width() / 2).toInt();
1264 height = configSettings->value("/window height", parent->height() / 2).toInt();
Roman Zippel7fc925f2006-06-08 22:12:46 -07001265 resize(width, height);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001266 x = configSettings->value("/window x");
1267 y = configSettings->value("/window y");
1268 if ((x.isValid())&&(y.isValid()))
1269 move(x.toInt(), y.toInt());
Boris Barbulovski041fbdc2015-09-22 11:36:05 -07001270 QList<int> sizes = configSettings->readSizes("/split", &ok);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001271 if (ok)
1272 split->setSizes(sizes);
1273 configSettings->endGroup();
1274 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
1275 }
1276}
1277
1278void ConfigSearchWindow::saveSettings(void)
1279{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001280 if (!objectName().isEmpty()) {
1281 configSettings->beginGroup(objectName());
1282 configSettings->setValue("/window x", pos().x());
1283 configSettings->setValue("/window y", pos().y());
1284 configSettings->setValue("/window width", size().width());
1285 configSettings->setValue("/window height", size().height());
1286 configSettings->writeSizes("/split", split->sizes());
1287 configSettings->endGroup();
1288 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001289}
1290
1291void ConfigSearchWindow::search(void)
1292{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001293 struct symbol **p;
1294 struct property *prop;
1295 ConfigItem *lastItem = NULL;
1296
1297 free(result);
1298 list->list->clear();
1299 info->clear();
1300
1301 result = sym_re_search(editField->text().toLatin1());
1302 if (!result)
1303 return;
1304 for (p = result; *p; p++) {
1305 for_all_prompts((*p), prop)
1306 lastItem = new ConfigItem(list->list, lastItem, prop->menu,
1307 menu_is_visible(prop->menu));
1308 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001309}
1310
Linus Torvalds1da177e2005-04-16 15:20:36 -07001311/*
1312 * Construct the complete config widget
1313 */
1314ConfigMainWindow::ConfigMainWindow(void)
Roman Zippelf12aa702006-11-25 11:09:31 -08001315 : searchWindow(0)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001316{
1317 QMenuBar* menu;
Boris Barbulovski92119932015-09-22 11:36:16 -07001318 bool ok = true;
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001319 QVariant x, y;
1320 int width, height;
Randy Dunlapa54bb702007-10-20 11:18:47 -07001321 char title[256];
Linus Torvalds1da177e2005-04-16 15:20:36 -07001322
Markus Heidelberg8d90c972009-05-18 01:36:52 +02001323 QDesktopWidget *d = configApp->desktop();
Arnaud Lacombe09548282010-08-18 01:57:13 -04001324 snprintf(title, sizeof(title), "%s%s",
1325 rootmenu.prompt->text,
Michal Marek76a136c2010-09-01 17:39:27 +02001326 ""
Michal Marek76a136c2010-09-01 17:39:27 +02001327 );
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001328 setWindowTitle(title);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001329
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001330 width = configSettings->value("/window width", d->width() - 64).toInt();
1331 height = configSettings->value("/window height", d->height() - 64).toInt();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001332 resize(width, height);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001333 x = configSettings->value("/window x");
1334 y = configSettings->value("/window y");
1335 if ((x.isValid())&&(y.isValid()))
1336 move(x.toInt(), y.toInt());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001337
1338 split1 = new QSplitter(this);
Markus Heidelberg7298b932009-05-18 01:36:50 +02001339 split1->setOrientation(Qt::Horizontal);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001340 setCentralWidget(split1);
1341
Roman Zippel7fc925f2006-06-08 22:12:46 -07001342 menuView = new ConfigView(split1, "menu");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001343 menuList = menuView->list;
1344
1345 split2 = new QSplitter(split1);
Markus Heidelberg7298b932009-05-18 01:36:50 +02001346 split2->setOrientation(Qt::Vertical);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001347
1348 // create config tree
Roman Zippel7fc925f2006-06-08 22:12:46 -07001349 configView = new ConfigView(split2, "config");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001350 configList = configView->list;
1351
Roman Zippel7fc925f2006-06-08 22:12:46 -07001352 helpText = new ConfigInfoView(split2, "help");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001353
1354 setTabOrder(configList, helpText);
1355 configList->setFocus();
1356
1357 menu = menuBar();
Boris Barbulovskib1f8a452015-09-22 11:36:02 -07001358 toolBar = new QToolBar("Tools", this);
Boris Barbulovski29a70162015-09-22 11:36:10 -07001359 addToolBar(toolBar);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001360
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001361 backAction = new QAction(QPixmap(xpm_back), _("Back"), this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001362 connect(backAction, SIGNAL(triggered(bool)), SLOT(goBack()));
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001363 backAction->setEnabled(false);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001364 QAction *quitAction = new QAction(_("&Quit"), this);
1365 quitAction->setShortcut(Qt::CTRL + Qt::Key_Q);
Boris Barbulovski92119932015-09-22 11:36:16 -07001366 connect(quitAction, SIGNAL(triggered(bool)), SLOT(close()));
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001367 QAction *loadAction = new QAction(QPixmap(xpm_load), _("&Load"), this);
1368 loadAction->setShortcut(Qt::CTRL + Qt::Key_L);
Boris Barbulovski92119932015-09-22 11:36:16 -07001369 connect(loadAction, SIGNAL(triggered(bool)), SLOT(loadConfig()));
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001370 saveAction = new QAction(QPixmap(xpm_save), _("&Save"), this);
1371 saveAction->setShortcut(Qt::CTRL + Qt::Key_S);
Boris Barbulovski92119932015-09-22 11:36:16 -07001372 connect(saveAction, SIGNAL(triggered(bool)), SLOT(saveConfig()));
Karsten Wiese3b354c52006-12-13 00:34:08 -08001373 conf_set_changed_callback(conf_changed);
1374 // Set saveAction's initial state
1375 conf_changed();
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001376 QAction *saveAsAction = new QAction(_("Save &As..."), this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001377 connect(saveAsAction, SIGNAL(triggered(bool)), SLOT(saveConfigAs()));
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001378 QAction *searchAction = new QAction(_("&Find"), this);
1379 searchAction->setShortcut(Qt::CTRL + Qt::Key_F);
Boris Barbulovski92119932015-09-22 11:36:16 -07001380 connect(searchAction, SIGNAL(triggered(bool)), SLOT(searchConfig()));
Boris Barbulovski780505e2015-09-22 11:36:13 -07001381 singleViewAction = new QAction(QPixmap(xpm_single_view), _("Single View"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001382 singleViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001383 connect(singleViewAction, SIGNAL(triggered(bool)), SLOT(showSingleView()));
Boris Barbulovski780505e2015-09-22 11:36:13 -07001384 splitViewAction = new QAction(QPixmap(xpm_split_view), _("Split View"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001385 splitViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001386 connect(splitViewAction, SIGNAL(triggered(bool)), SLOT(showSplitView()));
Boris Barbulovski780505e2015-09-22 11:36:13 -07001387 fullViewAction = new QAction(QPixmap(xpm_tree_view), _("Full View"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001388 fullViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001389 connect(fullViewAction, SIGNAL(triggered(bool)), SLOT(showFullView()));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001390
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001391 QAction *showNameAction = new QAction(_("Show Name"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001392 showNameAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001393 connect(showNameAction, SIGNAL(toggled(bool)), configView, SLOT(setShowName(bool)));
Boris Barbulovski9c862352015-09-22 11:36:12 -07001394 showNameAction->setChecked(configView->showName());
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001395 QAction *showRangeAction = new QAction(_("Show Range"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001396 showRangeAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001397 connect(showRangeAction, SIGNAL(toggled(bool)), configView, SLOT(setShowRange(bool)));
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001398 QAction *showDataAction = new QAction(_("Show Data"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001399 showDataAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001400 connect(showDataAction, SIGNAL(toggled(bool)), configView, SLOT(setShowData(bool)));
Li Zefan39a48972010-05-10 16:33:41 +08001401
1402 QActionGroup *optGroup = new QActionGroup(this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001403 optGroup->setExclusive(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001404 connect(optGroup, SIGNAL(triggered(QAction*)), configView,
Li Zefan39a48972010-05-10 16:33:41 +08001405 SLOT(setOptionMode(QAction *)));
Boris Barbulovski92119932015-09-22 11:36:16 -07001406 connect(optGroup, SIGNAL(triggered(QAction *)), menuView,
Li Zefan39a48972010-05-10 16:33:41 +08001407 SLOT(setOptionMode(QAction *)));
1408
Alexander Stein133c5f72010-08-31 17:34:37 +02001409 configView->showNormalAction = new QAction(_("Show Normal Options"), optGroup);
1410 configView->showAllAction = new QAction(_("Show All Options"), optGroup);
1411 configView->showPromptAction = new QAction(_("Show Prompt Options"), optGroup);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001412 configView->showNormalAction->setCheckable(true);
1413 configView->showAllAction->setCheckable(true);
1414 configView->showPromptAction->setCheckable(true);
Li Zefan39a48972010-05-10 16:33:41 +08001415
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001416 QAction *showDebugAction = new QAction( _("Show Debug Info"), this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001417 showDebugAction->setCheckable(true);
Roman Zippel43bf6122006-06-08 22:12:45 -07001418 connect(showDebugAction, SIGNAL(toggled(bool)), helpText, SLOT(setShowDebug(bool)));
Boris Barbulovski9c862352015-09-22 11:36:12 -07001419 showDebugAction->setChecked(helpText->showDebug());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001420
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001421 QAction *showIntroAction = new QAction( _("Introduction"), this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001422 connect(showIntroAction, SIGNAL(triggered(bool)), SLOT(showIntro()));
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001423 QAction *showAboutAction = new QAction( _("About"), this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001424 connect(showAboutAction, SIGNAL(triggered(bool)), SLOT(showAbout()));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001425
1426 // init tool bar
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001427 toolBar->addAction(backAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001428 toolBar->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001429 toolBar->addAction(loadAction);
1430 toolBar->addAction(saveAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001431 toolBar->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001432 toolBar->addAction(singleViewAction);
1433 toolBar->addAction(splitViewAction);
1434 toolBar->addAction(fullViewAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001435
1436 // create config menu
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001437 QMenu* config = menu->addMenu(_("&File"));
1438 config->addAction(loadAction);
1439 config->addAction(saveAction);
1440 config->addAction(saveAsAction);
Boris Barbulovski76bede82015-09-22 11:36:07 -07001441 config->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001442 config->addAction(quitAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001443
Shlomi Fish66e7c722007-02-14 00:32:58 -08001444 // create edit menu
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001445 QMenu* editMenu = menu->addMenu(_("&Edit"));
1446 editMenu->addAction(searchAction);
Shlomi Fish66e7c722007-02-14 00:32:58 -08001447
Linus Torvalds1da177e2005-04-16 15:20:36 -07001448 // create options menu
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001449 QMenu* optionMenu = menu->addMenu(_("&Option"));
1450 optionMenu->addAction(showNameAction);
1451 optionMenu->addAction(showRangeAction);
1452 optionMenu->addAction(showDataAction);
Boris Barbulovski76bede82015-09-22 11:36:07 -07001453 optionMenu->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001454 optionMenu->addActions(optGroup->actions());
Boris Barbulovski76bede82015-09-22 11:36:07 -07001455 optionMenu->addSeparator();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001456
1457 // create help menu
Boris Barbulovski76bede82015-09-22 11:36:07 -07001458 menu->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001459 QMenu* helpMenu = menu->addMenu(_("&Help"));
1460 helpMenu->addAction(showIntroAction);
1461 helpMenu->addAction(showAboutAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001462
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001463 connect(configList, SIGNAL(menuChanged(struct menu *)),
1464 helpText, SLOT(setInfo(struct menu *)));
1465 connect(configList, SIGNAL(menuSelected(struct menu *)),
1466 SLOT(changeMenu(struct menu *)));
1467 connect(configList, SIGNAL(parentSelected()),
1468 SLOT(goBack()));
1469 connect(menuList, SIGNAL(menuChanged(struct menu *)),
1470 helpText, SLOT(setInfo(struct menu *)));
1471 connect(menuList, SIGNAL(menuSelected(struct menu *)),
1472 SLOT(changeMenu(struct menu *)));
1473
1474 connect(configList, SIGNAL(gotFocus(struct menu *)),
1475 helpText, SLOT(setInfo(struct menu *)));
1476 connect(menuList, SIGNAL(gotFocus(struct menu *)),
1477 helpText, SLOT(setInfo(struct menu *)));
1478 connect(menuList, SIGNAL(gotFocus(struct menu *)),
1479 SLOT(listFocusChanged(void)));
Roman Zippelb65a47e2006-06-08 22:12:47 -07001480 connect(helpText, SIGNAL(menuSelected(struct menu *)),
1481 SLOT(setMenuLink(struct menu *)));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001482
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001483 QString listMode = configSettings->value("/listMode", "symbol").toString();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001484 if (listMode == "single")
1485 showSingleView();
1486 else if (listMode == "full")
1487 showFullView();
1488 else /*if (listMode == "split")*/
1489 showSplitView();
1490
1491 // UI setup done, restore splitter positions
Boris Barbulovski041fbdc2015-09-22 11:36:05 -07001492 QList<int> sizes = configSettings->readSizes("/split1", &ok);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001493 if (ok)
1494 split1->setSizes(sizes);
1495
Roman Zippel7fc925f2006-06-08 22:12:46 -07001496 sizes = configSettings->readSizes("/split2", &ok);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001497 if (ok)
1498 split2->setSizes(sizes);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001499}
1500
Linus Torvalds1da177e2005-04-16 15:20:36 -07001501void ConfigMainWindow::loadConfig(void)
1502{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001503 QString s = QFileDialog::getOpenFileName(this, "", conf_get_configname());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001504 if (s.isNull())
1505 return;
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -07001506 if (conf_read(QFile::encodeName(s)))
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001507 QMessageBox::information(this, "qconf", _("Unable to load configuration!"));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001508 ConfigView::updateListAll();
1509}
1510
Michal Marekbac6aa82011-05-25 15:10:25 +02001511bool ConfigMainWindow::saveConfig(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001512{
Michal Marekbac6aa82011-05-25 15:10:25 +02001513 if (conf_write(NULL)) {
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001514 QMessageBox::information(this, "qconf", _("Unable to save configuration!"));
Michal Marekbac6aa82011-05-25 15:10:25 +02001515 return false;
1516 }
1517 return true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001518}
1519
1520void ConfigMainWindow::saveConfigAs(void)
1521{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001522 QString s = QFileDialog::getSaveFileName(this, "", conf_get_configname());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001523 if (s.isNull())
1524 return;
Arnaud Lacombed49e4682011-05-24 14:16:18 -04001525 saveConfig();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001526}
1527
Roman Zippel43bf6122006-06-08 22:12:45 -07001528void ConfigMainWindow::searchConfig(void)
1529{
1530 if (!searchWindow)
Roman Zippel7fc925f2006-06-08 22:12:46 -07001531 searchWindow = new ConfigSearchWindow(this, "search");
Roman Zippel43bf6122006-06-08 22:12:45 -07001532 searchWindow->show();
1533}
1534
Linus Torvalds1da177e2005-04-16 15:20:36 -07001535void ConfigMainWindow::changeMenu(struct menu *menu)
1536{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001537 configList->setRootMenu(menu);
1538 if (configList->rootEntry->parent == &rootmenu)
1539 backAction->setEnabled(false);
1540 else
1541 backAction->setEnabled(true);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001542}
1543
Roman Zippelb65a47e2006-06-08 22:12:47 -07001544void ConfigMainWindow::setMenuLink(struct menu *menu)
1545{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001546 struct menu *parent;
1547 ConfigList* list = NULL;
1548 ConfigItem* item;
1549
1550 if (configList->menuSkip(menu))
1551 return;
1552
1553 switch (configList->mode) {
1554 case singleMode:
1555 list = configList;
1556 parent = menu_get_parent_menu(menu);
1557 if (!parent)
1558 return;
1559 list->setRootMenu(parent);
1560 break;
1561 case symbolMode:
1562 if (menu->flags & MENU_ROOT) {
1563 configList->setRootMenu(menu);
1564 configList->clearSelection();
1565 list = menuList;
1566 } else {
1567 list = configList;
1568 parent = menu_get_parent_menu(menu->parent);
1569 if (!parent)
1570 return;
1571 item = menuList->findConfigItem(parent);
1572 if (item) {
1573 item->setSelected(true);
1574 menuList->scrollToItem(item);
1575 }
1576 list->setRootMenu(parent);
1577 }
1578 break;
1579 case fullMode:
1580 list = configList;
1581 break;
1582 default:
1583 break;
1584 }
1585
1586 if (list) {
1587 item = list->findConfigItem(menu);
1588 if (item) {
1589 item->setSelected(true);
1590 list->scrollToItem(item);
1591 list->setFocus();
1592 }
1593 }
Roman Zippelb65a47e2006-06-08 22:12:47 -07001594}
1595
Linus Torvalds1da177e2005-04-16 15:20:36 -07001596void ConfigMainWindow::listFocusChanged(void)
1597{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001598 if (menuList->mode == menuMode)
1599 configList->clearSelection();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001600}
1601
1602void ConfigMainWindow::goBack(void)
1603{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001604 ConfigItem* item;
1605
1606 configList->setParentMenu();
1607 if (configList->rootEntry == &rootmenu)
1608 backAction->setEnabled(false);
1609 item = (ConfigItem*)menuList->selectedItems().first();
1610 while (item) {
1611 if (item->menu == configList->rootEntry) {
1612 item->setSelected(true);
1613 break;
1614 }
1615 item = (ConfigItem*)item->parent();
1616 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001617}
1618
1619void ConfigMainWindow::showSingleView(void)
1620{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001621 singleViewAction->setEnabled(false);
1622 singleViewAction->setChecked(true);
1623 splitViewAction->setEnabled(true);
1624 splitViewAction->setChecked(false);
1625 fullViewAction->setEnabled(true);
1626 fullViewAction->setChecked(false);
1627
Linus Torvalds1da177e2005-04-16 15:20:36 -07001628 menuView->hide();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001629 menuList->setRootMenu(0);
1630 configList->mode = singleMode;
1631 if (configList->rootEntry == &rootmenu)
1632 configList->updateListAll();
1633 else
1634 configList->setRootMenu(&rootmenu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001635 configList->setFocus();
1636}
1637
1638void ConfigMainWindow::showSplitView(void)
1639{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001640 singleViewAction->setEnabled(true);
1641 singleViewAction->setChecked(false);
1642 splitViewAction->setEnabled(false);
1643 splitViewAction->setChecked(true);
1644 fullViewAction->setEnabled(true);
1645 fullViewAction->setChecked(false);
1646
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001647 configList->mode = symbolMode;
1648 if (configList->rootEntry == &rootmenu)
1649 configList->updateListAll();
1650 else
1651 configList->setRootMenu(&rootmenu);
1652 configList->setAllOpen(true);
1653 configApp->processEvents();
1654 menuList->mode = menuMode;
1655 menuList->setRootMenu(&rootmenu);
1656 menuList->setAllOpen(true);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001657 menuView->show();
1658 menuList->setFocus();
1659}
1660
1661void ConfigMainWindow::showFullView(void)
1662{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001663 singleViewAction->setEnabled(true);
1664 singleViewAction->setChecked(false);
1665 splitViewAction->setEnabled(true);
1666 splitViewAction->setChecked(false);
1667 fullViewAction->setEnabled(false);
1668 fullViewAction->setChecked(true);
1669
Linus Torvalds1da177e2005-04-16 15:20:36 -07001670 menuView->hide();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001671 menuList->setRootMenu(0);
1672 configList->mode = fullMode;
1673 if (configList->rootEntry == &rootmenu)
1674 configList->updateListAll();
1675 else
1676 configList->setRootMenu(&rootmenu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001677 configList->setFocus();
1678}
1679
Linus Torvalds1da177e2005-04-16 15:20:36 -07001680/*
1681 * ask for saving configuration before quitting
1682 * TODO ask only when something changed
1683 */
1684void ConfigMainWindow::closeEvent(QCloseEvent* e)
1685{
Karsten Wieseb3214292006-12-13 00:34:06 -08001686 if (!conf_get_changed()) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001687 e->accept();
1688 return;
1689 }
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001690 QMessageBox mb("qconf", _("Save configuration?"), QMessageBox::Warning,
Linus Torvalds1da177e2005-04-16 15:20:36 -07001691 QMessageBox::Yes | QMessageBox::Default, QMessageBox::No, QMessageBox::Cancel | QMessageBox::Escape);
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001692 mb.setButtonText(QMessageBox::Yes, _("&Save Changes"));
1693 mb.setButtonText(QMessageBox::No, _("&Discard Changes"));
1694 mb.setButtonText(QMessageBox::Cancel, _("Cancel Exit"));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001695 switch (mb.exec()) {
1696 case QMessageBox::Yes:
Michal Marekbac6aa82011-05-25 15:10:25 +02001697 if (saveConfig())
1698 e->accept();
1699 else
1700 e->ignore();
1701 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001702 case QMessageBox::No:
1703 e->accept();
1704 break;
1705 case QMessageBox::Cancel:
1706 e->ignore();
1707 break;
1708 }
1709}
1710
1711void ConfigMainWindow::showIntro(void)
1712{
Arnaud Lacombe652cf982010-08-14 23:51:40 -04001713 static const QString str = _("Welcome to the qconf graphical configuration tool.\n\n"
Linus Torvalds1da177e2005-04-16 15:20:36 -07001714 "For each option, a blank box indicates the feature is disabled, a check\n"
1715 "indicates it is enabled, and a dot indicates that it is to be compiled\n"
1716 "as a module. Clicking on the box will cycle through the three states.\n\n"
1717 "If you do not see an option (e.g., a device driver) that you believe\n"
1718 "should be present, try turning on Show All Options under the Options menu.\n"
1719 "Although there is no cross reference yet to help you figure out what other\n"
1720 "options must be enabled to support the option you are interested in, you can\n"
1721 "still view the help of a grayed-out option.\n\n"
1722 "Toggling Show Debug Info under the Options menu will show the dependencies,\n"
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001723 "which you can then match by examining other options.\n\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001724
1725 QMessageBox::information(this, "qconf", str);
1726}
1727
1728void ConfigMainWindow::showAbout(void)
1729{
EGRY Gaborc21a2d92008-01-11 23:52:07 +01001730 static const QString str = _("qconf is Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>.\n\n"
1731 "Bug reports and feature request can also be entered at http://bugzilla.kernel.org/\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001732
1733 QMessageBox::information(this, "qconf", str);
1734}
1735
1736void ConfigMainWindow::saveSettings(void)
1737{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001738 configSettings->setValue("/window x", pos().x());
1739 configSettings->setValue("/window y", pos().y());
1740 configSettings->setValue("/window width", size().width());
1741 configSettings->setValue("/window height", size().height());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001742
1743 QString entry;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001744 switch(configList->mode) {
1745 case singleMode :
1746 entry = "single";
1747 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001748
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001749 case symbolMode :
1750 entry = "split";
1751 break;
1752
1753 case fullMode :
1754 entry = "full";
1755 break;
1756
1757 default:
1758 break;
1759 }
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001760 configSettings->setValue("/listMode", entry);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001761
Roman Zippel7fc925f2006-06-08 22:12:46 -07001762 configSettings->writeSizes("/split1", split1->sizes());
1763 configSettings->writeSizes("/split2", split2->sizes());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001764}
1765
Karsten Wiese3b354c52006-12-13 00:34:08 -08001766void ConfigMainWindow::conf_changed(void)
1767{
1768 if (saveAction)
1769 saveAction->setEnabled(conf_get_changed());
1770}
1771
Linus Torvalds1da177e2005-04-16 15:20:36 -07001772void fixup_rootmenu(struct menu *menu)
1773{
1774 struct menu *child;
1775 static int menu_cnt = 0;
1776
1777 menu->flags |= MENU_ROOT;
1778 for (child = menu->list; child; child = child->next) {
1779 if (child->prompt && child->prompt->type == P_MENU) {
1780 menu_cnt++;
1781 fixup_rootmenu(child);
1782 menu_cnt--;
1783 } else if (!menu_cnt)
1784 fixup_rootmenu(child);
1785 }
1786}
1787
1788static const char *progname;
1789
1790static void usage(void)
1791{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001792 printf(_("%s [-s] <config>\n").toLatin1().constData(), progname);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001793 exit(0);
1794}
1795
1796int main(int ac, char** av)
1797{
1798 ConfigMainWindow* v;
1799 const char *name;
1800
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -07001801 bindtextdomain(PACKAGE, LOCALEDIR);
1802 textdomain(PACKAGE);
1803
Linus Torvalds1da177e2005-04-16 15:20:36 -07001804 progname = av[0];
1805 configApp = new QApplication(ac, av);
1806 if (ac > 1 && av[1][0] == '-') {
1807 switch (av[1][1]) {
Michal Marek0a1f00a2015-04-08 13:30:42 +02001808 case 's':
1809 conf_set_message_callback(NULL);
1810 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001811 case 'h':
1812 case '?':
1813 usage();
1814 }
1815 name = av[2];
1816 } else
1817 name = av[1];
1818 if (!name)
1819 usage();
1820
1821 conf_parse(name);
1822 fixup_rootmenu(&rootmenu);
1823 conf_read(NULL);
1824 //zconfdump(stdout);
1825
Roman Zippel7fc925f2006-06-08 22:12:46 -07001826 configSettings = new ConfigSettings();
1827 configSettings->beginGroup("/kconfig/qconf");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001828 v = new ConfigMainWindow();
1829
1830 //zconfdump(stdout);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001831 configApp->connect(configApp, SIGNAL(lastWindowClosed()), SLOT(quit()));
1832 configApp->connect(configApp, SIGNAL(aboutToQuit()), v, SLOT(saveSettings()));
Roman Zippel43bf6122006-06-08 22:12:45 -07001833 v->show();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001834 configApp->exec();
1835
Roman Zippel7fc925f2006-06-08 22:12:46 -07001836 configSettings->endGroup();
1837 delete configSettings;
1838
Linus Torvalds1da177e2005-04-16 15:20:36 -07001839 return 0;
1840}