blob: 7cab996c3617cba6637ef58d54699d6734c379e1 [file] [log] [blame]
Masahiro Yamada0c874102018-12-18 21:13:35 +09001// SPDX-License-Identifier: GPL-2.0
Linus Torvalds1da177e2005-04-16 15:20:36 -07002/*
3 * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
Boris Barbulovskib4ff1de2015-09-22 11:36:38 -07004 * Copyright (C) 2015 Boris Barbulovski <bbarbulovski@gmail.com>
Linus Torvalds1da177e2005-04-16 15:20:36 -07005 */
6
Boris Barbulovski85eaf282015-09-22 11:36:03 -07007#include <QAction>
Mauro Carvalho Chehabcf81dfa2020-06-30 08:26:35 +02008#include <QApplication>
9#include <QCloseEvent>
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +020010#include <QDebug>
Mauro Carvalho Chehabcf81dfa2020-06-30 08:26:35 +020011#include <QDesktopWidget>
Boris Barbulovskibea00772015-09-22 11:36:04 -070012#include <QFileDialog>
Mauro Carvalho Chehabcf81dfa2020-06-30 08:26:35 +020013#include <QLabel>
14#include <QLayout>
15#include <QList>
Boris Barbulovski76bede82015-09-22 11:36:07 -070016#include <QMenu>
Mauro Carvalho Chehabcf81dfa2020-06-30 08:26:35 +020017#include <QMenuBar>
18#include <QMessageBox>
19#include <QToolBar>
Linus Torvalds1da177e2005-04-16 15:20:36 -070020
21#include <stdlib.h>
22
23#include "lkc.h"
24#include "qconf.h"
25
Masahiro Yamada3b541978562018-12-21 17:33:07 +090026#include "images.h"
Linus Torvalds1da177e2005-04-16 15:20:36 -070027
Arnaldo Carvalho de Melo3b9fa092005-05-05 15:09:46 -070028
Linus Torvalds1da177e2005-04-16 15:20:36 -070029static QApplication *configApp;
Roman Zippel7fc925f2006-06-08 22:12:46 -070030static ConfigSettings *configSettings;
Linus Torvalds1da177e2005-04-16 15:20:36 -070031
Boris Barbulovski85eaf282015-09-22 11:36:03 -070032QAction *ConfigMainWindow::saveAction;
Karsten Wiese3b354c52006-12-13 00:34:08 -080033
Ben Hutchings00d4f8f2013-10-06 19:21:31 +010034ConfigSettings::ConfigSettings()
35 : QSettings("kernel.org", "qconf")
36{
37}
38
Linus Torvalds1da177e2005-04-16 15:20:36 -070039/**
40 * Reads a list of integer values from the application settings.
41 */
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070042QList<int> ConfigSettings::readSizes(const QString& key, bool *ok)
Linus Torvalds1da177e2005-04-16 15:20:36 -070043{
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070044 QList<int> result;
Li Zefanc1f96f02010-05-07 13:58:04 +080045
Boris Barbulovski83c3a1b2016-11-30 14:57:55 -080046 if (contains(key))
47 {
48 QStringList entryList = value(key).toStringList();
49 QStringList::Iterator it;
50
51 for (it = entryList.begin(); it != entryList.end(); ++it)
52 result.push_back((*it).toInt());
53
54 *ok = true;
55 }
56 else
57 *ok = false;
Linus Torvalds1da177e2005-04-16 15:20:36 -070058
59 return result;
60}
61
62/**
63 * Writes a list of integer values to the application settings.
64 */
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070065bool ConfigSettings::writeSizes(const QString& key, const QList<int>& value)
Linus Torvalds1da177e2005-04-16 15:20:36 -070066{
67 QStringList stringList;
Boris Barbulovski041fbdc2015-09-22 11:36:05 -070068 QList<int>::ConstIterator it;
Linus Torvalds1da177e2005-04-16 15:20:36 -070069
70 for (it = value.begin(); it != value.end(); ++it)
71 stringList.push_back(QString::number(*it));
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070072 setValue(key, stringList);
Boris Barbulovski59e56442015-09-22 11:36:18 -070073
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -070074 return true;
Linus Torvalds1da177e2005-04-16 15:20:36 -070075}
Linus Torvalds1da177e2005-04-16 15:20:36 -070076
Masahiro Yamada5cb255f2020-08-07 18:19:07 +090077QIcon ConfigItem::symbolYesIcon;
78QIcon ConfigItem::symbolModIcon;
79QIcon ConfigItem::symbolNoIcon;
80QIcon ConfigItem::choiceYesIcon;
81QIcon ConfigItem::choiceNoIcon;
82QIcon ConfigItem::menuIcon;
83QIcon ConfigItem::menubackIcon;
Boris Barbulovski59e56442015-09-22 11:36:18 -070084
85/*
Boris Barbulovski59e56442015-09-22 11:36:18 -070086 * update the displayed of a menu entry
87 */
88void ConfigItem::updateMenu(void)
89{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -070090 ConfigList* list;
91 struct symbol* sym;
92 struct property *prop;
93 QString prompt;
94 int type;
95 tristate expr;
96
97 list = listView();
98 if (goParent) {
Masahiro Yamada5cb255f2020-08-07 18:19:07 +090099 setIcon(promptColIdx, menubackIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700100 prompt = "..";
101 goto set_prompt;
102 }
103
104 sym = menu->sym;
105 prop = menu->prompt;
Masahiro Yamada3c73ff02020-08-07 18:19:02 +0900106 prompt = menu_get_prompt(menu);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700107
108 if (prop) switch (prop->type) {
109 case P_MENU:
110 if (list->mode == singleMode || list->mode == symbolMode) {
111 /* a menuconfig entry is displayed differently
112 * depending whether it's at the view root or a child.
113 */
114 if (sym && list->rootEntry == menu)
115 break;
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900116 setIcon(promptColIdx, menuIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700117 } else {
118 if (sym)
119 break;
Masahiro Yamada711b8752020-08-07 18:19:03 +0900120 setIcon(promptColIdx, QIcon());
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700121 }
122 goto set_prompt;
123 case P_COMMENT:
Masahiro Yamada711b8752020-08-07 18:19:03 +0900124 setIcon(promptColIdx, QIcon());
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700125 goto set_prompt;
126 default:
127 ;
128 }
129 if (!sym)
130 goto set_prompt;
131
Masahiro Yamada3c73ff02020-08-07 18:19:02 +0900132 setText(nameColIdx, sym->name);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700133
134 type = sym_get_type(sym);
135 switch (type) {
136 case S_BOOLEAN:
137 case S_TRISTATE:
138 char ch;
139
Marco Ammonbaa23ec2019-07-04 12:50:41 +0200140 if (!sym_is_changeable(sym) && list->optMode == normalOpt) {
Masahiro Yamada711b8752020-08-07 18:19:03 +0900141 setIcon(promptColIdx, QIcon());
Mauro Carvalho Chehabcf497b92020-04-02 11:27:58 +0200142 setText(noColIdx, QString());
143 setText(modColIdx, QString());
144 setText(yesColIdx, QString());
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700145 break;
146 }
147 expr = sym_get_tristate_value(sym);
148 switch (expr) {
149 case yes:
150 if (sym_is_choice_value(sym) && type == S_BOOLEAN)
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900151 setIcon(promptColIdx, choiceYesIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700152 else
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900153 setIcon(promptColIdx, symbolYesIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700154 setText(yesColIdx, "Y");
155 ch = 'Y';
156 break;
157 case mod:
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900158 setIcon(promptColIdx, symbolModIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700159 setText(modColIdx, "M");
160 ch = 'M';
161 break;
162 default:
163 if (sym_is_choice_value(sym) && type == S_BOOLEAN)
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900164 setIcon(promptColIdx, choiceNoIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700165 else
Masahiro Yamada5cb255f2020-08-07 18:19:07 +0900166 setIcon(promptColIdx, symbolNoIcon);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700167 setText(noColIdx, "N");
168 ch = 'N';
169 break;
170 }
171 if (expr != no)
172 setText(noColIdx, sym_tristate_within_range(sym, no) ? "_" : 0);
173 if (expr != mod)
174 setText(modColIdx, sym_tristate_within_range(sym, mod) ? "_" : 0);
175 if (expr != yes)
176 setText(yesColIdx, sym_tristate_within_range(sym, yes) ? "_" : 0);
177
178 setText(dataColIdx, QChar(ch));
179 break;
180 case S_INT:
181 case S_HEX:
182 case S_STRING:
183 const char* data;
184
185 data = sym_get_string_value(sym);
186
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700187 setText(dataColIdx, data);
188 if (type == S_STRING)
189 prompt = QString("%1: %2").arg(prompt).arg(data);
190 else
191 prompt = QString("(%2) %1").arg(prompt).arg(data);
192 break;
193 }
194 if (!sym_has_value(sym) && visible)
Sam Ravnborg694c49a2018-05-22 21:36:12 +0200195 prompt += " (NEW)";
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700196set_prompt:
197 setText(promptColIdx, prompt);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700198}
199
200void ConfigItem::testUpdateMenu(bool v)
201{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700202 ConfigItem* i;
203
204 visible = v;
205 if (!menu)
206 return;
207
208 sym_calc_value(menu->sym);
209 if (menu->flags & MENU_CHANGED) {
210 /* the menu entry changed, so update all list items */
211 menu->flags &= ~MENU_CHANGED;
212 for (i = (ConfigItem*)menu->data; i; i = i->nextItem)
213 i->updateMenu();
214 } else if (listView()->updateAll)
215 updateMenu();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700216}
217
218
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700219/*
220 * construct a menu entry
221 */
222void ConfigItem::init(void)
223{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700224 if (menu) {
225 ConfigList* list = listView();
226 nextItem = (ConfigItem*)menu->data;
227 menu->data = this;
228
229 if (list->mode != fullMode)
230 setExpanded(true);
231 sym_calc_value(menu->sym);
232 }
233 updateMenu();
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700234}
235
236/*
237 * destruct a menu entry
238 */
239ConfigItem::~ConfigItem(void)
240{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700241 if (menu) {
242 ConfigItem** ip = (ConfigItem**)&menu->data;
243 for (; *ip; ip = &(*ip)->nextItem) {
244 if (*ip == this) {
245 *ip = nextItem;
246 break;
247 }
248 }
249 }
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700250}
251
Roman Zippel43bf6122006-06-08 22:12:45 -0700252ConfigLineEdit::ConfigLineEdit(ConfigView* parent)
253 : Parent(parent)
254{
Boris Barbulovskic14fa5e2015-09-22 11:36:21 -0700255 connect(this, SIGNAL(editingFinished()), SLOT(hide()));
Roman Zippel43bf6122006-06-08 22:12:45 -0700256}
257
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700258void ConfigLineEdit::show(ConfigItem* i)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700259{
260 item = i;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700261 if (sym_get_string_value(item->menu->sym))
Masahiro Yamada3c73ff02020-08-07 18:19:02 +0900262 setText(sym_get_string_value(item->menu->sym));
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700263 else
Mauro Carvalho Chehabcf497b92020-04-02 11:27:58 +0200264 setText(QString());
Linus Torvalds1da177e2005-04-16 15:20:36 -0700265 Parent::show();
266 setFocus();
267}
268
269void ConfigLineEdit::keyPressEvent(QKeyEvent* e)
270{
271 switch (e->key()) {
Markus Heidelbergfbb86372009-05-18 01:36:51 +0200272 case Qt::Key_Escape:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700273 break;
Markus Heidelbergfbb86372009-05-18 01:36:51 +0200274 case Qt::Key_Return:
275 case Qt::Key_Enter:
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700276 sym_set_string_value(item->menu->sym, text().toLatin1());
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900277 ConfigList::updateListForAll();
Linus Torvalds1da177e2005-04-16 15:20:36 -0700278 break;
279 default:
280 Parent::keyPressEvent(e);
281 return;
282 }
283 e->accept();
284 parent()->list->setFocus();
285 hide();
286}
287
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700288ConfigList::ConfigList(ConfigView* p, const char *name)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700289 : Parent(p),
290 updateAll(false),
Boris Barbulovskidbf62932015-09-22 11:36:26 -0700291 showName(false), showRange(false), showData(false), mode(singleMode), optMode(normalOpt),
Boris Barbulovski59e56442015-09-22 11:36:18 -0700292 rootEntry(0), headerPopup(0)
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700293{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700294 setObjectName(name);
Boris Barbulovskia5225e92015-09-22 11:36:29 -0700295 setSortingEnabled(false);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700296 setRootIsDecorated(true);
297
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700298 setVerticalScrollMode(ScrollPerPixel);
299 setHorizontalScrollMode(ScrollPerPixel);
300
Masahiro Yamada97bebbc2020-07-30 02:46:17 +0900301 setHeaderLabels(QStringList() << "Option" << "Name" << "N" << "M" << "Y" << "Value");
Boris Barbulovskia52cb322015-09-22 11:36:24 -0700302
Boris Barbulovskic14fa5e2015-09-22 11:36:21 -0700303 connect(this, SIGNAL(itemSelectionChanged(void)),
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700304 SLOT(updateSelection(void)));
305
306 if (name) {
307 configSettings->beginGroup(name);
308 showName = configSettings->value("/showName", false).toBool();
309 showRange = configSettings->value("/showRange", false).toBool();
310 showData = configSettings->value("/showData", false).toBool();
311 optMode = (enum optionMode)configSettings->value("/optionMode", 0).toInt();
312 configSettings->endGroup();
313 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
314 }
315
Masahiro Yamadaabf741a2020-08-07 18:19:04 +0900316 showColumn(promptColIdx);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700317
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900318 allLists.append(this);
319
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700320 reinit();
321}
322
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900323ConfigList::~ConfigList()
324{
325 allLists.removeOne(this);
326}
327
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700328bool ConfigList::menuSkip(struct menu *menu)
329{
330 if (optMode == normalOpt && menu_is_visible(menu))
331 return false;
332 if (optMode == promptOpt && menu_has_prompt(menu))
333 return false;
334 if (optMode == allOpt)
335 return false;
336 return true;
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700337}
Boris Barbulovski59e56442015-09-22 11:36:18 -0700338
339void ConfigList::reinit(void)
340{
Masahiro Yamadaabf741a2020-08-07 18:19:04 +0900341 hideColumn(dataColIdx);
342 hideColumn(yesColIdx);
343 hideColumn(modColIdx);
344 hideColumn(noColIdx);
345 hideColumn(nameColIdx);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700346
347 if (showName)
Masahiro Yamadaabf741a2020-08-07 18:19:04 +0900348 showColumn(nameColIdx);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700349 if (showRange) {
Masahiro Yamadaabf741a2020-08-07 18:19:04 +0900350 showColumn(noColIdx);
351 showColumn(modColIdx);
352 showColumn(yesColIdx);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700353 }
354 if (showData)
Masahiro Yamadaabf741a2020-08-07 18:19:04 +0900355 showColumn(dataColIdx);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700356
357 updateListAll();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700358}
359
Masahiro Yamadad4bbe8a2020-08-07 18:19:09 +0900360void ConfigList::setOptionMode(QAction *action)
361{
362 if (action == showNormalAction)
363 optMode = normalOpt;
364 else if (action == showAllAction)
365 optMode = allOpt;
366 else
367 optMode = promptOpt;
368
369 updateListAll();
370}
371
Boris Barbulovski59e56442015-09-22 11:36:18 -0700372void ConfigList::saveSettings(void)
373{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700374 if (!objectName().isEmpty()) {
375 configSettings->beginGroup(objectName());
376 configSettings->setValue("/showName", showName);
377 configSettings->setValue("/showRange", showRange);
378 configSettings->setValue("/showData", showData);
379 configSettings->setValue("/optionMode", (int)optMode);
380 configSettings->endGroup();
381 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700382}
383
384ConfigItem* ConfigList::findConfigItem(struct menu *menu)
385{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700386 ConfigItem* item = (ConfigItem*)menu->data;
387
388 for (; item; item = item->nextItem) {
389 if (this == item->listView())
390 break;
391 }
392
393 return item;
Boris Barbulovski59e56442015-09-22 11:36:18 -0700394}
395
396void ConfigList::updateSelection(void)
397{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700398 struct menu *menu;
399 enum prop_type type;
400
Boris Barbulovskibe596aa2015-09-22 11:36:28 -0700401 if (selectedItems().count() == 0)
402 return;
403
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700404 ConfigItem* item = (ConfigItem*)selectedItems().first();
405 if (!item)
406 return;
407
408 menu = item->menu;
409 emit menuChanged(menu);
410 if (!menu)
411 return;
412 type = menu->prompt ? menu->prompt->type : P_UNKNOWN;
413 if (mode == menuMode && type == P_MENU)
414 emit menuSelected(menu);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700415}
416
Masahiro Yamadacb770432020-08-07 18:18:59 +0900417void ConfigList::updateList()
Boris Barbulovski59e56442015-09-22 11:36:18 -0700418{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700419 ConfigItem* last = 0;
Masahiro Yamadacb770432020-08-07 18:18:59 +0900420 ConfigItem *item;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700421
422 if (!rootEntry) {
423 if (mode != listMode)
424 goto update;
425 QTreeWidgetItemIterator it(this);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700426
427 while (*it) {
428 item = (ConfigItem*)(*it);
429 if (!item->menu)
430 continue;
431 item->testUpdateMenu(menu_is_visible(item->menu));
432
433 ++it;
434 }
435 return;
436 }
437
438 if (rootEntry != &rootmenu && (mode == singleMode ||
439 (mode == symbolMode && rootEntry->parent != &rootmenu))) {
Boris Barbulovskiee7298f2015-09-22 11:36:37 -0700440 item = (ConfigItem *)topLevelItem(0);
Masahiro Yamada4b20e102020-08-01 16:08:49 +0900441 if (!item)
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700442 item = new ConfigItem(this, 0, true);
Masahiro Yamada4b20e102020-08-01 16:08:49 +0900443 last = item;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700444 }
445 if ((mode == singleMode || (mode == symbolMode && !(rootEntry->flags & MENU_ROOT))) &&
446 rootEntry->sym && rootEntry->prompt) {
Masahiro Yamadaccf56e52020-08-01 16:08:50 +0900447 item = last ? last->nextSibling() : nullptr;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700448 if (!item)
449 item = new ConfigItem(this, last, rootEntry, true);
450 else
451 item->testUpdateMenu(true);
452
453 updateMenuList(item, rootEntry);
454 update();
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700455 resizeColumnToContents(0);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700456 return;
457 }
458update:
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900459 updateMenuList(rootEntry);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700460 update();
Boris Barbulovskif999cc02015-09-22 11:36:31 -0700461 resizeColumnToContents(0);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700462}
463
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900464void ConfigList::updateListForAll()
465{
466 QListIterator<ConfigList *> it(allLists);
467
468 while (it.hasNext()) {
469 ConfigList *list = it.next();
470
471 list->updateList();
472 }
473}
474
475void ConfigList::updateListAllForAll()
476{
477 QListIterator<ConfigList *> it(allLists);
478
479 while (it.hasNext()) {
480 ConfigList *list = it.next();
481
482 list->updateList();
483 }
484}
485
Boris Barbulovski59e56442015-09-22 11:36:18 -0700486void ConfigList::setValue(ConfigItem* item, tristate val)
487{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700488 struct symbol* sym;
489 int type;
490 tristate oldval;
491
492 sym = item->menu ? item->menu->sym : 0;
493 if (!sym)
494 return;
495
496 type = sym_get_type(sym);
497 switch (type) {
498 case S_BOOLEAN:
499 case S_TRISTATE:
500 oldval = sym_get_tristate_value(sym);
501
502 if (!sym_set_tristate_value(sym, val))
503 return;
504 if (oldval == no && item->menu->list)
505 item->setExpanded(true);
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900506 ConfigList::updateListForAll();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700507 break;
508 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700509}
510
511void ConfigList::changeValue(ConfigItem* item)
512{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700513 struct symbol* sym;
514 struct menu* menu;
515 int type, oldexpr, newexpr;
516
517 menu = item->menu;
518 if (!menu)
519 return;
520 sym = menu->sym;
521 if (!sym) {
522 if (item->menu->list)
523 item->setExpanded(!item->isExpanded());
524 return;
525 }
526
527 type = sym_get_type(sym);
528 switch (type) {
529 case S_BOOLEAN:
530 case S_TRISTATE:
531 oldexpr = sym_get_tristate_value(sym);
532 newexpr = sym_toggle_tristate_value(sym);
533 if (item->menu->list) {
534 if (oldexpr == newexpr)
535 item->setExpanded(!item->isExpanded());
536 else if (oldexpr == no)
537 item->setExpanded(true);
538 }
539 if (oldexpr != newexpr)
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900540 ConfigList::updateListForAll();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700541 break;
542 case S_INT:
543 case S_HEX:
544 case S_STRING:
Boris Barbulovskie336b9f2015-09-22 11:36:34 -0700545 parent()->lineEdit->show(item);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700546 break;
547 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700548}
549
550void ConfigList::setRootMenu(struct menu *menu)
551{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700552 enum prop_type type;
553
554 if (rootEntry == menu)
555 return;
556 type = menu && menu->prompt ? menu->prompt->type : P_UNKNOWN;
557 if (type != P_MENU)
558 return;
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900559 updateMenuList(0);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700560 rootEntry = menu;
561 updateListAll();
562 if (currentItem()) {
Mauro Carvalho Chehabb06c3ec2020-06-30 08:26:38 +0200563 setSelected(currentItem(), hasFocus());
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700564 scrollToItem(currentItem());
565 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700566}
567
568void ConfigList::setParentMenu(void)
569{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700570 ConfigItem* item;
571 struct menu *oldroot;
572
573 oldroot = rootEntry;
574 if (rootEntry == &rootmenu)
575 return;
576 setRootMenu(menu_get_parent_menu(rootEntry->parent));
577
578 QTreeWidgetItemIterator it(this);
579 while (*it) {
580 item = (ConfigItem *)(*it);
581 if (item->menu == oldroot) {
582 setCurrentItem(item);
583 scrollToItem(item);
584 break;
585 }
586
587 ++it;
588 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700589}
590
591/*
592 * update all the children of a menu entry
593 * removes/adds the entries from the parent widget as necessary
594 *
595 * parent: either the menu list widget or a menu entry widget
596 * menu: entry to be updated
597 */
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700598void ConfigList::updateMenuList(ConfigItem *parent, struct menu* menu)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700599{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700600 struct menu* child;
601 ConfigItem* item;
602 ConfigItem* last;
603 bool visible;
604 enum prop_type type;
605
606 if (!menu) {
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700607 while (parent->childCount() > 0)
608 {
609 delete parent->takeChild(0);
610 }
611
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700612 return;
613 }
614
615 last = parent->firstChild();
616 if (last && !last->goParent)
617 last = 0;
618 for (child = menu->list; child; child = child->next) {
619 item = last ? last->nextSibling() : parent->firstChild();
620 type = child->prompt ? child->prompt->type : P_UNKNOWN;
621
622 switch (mode) {
623 case menuMode:
624 if (!(child->flags & MENU_ROOT))
625 goto hide;
626 break;
627 case symbolMode:
628 if (child->flags & MENU_ROOT)
629 goto hide;
630 break;
631 default:
632 break;
633 }
634
635 visible = menu_is_visible(child);
636 if (!menuSkip(child)) {
637 if (!child->sym && !child->list && !child->prompt)
638 continue;
639 if (!item || item->menu != child)
640 item = new ConfigItem(parent, last, child, visible);
641 else
642 item->testUpdateMenu(visible);
643
644 if (mode == fullMode || mode == menuMode || type != P_MENU)
645 updateMenuList(item, child);
646 else
647 updateMenuList(item, 0);
648 last = item;
649 continue;
650 }
Mauro Carvalho Chehab60969f02020-04-02 11:28:03 +0200651hide:
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700652 if (item && item->menu == child) {
653 last = parent->firstChild();
654 if (last == item)
655 last = 0;
656 else while (last->nextSibling() != item)
657 last = last->nextSibling();
658 delete item;
659 }
660 }
Boris Barbulovski59e56442015-09-22 11:36:18 -0700661}
662
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900663void ConfigList::updateMenuList(struct menu *menu)
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700664{
665 struct menu* child;
666 ConfigItem* item;
667 ConfigItem* last;
668 bool visible;
669 enum prop_type type;
670
671 if (!menu) {
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900672 while (topLevelItemCount() > 0)
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700673 {
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900674 delete takeTopLevelItem(0);
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700675 }
676
677 return;
678 }
679
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900680 last = (ConfigItem *)topLevelItem(0);
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700681 if (last && !last->goParent)
682 last = 0;
683 for (child = menu->list; child; child = child->next) {
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900684 item = last ? last->nextSibling() : (ConfigItem *)topLevelItem(0);
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700685 type = child->prompt ? child->prompt->type : P_UNKNOWN;
686
687 switch (mode) {
688 case menuMode:
689 if (!(child->flags & MENU_ROOT))
690 goto hide;
691 break;
692 case symbolMode:
693 if (child->flags & MENU_ROOT)
694 goto hide;
695 break;
696 default:
697 break;
698 }
699
700 visible = menu_is_visible(child);
701 if (!menuSkip(child)) {
702 if (!child->sym && !child->list && !child->prompt)
703 continue;
704 if (!item || item->menu != child)
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900705 item = new ConfigItem(this, last, child, visible);
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700706 else
707 item->testUpdateMenu(visible);
708
709 if (mode == fullMode || mode == menuMode || type != P_MENU)
710 updateMenuList(item, child);
711 else
712 updateMenuList(item, 0);
713 last = item;
714 continue;
715 }
Mauro Carvalho Chehab60969f02020-04-02 11:28:03 +0200716hide:
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700717 if (item && item->menu == child) {
Masahiro Yamada5b75a6c2020-08-07 18:19:01 +0900718 last = (ConfigItem *)topLevelItem(0);
Boris Barbulovski5c6f1552015-09-22 11:36:27 -0700719 if (last == item)
720 last = 0;
721 else while (last->nextSibling() != item)
722 last = last->nextSibling();
723 delete item;
724 }
725 }
726}
727
Boris Barbulovski59e56442015-09-22 11:36:18 -0700728void ConfigList::keyPressEvent(QKeyEvent* ev)
729{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700730 QTreeWidgetItem* i = currentItem();
731 ConfigItem* item;
732 struct menu *menu;
733 enum prop_type type;
734
735 if (ev->key() == Qt::Key_Escape && mode != fullMode && mode != listMode) {
736 emit parentSelected();
737 ev->accept();
738 return;
739 }
740
741 if (!i) {
742 Parent::keyPressEvent(ev);
743 return;
744 }
745 item = (ConfigItem*)i;
746
747 switch (ev->key()) {
748 case Qt::Key_Return:
749 case Qt::Key_Enter:
750 if (item->goParent) {
751 emit parentSelected();
752 break;
753 }
754 menu = item->menu;
755 if (!menu)
756 break;
757 type = menu->prompt ? menu->prompt->type : P_UNKNOWN;
758 if (type == P_MENU && rootEntry != menu &&
759 mode != fullMode && mode != menuMode) {
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +0200760 if (mode == menuMode)
761 emit menuSelected(menu);
762 else
763 emit itemSelected(menu);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700764 break;
765 }
766 case Qt::Key_Space:
767 changeValue(item);
768 break;
769 case Qt::Key_N:
770 setValue(item, no);
771 break;
772 case Qt::Key_M:
773 setValue(item, mod);
774 break;
775 case Qt::Key_Y:
776 setValue(item, yes);
777 break;
778 default:
779 Parent::keyPressEvent(ev);
780 return;
781 }
782 ev->accept();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700783}
784
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700785void ConfigList::mousePressEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700786{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700787 //QPoint p(contentsToViewport(e->pos()));
788 //printf("contentsMousePressEvent: %d,%d\n", p.x(), p.y());
789 Parent::mousePressEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700790}
791
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700792void ConfigList::mouseReleaseEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700793{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700794 QPoint p = e->pos();
795 ConfigItem* item = (ConfigItem*)itemAt(p);
796 struct menu *menu;
797 enum prop_type ptype;
798 QIcon icon;
799 int idx, x;
800
801 if (!item)
802 goto skip;
803
804 menu = item->menu;
805 x = header()->offset() + p.x();
Boris Barbulovski76d53cb2015-09-22 11:36:35 -0700806 idx = header()->logicalIndexAt(x);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700807 switch (idx) {
808 case promptColIdx:
Masahiro Yamada711b8752020-08-07 18:19:03 +0900809 icon = item->icon(promptColIdx);
Boris Barbulovski76d53cb2015-09-22 11:36:35 -0700810 if (!icon.isNull()) {
811 int off = header()->sectionPosition(0) + visualRect(indexAt(p)).x() + 4; // 4 is Hardcoded image offset. There might be a way to do it properly.
812 if (x >= off && x < off + icon.availableSizes().first().width()) {
813 if (item->goParent) {
814 emit parentSelected();
815 break;
816 } else if (!menu)
817 break;
818 ptype = menu->prompt ? menu->prompt->type : P_UNKNOWN;
819 if (ptype == P_MENU && rootEntry != menu &&
Maxime Chretien7eb7c106f2020-07-08 15:32:15 +0200820 mode != fullMode && mode != menuMode &&
821 mode != listMode)
Boris Barbulovski76d53cb2015-09-22 11:36:35 -0700822 emit menuSelected(menu);
823 else
824 changeValue(item);
825 }
826 }
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700827 break;
828 case noColIdx:
829 setValue(item, no);
830 break;
831 case modColIdx:
832 setValue(item, mod);
833 break;
834 case yesColIdx:
835 setValue(item, yes);
836 break;
837 case dataColIdx:
838 changeValue(item);
839 break;
840 }
841
842skip:
843 //printf("contentsMouseReleaseEvent: %d,%d\n", p.x(), p.y());
844 Parent::mouseReleaseEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700845}
846
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700847void ConfigList::mouseMoveEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700848{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700849 //QPoint p(contentsToViewport(e->pos()));
850 //printf("contentsMouseMoveEvent: %d,%d\n", p.x(), p.y());
851 Parent::mouseMoveEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700852}
853
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700854void ConfigList::mouseDoubleClickEvent(QMouseEvent* e)
Boris Barbulovski59e56442015-09-22 11:36:18 -0700855{
Mauro Carvalho Chehabe1f77692020-04-02 11:28:02 +0200856 QPoint p = e->pos();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700857 ConfigItem* item = (ConfigItem*)itemAt(p);
858 struct menu *menu;
859 enum prop_type ptype;
860
861 if (!item)
862 goto skip;
863 if (item->goParent) {
864 emit parentSelected();
865 goto skip;
866 }
867 menu = item->menu;
868 if (!menu)
869 goto skip;
870 ptype = menu->prompt ? menu->prompt->type : P_UNKNOWN;
Maxime Chretien7eb7c106f2020-07-08 15:32:15 +0200871 if (ptype == P_MENU && mode != listMode) {
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +0200872 if (mode == singleMode)
873 emit itemSelected(menu);
874 else if (mode == symbolMode)
875 emit menuSelected(menu);
876 } else if (menu->sym)
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700877 changeValue(item);
878
879skip:
880 //printf("contentsMouseDoubleClickEvent: %d,%d\n", p.x(), p.y());
881 Parent::mouseDoubleClickEvent(e);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700882}
883
884void ConfigList::focusInEvent(QFocusEvent *e)
885{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700886 struct menu *menu = NULL;
887
888 Parent::focusInEvent(e);
889
890 ConfigItem* item = (ConfigItem *)currentItem();
891 if (item) {
Mauro Carvalho Chehabb06c3ec2020-06-30 08:26:38 +0200892 setSelected(item, true);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700893 menu = item->menu;
894 }
895 emit gotFocus(menu);
Boris Barbulovski59e56442015-09-22 11:36:18 -0700896}
897
898void ConfigList::contextMenuEvent(QContextMenuEvent *e)
899{
Masahiro Yamadafa8de0a2020-08-07 18:19:08 +0900900 if (!headerPopup) {
901 QAction *action;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700902
Masahiro Yamadafa8de0a2020-08-07 18:19:08 +0900903 headerPopup = new QMenu(this);
904 action = new QAction("Show Name", this);
905 action->setCheckable(true);
906 connect(action, SIGNAL(toggled(bool)),
907 parent(), SLOT(setShowName(bool)));
908 connect(parent(), SIGNAL(showNameChanged(bool)),
Masahiro Yamadad85de332020-08-18 01:36:29 +0900909 action, SLOT(setChecked(bool)));
Masahiro Yamadafa8de0a2020-08-07 18:19:08 +0900910 action->setChecked(showName);
911 headerPopup->addAction(action);
912
913 action = new QAction("Show Range", this);
914 action->setCheckable(true);
915 connect(action, SIGNAL(toggled(bool)),
916 parent(), SLOT(setShowRange(bool)));
917 connect(parent(), SIGNAL(showRangeChanged(bool)),
Masahiro Yamadad85de332020-08-18 01:36:29 +0900918 action, SLOT(setChecked(bool)));
Masahiro Yamadafa8de0a2020-08-07 18:19:08 +0900919 action->setChecked(showRange);
920 headerPopup->addAction(action);
921
922 action = new QAction("Show Data", this);
923 action->setCheckable(true);
924 connect(action, SIGNAL(toggled(bool)),
925 parent(), SLOT(setShowData(bool)));
926 connect(parent(), SIGNAL(showDataChanged(bool)),
Masahiro Yamadad85de332020-08-18 01:36:29 +0900927 action, SLOT(setChecked(bool)));
Masahiro Yamadafa8de0a2020-08-07 18:19:08 +0900928 action->setChecked(showData);
929 headerPopup->addAction(action);
930 }
931
932 headerPopup->exec(e->globalPos());
933 e->accept();
Boris Barbulovski59e56442015-09-22 11:36:18 -0700934}
935
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +0900936QList<ConfigList *> ConfigList::allLists;
Masahiro Yamadad4bbe8a2020-08-07 18:19:09 +0900937QAction *ConfigList::showNormalAction;
938QAction *ConfigList::showAllAction;
939QAction *ConfigList::showPromptAction;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700940
Roman Zippel7fc925f2006-06-08 22:12:46 -0700941ConfigView::ConfigView(QWidget* parent, const char *name)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -0700942 : Parent(parent)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700943{
Boris Barbulovski9bd36ed2015-09-22 11:36:22 -0700944 setObjectName(name);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700945 QVBoxLayout *verticalLayout = new QVBoxLayout(this);
Boris Barbulovski92298b42015-09-22 11:36:11 -0700946 verticalLayout->setContentsMargins(0, 0, 0, 0);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700947
Boris Barbulovski1019f1a2015-09-22 11:36:17 -0700948 list = new ConfigList(this);
Boris Barbulovski29a70162015-09-22 11:36:10 -0700949 verticalLayout->addWidget(list);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700950 lineEdit = new ConfigLineEdit(this);
951 lineEdit->hide();
Boris Barbulovski29a70162015-09-22 11:36:10 -0700952 verticalLayout->addWidget(lineEdit);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700953}
954
Roman Zippel7fc925f2006-06-08 22:12:46 -0700955void ConfigView::setShowName(bool b)
956{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700957 if (list->showName != b) {
958 list->showName = b;
959 list->reinit();
960 emit showNameChanged(b);
961 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700962}
963
964void ConfigView::setShowRange(bool b)
965{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700966 if (list->showRange != b) {
967 list->showRange = b;
968 list->reinit();
969 emit showRangeChanged(b);
970 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700971}
972
973void ConfigView::setShowData(bool b)
974{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700975 if (list->showData != b) {
976 list->showData = b;
977 list->reinit();
978 emit showDataChanged(b);
979 }
980}
981
982void ConfigList::setAllOpen(bool open)
983{
984 QTreeWidgetItemIterator it(this);
985
986 while (*it) {
987 (*it)->setExpanded(open);
988
989 ++it;
990 }
Roman Zippel7fc925f2006-06-08 22:12:46 -0700991}
992
Roman Zippel43bf6122006-06-08 22:12:45 -0700993ConfigInfoView::ConfigInfoView(QWidget* parent, const char *name)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -0700994 : Parent(parent), sym(0), _menu(0)
Roman Zippel43bf6122006-06-08 22:12:45 -0700995{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700996 setObjectName(name);
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +0200997 setOpenLinks(false);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -0700998
999 if (!objectName().isEmpty()) {
1000 configSettings->beginGroup(objectName());
Boris Barbulovskie0393032016-11-30 14:57:52 -08001001 setShowDebug(configSettings->value("/showDebug", false).toBool());
Roman Zippel7fc925f2006-06-08 22:12:46 -07001002 configSettings->endGroup();
1003 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
1004 }
Masahiro Yamada7d1300e2020-08-18 01:36:30 +09001005
1006 contextMenu = createStandardContextMenu();
1007 QAction *action = new QAction("Show Debug Info", contextMenu);
1008
1009 action->setCheckable(true);
1010 connect(action, SIGNAL(toggled(bool)), SLOT(setShowDebug(bool)));
1011 connect(this, SIGNAL(showDebugChanged(bool)), action, SLOT(setChecked(bool)));
1012 action->setChecked(showDebug());
1013 contextMenu->addSeparator();
1014 contextMenu->addAction(action);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001015}
1016
1017void ConfigInfoView::saveSettings(void)
1018{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001019 if (!objectName().isEmpty()) {
1020 configSettings->beginGroup(objectName());
1021 configSettings->setValue("/showDebug", showDebug());
1022 configSettings->endGroup();
1023 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001024}
1025
1026void ConfigInfoView::setShowDebug(bool b)
1027{
1028 if (_showDebug != b) {
1029 _showDebug = b;
Alexander Stein133c5f72010-08-31 17:34:37 +02001030 if (_menu)
Roman Zippel43bf6122006-06-08 22:12:45 -07001031 menuInfo();
Roman Zippelab45d192006-06-08 22:12:47 -07001032 else if (sym)
1033 symbolInfo();
Roman Zippel43bf6122006-06-08 22:12:45 -07001034 emit showDebugChanged(b);
1035 }
1036}
1037
1038void ConfigInfoView::setInfo(struct menu *m)
1039{
Alexander Stein133c5f72010-08-31 17:34:37 +02001040 if (_menu == m)
Roman Zippelb65a47e2006-06-08 22:12:47 -07001041 return;
Alexander Stein133c5f72010-08-31 17:34:37 +02001042 _menu = m;
Roman Zippel6fa1da82007-01-10 23:15:31 -08001043 sym = NULL;
Alexander Stein133c5f72010-08-31 17:34:37 +02001044 if (!_menu)
Roman Zippel43bf6122006-06-08 22:12:45 -07001045 clear();
Roman Zippel6fa1da82007-01-10 23:15:31 -08001046 else
Roman Zippel43bf6122006-06-08 22:12:45 -07001047 menuInfo();
1048}
1049
Roman Zippelab45d192006-06-08 22:12:47 -07001050void ConfigInfoView::symbolInfo(void)
1051{
1052 QString str;
1053
1054 str += "<big>Symbol: <b>";
1055 str += print_filter(sym->name);
1056 str += "</b></big><br><br>value: ";
1057 str += print_filter(sym_get_string_value(sym));
1058 str += "<br>visibility: ";
1059 str += sym->visible == yes ? "y" : sym->visible == mod ? "m" : "n";
1060 str += "<br>";
1061 str += debug_info(sym);
1062
1063 setText(str);
1064}
1065
Roman Zippel43bf6122006-06-08 22:12:45 -07001066void ConfigInfoView::menuInfo(void)
1067{
1068 struct symbol* sym;
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001069 QString info;
1070 QTextStream stream(&info);
Roman Zippel43bf6122006-06-08 22:12:45 -07001071
Alexander Stein133c5f72010-08-31 17:34:37 +02001072 sym = _menu->sym;
Roman Zippel43bf6122006-06-08 22:12:45 -07001073 if (sym) {
Alexander Stein133c5f72010-08-31 17:34:37 +02001074 if (_menu->prompt) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001075 stream << "<big><b>";
1076 stream << print_filter(_menu->prompt->text);
1077 stream << "</b></big>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001078 if (sym->name) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001079 stream << " (";
Roman Zippelab45d192006-06-08 22:12:47 -07001080 if (showDebug())
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001081 stream << "<a href=\"s" << sym->name << "\">";
1082 stream << print_filter(sym->name);
Roman Zippelab45d192006-06-08 22:12:47 -07001083 if (showDebug())
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001084 stream << "</a>";
1085 stream << ")";
Roman Zippel43bf6122006-06-08 22:12:45 -07001086 }
1087 } else if (sym->name) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001088 stream << "<big><b>";
Roman Zippelab45d192006-06-08 22:12:47 -07001089 if (showDebug())
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001090 stream << "<a href=\"s" << sym->name << "\">";
1091 stream << print_filter(sym->name);
Roman Zippelab45d192006-06-08 22:12:47 -07001092 if (showDebug())
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001093 stream << "</a>";
1094 stream << "</b></big>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001095 }
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001096 stream << "<br><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001097
1098 if (showDebug())
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001099 stream << debug_info(sym);
1100
Masahiro Yamadaa46afd12020-09-14 23:59:48 +09001101 struct gstr help_gstr = str_new();
1102
1103 menu_get_ext_help(_menu, &help_gstr);
1104 stream << print_filter(str_get(&help_gstr));
1105 str_free(&help_gstr);
Alexander Stein133c5f72010-08-31 17:34:37 +02001106 } else if (_menu->prompt) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001107 stream << "<big><b>";
1108 stream << print_filter(_menu->prompt->text);
1109 stream << "</b></big><br><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001110 if (showDebug()) {
Alexander Stein133c5f72010-08-31 17:34:37 +02001111 if (_menu->prompt->visible.expr) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001112 stream << "&nbsp;&nbsp;dep: ";
1113 expr_print(_menu->prompt->visible.expr,
1114 expr_print_help, &stream, E_NONE);
1115 stream << "<br><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001116 }
Masahiro Yamadaa46afd12020-09-14 23:59:48 +09001117
1118 stream << "defined at " << _menu->file->name << ":"
1119 << _menu->lineno << "<br><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001120 }
1121 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001122
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001123 setText(info);
Roman Zippel43bf6122006-06-08 22:12:45 -07001124}
1125
1126QString ConfigInfoView::debug_info(struct symbol *sym)
1127{
1128 QString debug;
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001129 QTextStream stream(&debug);
Roman Zippel43bf6122006-06-08 22:12:45 -07001130
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001131 stream << "type: ";
1132 stream << print_filter(sym_type_name(sym->type));
Roman Zippel43bf6122006-06-08 22:12:45 -07001133 if (sym_is_choice(sym))
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001134 stream << " (choice)";
Roman Zippel43bf6122006-06-08 22:12:45 -07001135 debug += "<br>";
1136 if (sym->rev_dep.expr) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001137 stream << "reverse dep: ";
1138 expr_print(sym->rev_dep.expr, expr_print_help, &stream, E_NONE);
1139 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001140 }
1141 for (struct property *prop = sym->prop; prop; prop = prop->next) {
1142 switch (prop->type) {
1143 case P_PROMPT:
1144 case P_MENU:
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001145 stream << "prompt: <a href=\"m" << sym->name << "\">";
1146 stream << print_filter(prop->text);
1147 stream << "</a><br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001148 break;
1149 case P_DEFAULT:
Roman Zippel93449082008-01-14 04:50:54 +01001150 case P_SELECT:
1151 case P_RANGE:
Mauro Carvalho Chehab8f8499a2020-06-30 08:48:53 +02001152 case P_COMMENT:
1153 case P_IMPLY:
1154 case P_SYMBOL:
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001155 stream << prop_get_type_name(prop->type);
1156 stream << ": ";
1157 expr_print(prop->expr, expr_print_help,
1158 &stream, E_NONE);
1159 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001160 break;
1161 case P_CHOICE:
1162 if (sym_is_choice(sym)) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001163 stream << "choice: ";
1164 expr_print(prop->expr, expr_print_help,
1165 &stream, E_NONE);
1166 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001167 }
1168 break;
Roman Zippel43bf6122006-06-08 22:12:45 -07001169 default:
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001170 stream << "unknown property: ";
1171 stream << prop_get_type_name(prop->type);
1172 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001173 }
1174 if (prop->visible.expr) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001175 stream << "&nbsp;&nbsp;&nbsp;&nbsp;dep: ";
1176 expr_print(prop->visible.expr, expr_print_help,
1177 &stream, E_NONE);
1178 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001179 }
1180 }
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001181 stream << "<br>";
Roman Zippel43bf6122006-06-08 22:12:45 -07001182
1183 return debug;
1184}
1185
1186QString ConfigInfoView::print_filter(const QString &str)
1187{
1188 QRegExp re("[<>&\"\\n]");
1189 QString res = str;
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001190 for (int i = 0; (i = res.indexOf(re, i)) >= 0;) {
1191 switch (res[i].toLatin1()) {
Roman Zippel43bf6122006-06-08 22:12:45 -07001192 case '<':
1193 res.replace(i, 1, "&lt;");
1194 i += 4;
1195 break;
1196 case '>':
1197 res.replace(i, 1, "&gt;");
1198 i += 4;
1199 break;
1200 case '&':
1201 res.replace(i, 1, "&amp;");
1202 i += 5;
1203 break;
1204 case '"':
1205 res.replace(i, 1, "&quot;");
1206 i += 6;
1207 break;
1208 case '\n':
1209 res.replace(i, 1, "<br>");
1210 i += 4;
1211 break;
1212 }
1213 }
1214 return res;
1215}
1216
Roman Zippelab45d192006-06-08 22:12:47 -07001217void ConfigInfoView::expr_print_help(void *data, struct symbol *sym, const char *str)
Roman Zippel43bf6122006-06-08 22:12:45 -07001218{
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001219 QTextStream *stream = reinterpret_cast<QTextStream *>(data);
Roman Zippelab45d192006-06-08 22:12:47 -07001220
1221 if (sym && sym->name && !(sym->flags & SYMBOL_CONST)) {
Masahiro Yamada510bc3cb2020-08-21 02:43:28 +09001222 *stream << "<a href=\"s" << sym->name << "\">";
1223 *stream << print_filter(str);
1224 *stream << "</a>";
1225 } else {
1226 *stream << print_filter(str);
1227 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001228}
1229
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001230void ConfigInfoView::clicked(const QUrl &url)
1231{
1232 QByteArray str = url.toEncoded();
1233 const std::size_t count = str.size();
1234 char *data = new char[count + 1];
1235 struct symbol **result;
1236 struct menu *m = NULL;
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001237
1238 if (count < 1) {
Masahiro Yamadac9b09a922020-07-30 02:02:39 +09001239 delete[] data;
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001240 return;
1241 }
1242
1243 memcpy(data, str.constData(), count);
1244 data[count] = '\0';
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001245
1246 /* Seek for exact match */
1247 data[0] = '^';
1248 strcat(data, "$");
1249 result = sym_re_search(data);
1250 if (!result) {
Masahiro Yamadac9b09a922020-07-30 02:02:39 +09001251 delete[] data;
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001252 return;
1253 }
1254
1255 sym = *result;
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001256
Mauro Carvalho Chehab8a3b6e52020-06-30 08:48:35 +02001257 /* Seek for the menu which holds the symbol */
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001258 for (struct property *prop = sym->prop; prop; prop = prop->next) {
1259 if (prop->type != P_PROMPT && prop->type != P_MENU)
1260 continue;
1261 m = prop->menu;
1262 break;
1263 }
1264
1265 if (!m) {
Mauro Carvalho Chehab8a3b6e52020-06-30 08:48:35 +02001266 /* Symbol is not visible as a menu */
1267 symbolInfo();
1268 emit showDebugChanged(true);
1269 } else {
1270 emit menuSelected(m);
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001271 }
1272
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001273 free(result);
Masahiro Yamadaa608b6a2020-09-09 07:16:37 +09001274 delete[] data;
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001275}
1276
Masahiro Yamada7d1300e2020-08-18 01:36:30 +09001277void ConfigInfoView::contextMenuEvent(QContextMenuEvent *event)
Roman Zippel7fc925f2006-06-08 22:12:46 -07001278{
Masahiro Yamada7d1300e2020-08-18 01:36:30 +09001279 contextMenu->popup(event->globalPos());
1280 event->accept();
Roman Zippel7fc925f2006-06-08 22:12:46 -07001281}
1282
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001283ConfigSearchWindow::ConfigSearchWindow(ConfigMainWindow *parent)
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001284 : Parent(parent), result(NULL)
Roman Zippel43bf6122006-06-08 22:12:45 -07001285{
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001286 setObjectName("search");
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001287 setWindowTitle("Search Config");
Roman Zippel43bf6122006-06-08 22:12:45 -07001288
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001289 QVBoxLayout* layout1 = new QVBoxLayout(this);
1290 layout1->setContentsMargins(11, 11, 11, 11);
1291 layout1->setSpacing(6);
Masahiro Yamada92641152020-08-07 18:18:58 +09001292
1293 QHBoxLayout* layout2 = new QHBoxLayout();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001294 layout2->setContentsMargins(0, 0, 0, 0);
1295 layout2->setSpacing(6);
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001296 layout2->addWidget(new QLabel("Find:", this));
Roman Zippel43bf6122006-06-08 22:12:45 -07001297 editField = new QLineEdit(this);
1298 connect(editField, SIGNAL(returnPressed()), SLOT(search()));
1299 layout2->addWidget(editField);
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001300 searchButton = new QPushButton("Search", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001301 searchButton->setAutoDefault(false);
Roman Zippel43bf6122006-06-08 22:12:45 -07001302 connect(searchButton, SIGNAL(clicked()), SLOT(search()));
1303 layout2->addWidget(searchButton);
1304 layout1->addLayout(layout2);
1305
Roman Zippel7fc925f2006-06-08 22:12:46 -07001306 split = new QSplitter(this);
Markus Heidelberg7298b932009-05-18 01:36:50 +02001307 split->setOrientation(Qt::Vertical);
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001308 list = new ConfigView(split, "search");
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001309 list->list->mode = listMode;
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001310 info = new ConfigInfoView(split, "search");
Roman Zippel43bf6122006-06-08 22:12:45 -07001311 connect(list->list, SIGNAL(menuChanged(struct menu *)),
1312 info, SLOT(setInfo(struct menu *)));
Marco Costalba63431e72006-10-05 19:12:59 +02001313 connect(list->list, SIGNAL(menuChanged(struct menu *)),
1314 parent, SLOT(setMenuLink(struct menu *)));
1315
Roman Zippel43bf6122006-06-08 22:12:45 -07001316 layout1->addWidget(split);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001317
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001318 QVariant x, y;
1319 int width, height;
1320 bool ok;
Roman Zippel7fc925f2006-06-08 22:12:46 -07001321
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001322 configSettings->beginGroup("search");
1323 width = configSettings->value("/window width", parent->width() / 2).toInt();
1324 height = configSettings->value("/window height", parent->height() / 2).toInt();
1325 resize(width, height);
1326 x = configSettings->value("/window x");
1327 y = configSettings->value("/window y");
1328 if (x.isValid() && y.isValid())
1329 move(x.toInt(), y.toInt());
1330 QList<int> sizes = configSettings->readSizes("/split", &ok);
1331 if (ok)
1332 split->setSizes(sizes);
1333 configSettings->endGroup();
1334 connect(configApp, SIGNAL(aboutToQuit()), SLOT(saveSettings()));
Roman Zippel7fc925f2006-06-08 22:12:46 -07001335}
1336
1337void ConfigSearchWindow::saveSettings(void)
1338{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001339 if (!objectName().isEmpty()) {
1340 configSettings->beginGroup(objectName());
1341 configSettings->setValue("/window x", pos().x());
1342 configSettings->setValue("/window y", pos().y());
1343 configSettings->setValue("/window width", size().width());
1344 configSettings->setValue("/window height", size().height());
1345 configSettings->writeSizes("/split", split->sizes());
1346 configSettings->endGroup();
1347 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001348}
1349
1350void ConfigSearchWindow::search(void)
1351{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001352 struct symbol **p;
1353 struct property *prop;
1354 ConfigItem *lastItem = NULL;
1355
1356 free(result);
1357 list->list->clear();
1358 info->clear();
1359
1360 result = sym_re_search(editField->text().toLatin1());
1361 if (!result)
1362 return;
1363 for (p = result; *p; p++) {
1364 for_all_prompts((*p), prop)
1365 lastItem = new ConfigItem(list->list, lastItem, prop->menu,
1366 menu_is_visible(prop->menu));
1367 }
Roman Zippel43bf6122006-06-08 22:12:45 -07001368}
1369
Linus Torvalds1da177e2005-04-16 15:20:36 -07001370/*
1371 * Construct the complete config widget
1372 */
1373ConfigMainWindow::ConfigMainWindow(void)
Roman Zippelf12aa702006-11-25 11:09:31 -08001374 : searchWindow(0)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001375{
Boris Barbulovski92119932015-09-22 11:36:16 -07001376 bool ok = true;
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001377 QVariant x, y;
1378 int width, height;
Randy Dunlapa54bb702007-10-20 11:18:47 -07001379 char title[256];
Linus Torvalds1da177e2005-04-16 15:20:36 -07001380
Markus Heidelberg8d90c972009-05-18 01:36:52 +02001381 QDesktopWidget *d = configApp->desktop();
Arnaud Lacombe09548282010-08-18 01:57:13 -04001382 snprintf(title, sizeof(title), "%s%s",
1383 rootmenu.prompt->text,
Michal Marek76a136c2010-09-01 17:39:27 +02001384 ""
Michal Marek76a136c2010-09-01 17:39:27 +02001385 );
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001386 setWindowTitle(title);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001387
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001388 width = configSettings->value("/window width", d->width() - 64).toInt();
1389 height = configSettings->value("/window height", d->height() - 64).toInt();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001390 resize(width, height);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001391 x = configSettings->value("/window x");
1392 y = configSettings->value("/window y");
1393 if ((x.isValid())&&(y.isValid()))
1394 move(x.toInt(), y.toInt());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001395
Masahiro Yamada5cb255f2020-08-07 18:19:07 +09001396 // set up icons
1397 ConfigItem::symbolYesIcon = QIcon(QPixmap(xpm_symbol_yes));
1398 ConfigItem::symbolModIcon = QIcon(QPixmap(xpm_symbol_mod));
1399 ConfigItem::symbolNoIcon = QIcon(QPixmap(xpm_symbol_no));
1400 ConfigItem::choiceYesIcon = QIcon(QPixmap(xpm_choice_yes));
1401 ConfigItem::choiceNoIcon = QIcon(QPixmap(xpm_choice_no));
1402 ConfigItem::menuIcon = QIcon(QPixmap(xpm_menu));
1403 ConfigItem::menubackIcon = QIcon(QPixmap(xpm_menuback));
1404
Mauro Carvalho Chehabcce1fab2020-04-02 11:28:00 +02001405 QWidget *widget = new QWidget(this);
1406 QVBoxLayout *layout = new QVBoxLayout(widget);
1407 setCentralWidget(widget);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001408
Mauro Carvalho Chehabcce1fab2020-04-02 11:28:00 +02001409 split1 = new QSplitter(widget);
1410 split1->setOrientation(Qt::Horizontal);
1411 split1->setChildrenCollapsible(false);
1412
1413 menuView = new ConfigView(widget, "menu");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001414 menuList = menuView->list;
1415
Mauro Carvalho Chehabcce1fab2020-04-02 11:28:00 +02001416 split2 = new QSplitter(widget);
1417 split2->setChildrenCollapsible(false);
Markus Heidelberg7298b932009-05-18 01:36:50 +02001418 split2->setOrientation(Qt::Vertical);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001419
1420 // create config tree
Mauro Carvalho Chehabcce1fab2020-04-02 11:28:00 +02001421 configView = new ConfigView(widget, "config");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001422 configList = configView->list;
1423
Mauro Carvalho Chehabcce1fab2020-04-02 11:28:00 +02001424 helpText = new ConfigInfoView(widget, "help");
1425
1426 layout->addWidget(split2);
1427 split2->addWidget(split1);
1428 split1->addWidget(configView);
1429 split1->addWidget(menuView);
1430 split2->addWidget(helpText);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001431
1432 setTabOrder(configList, helpText);
1433 configList->setFocus();
1434
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001435 backAction = new QAction(QPixmap(xpm_back), "Back", this);
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001436 connect(backAction, SIGNAL(triggered(bool)), SLOT(goBack()));
1437
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001438 QAction *quitAction = new QAction("&Quit", this);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001439 quitAction->setShortcut(Qt::CTRL + Qt::Key_Q);
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001440 connect(quitAction, SIGNAL(triggered(bool)), SLOT(close()));
1441
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001442 QAction *loadAction = new QAction(QPixmap(xpm_load), "&Load", this);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001443 loadAction->setShortcut(Qt::CTRL + Qt::Key_L);
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001444 connect(loadAction, SIGNAL(triggered(bool)), SLOT(loadConfig()));
1445
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001446 saveAction = new QAction(QPixmap(xpm_save), "&Save", this);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001447 saveAction->setShortcut(Qt::CTRL + Qt::Key_S);
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001448 connect(saveAction, SIGNAL(triggered(bool)), SLOT(saveConfig()));
1449
Karsten Wiese3b354c52006-12-13 00:34:08 -08001450 conf_set_changed_callback(conf_changed);
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001451
Karsten Wiese3b354c52006-12-13 00:34:08 -08001452 // Set saveAction's initial state
1453 conf_changed();
Masahiro Yamada87419082019-03-11 01:13:15 +09001454 configname = xstrdup(conf_get_configname());
1455
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001456 QAction *saveAsAction = new QAction("Save &As...", this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001457 connect(saveAsAction, SIGNAL(triggered(bool)), SLOT(saveConfigAs()));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001458 QAction *searchAction = new QAction("&Find", this);
Boris Barbulovski85eaf282015-09-22 11:36:03 -07001459 searchAction->setShortcut(Qt::CTRL + Qt::Key_F);
Boris Barbulovski92119932015-09-22 11:36:16 -07001460 connect(searchAction, SIGNAL(triggered(bool)), SLOT(searchConfig()));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001461 singleViewAction = new QAction(QPixmap(xpm_single_view), "Single View", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001462 singleViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001463 connect(singleViewAction, SIGNAL(triggered(bool)), SLOT(showSingleView()));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001464 splitViewAction = new QAction(QPixmap(xpm_split_view), "Split View", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001465 splitViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001466 connect(splitViewAction, SIGNAL(triggered(bool)), SLOT(showSplitView()));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001467 fullViewAction = new QAction(QPixmap(xpm_tree_view), "Full View", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001468 fullViewAction->setCheckable(true);
Boris Barbulovski92119932015-09-22 11:36:16 -07001469 connect(fullViewAction, SIGNAL(triggered(bool)), SLOT(showFullView()));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001470
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001471 QAction *showNameAction = new QAction("Show Name", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001472 showNameAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001473 connect(showNameAction, SIGNAL(toggled(bool)), configView, SLOT(setShowName(bool)));
Boris Barbulovski9c862352015-09-22 11:36:12 -07001474 showNameAction->setChecked(configView->showName());
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001475 QAction *showRangeAction = new QAction("Show Range", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001476 showRangeAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001477 connect(showRangeAction, SIGNAL(toggled(bool)), configView, SLOT(setShowRange(bool)));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001478 QAction *showDataAction = new QAction("Show Data", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001479 showDataAction->setCheckable(true);
Roman Zippel7fc925f2006-06-08 22:12:46 -07001480 connect(showDataAction, SIGNAL(toggled(bool)), configView, SLOT(setShowData(bool)));
Li Zefan39a48972010-05-10 16:33:41 +08001481
1482 QActionGroup *optGroup = new QActionGroup(this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001483 optGroup->setExclusive(true);
Masahiro Yamadad4bbe8a2020-08-07 18:19:09 +09001484 connect(optGroup, SIGNAL(triggered(QAction*)), configList,
Li Zefan39a48972010-05-10 16:33:41 +08001485 SLOT(setOptionMode(QAction *)));
Masahiro Yamadad4bbe8a2020-08-07 18:19:09 +09001486 connect(optGroup, SIGNAL(triggered(QAction *)), menuList,
Li Zefan39a48972010-05-10 16:33:41 +08001487 SLOT(setOptionMode(QAction *)));
1488
Masahiro Yamadad4bbe8a2020-08-07 18:19:09 +09001489 ConfigList::showNormalAction = new QAction("Show Normal Options", optGroup);
1490 ConfigList::showNormalAction->setCheckable(true);
1491 ConfigList::showAllAction = new QAction("Show All Options", optGroup);
1492 ConfigList::showAllAction->setCheckable(true);
1493 ConfigList::showPromptAction = new QAction("Show Prompt Options", optGroup);
1494 ConfigList::showPromptAction->setCheckable(true);
Li Zefan39a48972010-05-10 16:33:41 +08001495
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001496 QAction *showDebugAction = new QAction("Show Debug Info", this);
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001497 showDebugAction->setCheckable(true);
Roman Zippel43bf6122006-06-08 22:12:45 -07001498 connect(showDebugAction, SIGNAL(toggled(bool)), helpText, SLOT(setShowDebug(bool)));
Boris Barbulovski9c862352015-09-22 11:36:12 -07001499 showDebugAction->setChecked(helpText->showDebug());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001500
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001501 QAction *showIntroAction = new QAction("Introduction", this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001502 connect(showIntroAction, SIGNAL(triggered(bool)), SLOT(showIntro()));
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001503 QAction *showAboutAction = new QAction("About", this);
Boris Barbulovski92119932015-09-22 11:36:16 -07001504 connect(showAboutAction, SIGNAL(triggered(bool)), SLOT(showAbout()));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001505
1506 // init tool bar
Masahiro Yamada860ec3f2020-08-07 18:18:55 +09001507 QToolBar *toolBar = addToolBar("Tools");
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001508 toolBar->addAction(backAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001509 toolBar->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001510 toolBar->addAction(loadAction);
1511 toolBar->addAction(saveAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001512 toolBar->addSeparator();
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001513 toolBar->addAction(singleViewAction);
1514 toolBar->addAction(splitViewAction);
1515 toolBar->addAction(fullViewAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001516
Masahiro Yamada93ebaac2020-08-07 18:18:53 +09001517 // create file menu
1518 QMenu *menu = menuBar()->addMenu("&File");
1519 menu->addAction(loadAction);
1520 menu->addAction(saveAction);
1521 menu->addAction(saveAsAction);
1522 menu->addSeparator();
1523 menu->addAction(quitAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001524
Shlomi Fish66e7c722007-02-14 00:32:58 -08001525 // create edit menu
Masahiro Yamada93ebaac2020-08-07 18:18:53 +09001526 menu = menuBar()->addMenu("&Edit");
1527 menu->addAction(searchAction);
Shlomi Fish66e7c722007-02-14 00:32:58 -08001528
Linus Torvalds1da177e2005-04-16 15:20:36 -07001529 // create options menu
Masahiro Yamada93ebaac2020-08-07 18:18:53 +09001530 menu = menuBar()->addMenu("&Option");
1531 menu->addAction(showNameAction);
1532 menu->addAction(showRangeAction);
1533 menu->addAction(showDataAction);
1534 menu->addSeparator();
1535 menu->addActions(optGroup->actions());
1536 menu->addSeparator();
1537 menu->addAction(showDebugAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001538
1539 // create help menu
Masahiro Yamada93ebaac2020-08-07 18:18:53 +09001540 menu = menuBar()->addMenu("&Help");
1541 menu->addAction(showIntroAction);
1542 menu->addAction(showAboutAction);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001543
Mauro Carvalho Chehabc4f73982020-06-30 08:26:37 +02001544 connect (helpText, SIGNAL (anchorClicked (const QUrl &)),
1545 helpText, SLOT (clicked (const QUrl &)) );
1546
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001547 connect(configList, SIGNAL(menuChanged(struct menu *)),
1548 helpText, SLOT(setInfo(struct menu *)));
1549 connect(configList, SIGNAL(menuSelected(struct menu *)),
1550 SLOT(changeMenu(struct menu *)));
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001551 connect(configList, SIGNAL(itemSelected(struct menu *)),
1552 SLOT(changeItens(struct menu *)));
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001553 connect(configList, SIGNAL(parentSelected()),
1554 SLOT(goBack()));
1555 connect(menuList, SIGNAL(menuChanged(struct menu *)),
1556 helpText, SLOT(setInfo(struct menu *)));
1557 connect(menuList, SIGNAL(menuSelected(struct menu *)),
1558 SLOT(changeMenu(struct menu *)));
1559
1560 connect(configList, SIGNAL(gotFocus(struct menu *)),
1561 helpText, SLOT(setInfo(struct menu *)));
1562 connect(menuList, SIGNAL(gotFocus(struct menu *)),
1563 helpText, SLOT(setInfo(struct menu *)));
1564 connect(menuList, SIGNAL(gotFocus(struct menu *)),
1565 SLOT(listFocusChanged(void)));
Roman Zippelb65a47e2006-06-08 22:12:47 -07001566 connect(helpText, SIGNAL(menuSelected(struct menu *)),
1567 SLOT(setMenuLink(struct menu *)));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001568
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001569 QString listMode = configSettings->value("/listMode", "symbol").toString();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001570 if (listMode == "single")
1571 showSingleView();
1572 else if (listMode == "full")
1573 showFullView();
1574 else /*if (listMode == "split")*/
1575 showSplitView();
1576
1577 // UI setup done, restore splitter positions
Boris Barbulovski041fbdc2015-09-22 11:36:05 -07001578 QList<int> sizes = configSettings->readSizes("/split1", &ok);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001579 if (ok)
1580 split1->setSizes(sizes);
1581
Roman Zippel7fc925f2006-06-08 22:12:46 -07001582 sizes = configSettings->readSizes("/split2", &ok);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001583 if (ok)
1584 split2->setSizes(sizes);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001585}
1586
Linus Torvalds1da177e2005-04-16 15:20:36 -07001587void ConfigMainWindow::loadConfig(void)
1588{
Masahiro Yamada87419082019-03-11 01:13:15 +09001589 QString str;
1590 QByteArray ba;
1591 const char *name;
1592
1593 str = QFileDialog::getOpenFileName(this, "", configname);
1594 if (str.isNull())
Linus Torvalds1da177e2005-04-16 15:20:36 -07001595 return;
Masahiro Yamada87419082019-03-11 01:13:15 +09001596
1597 ba = str.toLocal8Bit();
1598 name = ba.data();
1599
1600 if (conf_read(name))
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001601 QMessageBox::information(this, "qconf", "Unable to load configuration!");
Masahiro Yamada87419082019-03-11 01:13:15 +09001602
1603 free(configname);
1604 configname = xstrdup(name);
1605
Masahiro Yamadaf9b918f2020-08-29 17:14:10 +09001606 ConfigList::updateListAllForAll();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001607}
1608
Michal Marekbac6aa82011-05-25 15:10:25 +02001609bool ConfigMainWindow::saveConfig(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001610{
Masahiro Yamada87419082019-03-11 01:13:15 +09001611 if (conf_write(configname)) {
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001612 QMessageBox::information(this, "qconf", "Unable to save configuration!");
Michal Marekbac6aa82011-05-25 15:10:25 +02001613 return false;
1614 }
Masahiro Yamada00c864f2018-07-20 16:46:31 +09001615 conf_write_autoconf(0);
1616
Michal Marekbac6aa82011-05-25 15:10:25 +02001617 return true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001618}
1619
1620void ConfigMainWindow::saveConfigAs(void)
1621{
Masahiro Yamada87419082019-03-11 01:13:15 +09001622 QString str;
1623 QByteArray ba;
1624 const char *name;
1625
1626 str = QFileDialog::getSaveFileName(this, "", configname);
1627 if (str.isNull())
Linus Torvalds1da177e2005-04-16 15:20:36 -07001628 return;
Masahiro Yamada87419082019-03-11 01:13:15 +09001629
1630 ba = str.toLocal8Bit();
1631 name = ba.data();
1632
1633 if (conf_write(name)) {
1634 QMessageBox::information(this, "qconf", "Unable to save configuration!");
1635 }
1636 conf_write_autoconf(0);
1637
1638 free(configname);
1639 configname = xstrdup(name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001640}
1641
Roman Zippel43bf6122006-06-08 22:12:45 -07001642void ConfigMainWindow::searchConfig(void)
1643{
1644 if (!searchWindow)
Masahiro Yamada740fdef2020-08-07 18:18:57 +09001645 searchWindow = new ConfigSearchWindow(this);
Roman Zippel43bf6122006-06-08 22:12:45 -07001646 searchWindow->show();
1647}
1648
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001649void ConfigMainWindow::changeItens(struct menu *menu)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001650{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001651 configList->setRootMenu(menu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001652}
1653
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001654void ConfigMainWindow::changeMenu(struct menu *menu)
1655{
1656 menuList->setRootMenu(menu);
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001657}
1658
Roman Zippelb65a47e2006-06-08 22:12:47 -07001659void ConfigMainWindow::setMenuLink(struct menu *menu)
1660{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001661 struct menu *parent;
1662 ConfigList* list = NULL;
1663 ConfigItem* item;
1664
1665 if (configList->menuSkip(menu))
1666 return;
1667
1668 switch (configList->mode) {
1669 case singleMode:
1670 list = configList;
1671 parent = menu_get_parent_menu(menu);
1672 if (!parent)
1673 return;
1674 list->setRootMenu(parent);
1675 break;
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001676 case menuMode:
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001677 if (menu->flags & MENU_ROOT) {
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001678 menuList->setRootMenu(menu);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001679 configList->clearSelection();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001680 list = configList;
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001681 } else {
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001682 parent = menu_get_parent_menu(menu->parent);
1683 if (!parent)
1684 return;
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001685
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001686 /* Select the config view */
1687 item = configList->findConfigItem(parent);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001688 if (item) {
Mauro Carvalho Chehabb06c3ec2020-06-30 08:26:38 +02001689 configList->setSelected(item, true);
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001690 configList->scrollToItem(item);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001691 }
Mauro Carvalho Chehabc699eaa2020-06-30 08:26:36 +02001692
1693 menuList->setRootMenu(parent);
1694 menuList->clearSelection();
1695 list = menuList;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001696 }
1697 break;
1698 case fullMode:
1699 list = configList;
1700 break;
1701 default:
1702 break;
1703 }
1704
1705 if (list) {
1706 item = list->findConfigItem(menu);
1707 if (item) {
Mauro Carvalho Chehabb06c3ec2020-06-30 08:26:38 +02001708 list->setSelected(item, true);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001709 list->scrollToItem(item);
1710 list->setFocus();
Mauro Carvalho Chehab8a3b6e52020-06-30 08:48:35 +02001711 helpText->setInfo(menu);
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001712 }
1713 }
Roman Zippelb65a47e2006-06-08 22:12:47 -07001714}
1715
Linus Torvalds1da177e2005-04-16 15:20:36 -07001716void ConfigMainWindow::listFocusChanged(void)
1717{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001718 if (menuList->mode == menuMode)
1719 configList->clearSelection();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001720}
1721
1722void ConfigMainWindow::goBack(void)
1723{
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001724 if (configList->rootEntry == &rootmenu)
Boris Barbulovskibe596aa2015-09-22 11:36:28 -07001725 return;
1726
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001727 configList->setParentMenu();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001728}
1729
1730void ConfigMainWindow::showSingleView(void)
1731{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001732 singleViewAction->setEnabled(false);
1733 singleViewAction->setChecked(true);
1734 splitViewAction->setEnabled(true);
1735 splitViewAction->setChecked(false);
1736 fullViewAction->setEnabled(true);
1737 fullViewAction->setChecked(false);
1738
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001739 backAction->setEnabled(true);
1740
Linus Torvalds1da177e2005-04-16 15:20:36 -07001741 menuView->hide();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001742 menuList->setRootMenu(0);
1743 configList->mode = singleMode;
1744 if (configList->rootEntry == &rootmenu)
1745 configList->updateListAll();
1746 else
1747 configList->setRootMenu(&rootmenu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001748 configList->setFocus();
1749}
1750
1751void ConfigMainWindow::showSplitView(void)
1752{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001753 singleViewAction->setEnabled(true);
1754 singleViewAction->setChecked(false);
1755 splitViewAction->setEnabled(false);
1756 splitViewAction->setChecked(true);
1757 fullViewAction->setEnabled(true);
1758 fullViewAction->setChecked(false);
1759
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001760 backAction->setEnabled(false);
1761
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001762 configList->mode = menuMode;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001763 if (configList->rootEntry == &rootmenu)
1764 configList->updateListAll();
1765 else
1766 configList->setRootMenu(&rootmenu);
1767 configList->setAllOpen(true);
1768 configApp->processEvents();
Mauro Carvalho Chehabb3111422020-04-02 11:28:01 +02001769 menuList->mode = symbolMode;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001770 menuList->setRootMenu(&rootmenu);
1771 menuList->setAllOpen(true);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001772 menuView->show();
1773 menuList->setFocus();
1774}
1775
1776void ConfigMainWindow::showFullView(void)
1777{
Boris Barbulovski780505e2015-09-22 11:36:13 -07001778 singleViewAction->setEnabled(true);
1779 singleViewAction->setChecked(false);
1780 splitViewAction->setEnabled(true);
1781 splitViewAction->setChecked(false);
1782 fullViewAction->setEnabled(false);
1783 fullViewAction->setChecked(true);
1784
Mauro Carvalho Chehabaf737b4d2020-06-30 08:26:39 +02001785 backAction->setEnabled(false);
1786
Linus Torvalds1da177e2005-04-16 15:20:36 -07001787 menuView->hide();
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001788 menuList->setRootMenu(0);
1789 configList->mode = fullMode;
1790 if (configList->rootEntry == &rootmenu)
1791 configList->updateListAll();
1792 else
1793 configList->setRootMenu(&rootmenu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001794 configList->setFocus();
1795}
1796
Linus Torvalds1da177e2005-04-16 15:20:36 -07001797/*
1798 * ask for saving configuration before quitting
Linus Torvalds1da177e2005-04-16 15:20:36 -07001799 */
1800void ConfigMainWindow::closeEvent(QCloseEvent* e)
1801{
Karsten Wieseb3214292006-12-13 00:34:06 -08001802 if (!conf_get_changed()) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001803 e->accept();
1804 return;
1805 }
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001806 QMessageBox mb("qconf", "Save configuration?", QMessageBox::Warning,
Linus Torvalds1da177e2005-04-16 15:20:36 -07001807 QMessageBox::Yes | QMessageBox::Default, QMessageBox::No, QMessageBox::Cancel | QMessageBox::Escape);
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001808 mb.setButtonText(QMessageBox::Yes, "&Save Changes");
1809 mb.setButtonText(QMessageBox::No, "&Discard Changes");
1810 mb.setButtonText(QMessageBox::Cancel, "Cancel Exit");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001811 switch (mb.exec()) {
1812 case QMessageBox::Yes:
Michal Marekbac6aa82011-05-25 15:10:25 +02001813 if (saveConfig())
1814 e->accept();
1815 else
1816 e->ignore();
1817 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001818 case QMessageBox::No:
1819 e->accept();
1820 break;
1821 case QMessageBox::Cancel:
1822 e->ignore();
1823 break;
1824 }
1825}
1826
1827void ConfigMainWindow::showIntro(void)
1828{
Masahiro Yamada8c30e7e2020-08-29 17:14:07 +09001829 static const QString str =
1830 "Welcome to the qconf graphical configuration tool.\n"
1831 "\n"
1832 "For each option, a blank box indicates the feature is "
1833 "disabled, a check indicates it is enabled, and a dot "
1834 "indicates that it is to be compiled as a module. Clicking on "
1835 "the box will cycle through the three states.\n"
1836 "\n"
1837 "If you do not see an option (e.g., a device driver) that you "
1838 "believe should be present, try turning on Show All Options "
Masahiro Yamada1fb75242020-08-29 17:14:08 +09001839 "under the Options menu. Enabling Show Debug Info will help you"
1840 "figure out what other options must be enabled to support the "
1841 "option you are interested in, and hyperlinks will navigate to "
1842 "them.\n"
Masahiro Yamada8c30e7e2020-08-29 17:14:07 +09001843 "\n"
1844 "Toggling Show Debug Info under the Options menu will show the "
1845 "dependencies, which you can then match by examining other "
1846 "options.\n";
Linus Torvalds1da177e2005-04-16 15:20:36 -07001847
1848 QMessageBox::information(this, "qconf", str);
1849}
1850
1851void ConfigMainWindow::showAbout(void)
1852{
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001853 static const QString str = "qconf is Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>.\n"
Boris Barbulovskib4ff1de2015-09-22 11:36:38 -07001854 "Copyright (C) 2015 Boris Barbulovski <bbarbulovski@gmail.com>.\n\n"
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001855 "Bug reports and feature request can also be entered at http://bugzilla.kernel.org/\n";
Linus Torvalds1da177e2005-04-16 15:20:36 -07001856
1857 QMessageBox::information(this, "qconf", str);
1858}
1859
1860void ConfigMainWindow::saveSettings(void)
1861{
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001862 configSettings->setValue("/window x", pos().x());
1863 configSettings->setValue("/window y", pos().y());
1864 configSettings->setValue("/window width", size().width());
1865 configSettings->setValue("/window height", size().height());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001866
1867 QString entry;
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001868 switch(configList->mode) {
1869 case singleMode :
1870 entry = "single";
1871 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001872
Boris Barbulovskid5d973c2015-09-22 11:36:19 -07001873 case symbolMode :
1874 entry = "split";
1875 break;
1876
1877 case fullMode :
1878 entry = "full";
1879 break;
1880
1881 default:
1882 break;
1883 }
Boris Barbulovski68ccb7e2015-09-22 11:36:15 -07001884 configSettings->setValue("/listMode", entry);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001885
Roman Zippel7fc925f2006-06-08 22:12:46 -07001886 configSettings->writeSizes("/split1", split1->sizes());
1887 configSettings->writeSizes("/split2", split2->sizes());
Linus Torvalds1da177e2005-04-16 15:20:36 -07001888}
1889
Karsten Wiese3b354c52006-12-13 00:34:08 -08001890void ConfigMainWindow::conf_changed(void)
1891{
1892 if (saveAction)
1893 saveAction->setEnabled(conf_get_changed());
1894}
1895
Linus Torvalds1da177e2005-04-16 15:20:36 -07001896void fixup_rootmenu(struct menu *menu)
1897{
1898 struct menu *child;
1899 static int menu_cnt = 0;
1900
1901 menu->flags |= MENU_ROOT;
1902 for (child = menu->list; child; child = child->next) {
1903 if (child->prompt && child->prompt->type == P_MENU) {
1904 menu_cnt++;
1905 fixup_rootmenu(child);
1906 menu_cnt--;
1907 } else if (!menu_cnt)
1908 fixup_rootmenu(child);
1909 }
1910}
1911
1912static const char *progname;
1913
1914static void usage(void)
1915{
Sam Ravnborg694c49a2018-05-22 21:36:12 +02001916 printf("%s [-s] <config>\n", progname);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001917 exit(0);
1918}
1919
1920int main(int ac, char** av)
1921{
1922 ConfigMainWindow* v;
1923 const char *name;
1924
Linus Torvalds1da177e2005-04-16 15:20:36 -07001925 progname = av[0];
1926 configApp = new QApplication(ac, av);
1927 if (ac > 1 && av[1][0] == '-') {
1928 switch (av[1][1]) {
Michal Marek0a1f00a2015-04-08 13:30:42 +02001929 case 's':
1930 conf_set_message_callback(NULL);
1931 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001932 case 'h':
1933 case '?':
1934 usage();
1935 }
1936 name = av[2];
1937 } else
1938 name = av[1];
1939 if (!name)
1940 usage();
1941
1942 conf_parse(name);
1943 fixup_rootmenu(&rootmenu);
1944 conf_read(NULL);
1945 //zconfdump(stdout);
1946
Roman Zippel7fc925f2006-06-08 22:12:46 -07001947 configSettings = new ConfigSettings();
1948 configSettings->beginGroup("/kconfig/qconf");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001949 v = new ConfigMainWindow();
1950
1951 //zconfdump(stdout);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001952 configApp->connect(configApp, SIGNAL(lastWindowClosed()), SLOT(quit()));
1953 configApp->connect(configApp, SIGNAL(aboutToQuit()), v, SLOT(saveSettings()));
Roman Zippel43bf6122006-06-08 22:12:45 -07001954 v->show();
Linus Torvalds1da177e2005-04-16 15:20:36 -07001955 configApp->exec();
1956
Roman Zippel7fc925f2006-06-08 22:12:46 -07001957 configSettings->endGroup();
1958 delete configSettings;
Chris Bainbridge5b61c7b2016-01-08 20:44:04 +00001959 delete v;
1960 delete configApp;
Roman Zippel7fc925f2006-06-08 22:12:46 -07001961
Linus Torvalds1da177e2005-04-16 15:20:36 -07001962 return 0;
1963}