1 /* wireshark_preference.cpp
2  *
3  * Wireshark - Network traffic analyzer
4  * By Gerald Combs <gerald@wireshark.org>
5  * Copyright 1998 Gerald Combs
6  *
7  * SPDX-License-Identifier: GPL-2.0-or-later
8  */
9 
10 #include "config.h"
11 
12 #include <epan/prefs.h>
13 #include <epan/prefs-int.h>
14 
15 #include <ui/qt/manager/wireshark_preference.h>
16 #include <ui/qt/manager/preference_manager.h>
17 #include <ui/qt/widgets/range_syntax_lineedit.h>
18 #include "ui/qt/widgets/wireshark_file_dialog.h"
19 #include <ui/qt/wireshark_application.h>
20 #include <ui/qt/uat_dialog.h>
21 
22 #include <QDir>
23 #include <QLineEdit>
24 #include <QComboBox>
25 #include <QColorDialog>
26 
WiresharkPreference(QObject * parent)27 WiresharkPreference::WiresharkPreference(QObject * parent) : QObject(parent), _prefsItem(NULL)
28 {}
29 
editor(QWidget *,const QStyleOptionViewItem &,const QModelIndex &)30 QWidget * WiresharkPreference::editor(QWidget * /*parent*/, const QStyleOptionViewItem &/*option*/, const QModelIndex &/*index*/)
31 {
32     return Q_NULLPTR;
33 }
34 
setData(QWidget *,const QModelIndex &)35 void WiresharkPreference::setData(QWidget * /*editor*/, const QModelIndex &/*index*/) {}
setModelData(QWidget *,QAbstractItemModel *,const QModelIndex &)36 void WiresharkPreference::setModelData(QWidget * /*editor*/, QAbstractItemModel * /*model*/, const QModelIndex &/*index*/) {}
37 
setPrefsItem(PrefsItem * item)38 void WiresharkPreference::setPrefsItem(PrefsItem * item)
39 {
40     _prefsItem = item;
41 }
42 
prefsItem() const43 PrefsItem * WiresharkPreference::prefsItem() const
44 {
45     return _prefsItem;
46 }
47 
48 class BoolPreference : public WiresharkPreference
49 {
50 public:
BoolPreference(QObject * parent=Q_NULLPTR)51     BoolPreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem & option,const QModelIndex & index)52     virtual QWidget * editor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index)
53     {
54         const_cast<QAbstractItemModel*>(index.model())->setData(index, QString("BOOL"), Qt::EditRole);
55         return WiresharkPreference::editor(parent, option, index);
56     }
57 };
58 REGISTER_PREFERENCE_TYPE(PREF_BOOL, BoolPreference)
59 
60 class StringPreference : public WiresharkPreference
61 {
62 public:
StringPreference(QObject * parent=Q_NULLPTR)63     StringPreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem &,const QModelIndex &)64     virtual QWidget * editor(QWidget *parent, const QStyleOptionViewItem &/*option*/, const QModelIndex &/*index*/)
65     {
66         return new QLineEdit(parent);
67     }
68 
setData(QWidget * editor,const QModelIndex & index)69     virtual void setData(QWidget *editor, const QModelIndex &index)
70     {
71         QLineEdit* line = static_cast<QLineEdit*>(editor);
72         line->setText(index.model()->data(index, Qt::DisplayRole).toString());
73     }
74 
setModelData(QWidget * editor,QAbstractItemModel * model,const QModelIndex & index)75     virtual void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index)
76     {
77         QLineEdit* line = static_cast<QLineEdit*>(editor);
78         model->setData(index, line->text(), Qt::EditRole);
79     }
80 };
81 REGISTER_PREFERENCE_TYPE(PREF_STRING, StringPreference)
82 REGISTER_PREFERENCE_TYPE(PREF_CUSTOM, StringPreference)
83 
84 class UIntPreference : public StringPreference
85 {
86 public:
UIntPreference(QObject * parent=Q_NULLPTR)87     UIntPreference(QObject * parent = Q_NULLPTR) : StringPreference(parent) {}
88 };
89 REGISTER_PREFERENCE_TYPE(PREF_UINT, UIntPreference)
90 REGISTER_PREFERENCE_TYPE(PREF_DECODE_AS_UINT, UIntPreference)
91 
92 class EnumPreference : public WiresharkPreference
93 {
94 public:
EnumPreference(QObject * parent=Q_NULLPTR)95     EnumPreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem &,const QModelIndex &)96     virtual QWidget * editor(QWidget *parent, const QStyleOptionViewItem &/*option*/, const QModelIndex &/*index*/)
97     {
98         return new QComboBox(parent);
99     }
100 
setData(QWidget * editor,const QModelIndex & index)101     virtual void setData(QWidget *editor, const QModelIndex &index)
102     {
103         QComboBox* combo = static_cast<QComboBox*>(editor);
104         const enum_val_t *ev;
105         PrefsItem* pref = VariantPointer<PrefsItem>::asPtr(index.model()->data(index, Qt::UserRole));
106         for (ev = prefs_get_enumvals(pref->getPref()); ev && ev->description; ev++) {
107             combo->addItem(ev->description, QVariant(ev->value));
108             if (prefs_get_enum_value(pref->getPref(), pref_stashed) == ev->value)
109                 combo->setCurrentIndex(combo->count() - 1);
110         }
111     }
112 
setModelData(QWidget * editor,QAbstractItemModel * model,const QModelIndex & index)113     virtual void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index)
114     {
115         QComboBox* combo = static_cast<QComboBox*>(editor);
116         model->setData(index, combo->itemData(combo->currentIndex()), Qt::EditRole);
117     }
118 };
119 REGISTER_PREFERENCE_TYPE(PREF_ENUM, EnumPreference)
120 
121 class RangePreference : public WiresharkPreference
122 {
123 public:
RangePreference(QObject * parent=Q_NULLPTR)124     RangePreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem &,const QModelIndex &)125     virtual QWidget * editor(QWidget *parent, const QStyleOptionViewItem &/*option*/, const QModelIndex &/*index*/)
126     {
127         return new RangeSyntaxLineEdit(parent);
128     }
129 
setData(QWidget * editor,const QModelIndex & index)130     virtual void setData(QWidget *editor, const QModelIndex &index)
131     {
132         RangeSyntaxLineEdit* syntax = static_cast<RangeSyntaxLineEdit*>(editor);
133         syntax->setText(index.model()->data(index, Qt::DisplayRole).toString());
134     }
135 
setModelData(QWidget * editor,QAbstractItemModel * model,const QModelIndex & index)136     virtual void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index)
137     {
138         RangeSyntaxLineEdit* syntax = static_cast<RangeSyntaxLineEdit*>(editor);
139         model->setData(index, syntax->text(), Qt::EditRole);
140     }
141 };
142 REGISTER_PREFERENCE_TYPE(PREF_RANGE, RangePreference)
143 REGISTER_PREFERENCE_TYPE(PREF_DECODE_AS_RANGE, RangePreference)
144 
145 class ColorPreference : public WiresharkPreference
146 {
147 public:
ColorPreference(QObject * parent=Q_NULLPTR)148     ColorPreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem &,const QModelIndex &)149     virtual QWidget * editor(QWidget * parent, const QStyleOptionViewItem &/*option*/, const QModelIndex &/*index*/)
150     {
151         QColorDialog* color_dlg = new QColorDialog(parent);
152         color_dlg->setWindowModality(Qt::ApplicationModal);
153         color_dlg->show();
154         return color_dlg;
155     }
156 
setData(QWidget * editor,const QModelIndex & index)157     virtual void setData(QWidget *editor, const QModelIndex &index)
158     {
159         QColorDialog* color_dlg = static_cast<QColorDialog*>(editor);
160         QColor color = QColor("#" + index.model()->data(index, Qt::DisplayRole).toString());
161         color_dlg->setCurrentColor(color);
162     }
163 
setModelData(QWidget * editor,QAbstractItemModel * model,const QModelIndex & index)164     virtual void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index)
165     {
166         QColorDialog* color_dlg = static_cast<QColorDialog*>(editor);
167         if (color_dlg->result() == QDialog::Accepted) {
168             model->setData(index, color_dlg->currentColor().name(), Qt::EditRole);
169         }
170     }
171 };
172 REGISTER_PREFERENCE_TYPE(PREF_COLOR, ColorPreference)
173 
174 class SaveFilePreference : public WiresharkPreference
175 {
176 public:
SaveFilePreference(QObject * parent=Q_NULLPTR)177     SaveFilePreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem & option,const QModelIndex & index)178     virtual QWidget * editor(QWidget * parent, const QStyleOptionViewItem &option, const QModelIndex &index)
179     {
180         QString filename = WiresharkFileDialog::getSaveFileName(parent, wsApp->windowTitleString(prefs_get_title(prefsItem()->getPref())),
181                                                     index.model()->data(index, Qt::DisplayRole).toString());
182         if (!filename.isEmpty()) {
183             const_cast<QAbstractItemModel*>(index.model())->setData(index, QDir::toNativeSeparators(filename), Qt::EditRole);
184         }
185         return WiresharkPreference::editor(parent, option, index);
186     }
187 };
188 REGISTER_PREFERENCE_TYPE(PREF_SAVE_FILENAME, SaveFilePreference)
189 
190 class OpenFilePreference : public WiresharkPreference
191 {
192 public:
OpenFilePreference(QObject * parent=Q_NULLPTR)193     OpenFilePreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem & option,const QModelIndex & index)194     virtual QWidget * editor(QWidget * parent, const QStyleOptionViewItem &option, const QModelIndex &index)
195     {
196         QString filename = WiresharkFileDialog::getOpenFileName(parent, wsApp->windowTitleString(prefs_get_title(prefsItem()->getPref())),
197                                                         index.model()->data(index, Qt::DisplayRole).toString());
198         if (!filename.isEmpty()) {
199             const_cast<QAbstractItemModel*>(index.model())->setData(index, QDir::toNativeSeparators(filename), Qt::EditRole);
200         }
201         return WiresharkPreference::editor(parent, option, index);
202     }
203 };
204 REGISTER_PREFERENCE_TYPE(PREF_OPEN_FILENAME, OpenFilePreference)
205 
206 class DirNamePreference : public WiresharkPreference
207 {
208 public:
DirNamePreference(QObject * parent=Q_NULLPTR)209     DirNamePreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem & option,const QModelIndex & index)210     virtual QWidget * editor(QWidget * parent, const QStyleOptionViewItem &option, const QModelIndex &index)
211     {
212         QString filename = WiresharkFileDialog::getExistingDirectory(parent, wsApp->windowTitleString(prefs_get_title(prefsItem()->getPref())),
213                                                     index.model()->data(index, Qt::DisplayRole).toString());
214         if (!filename.isEmpty()) {
215             const_cast<QAbstractItemModel*>(index.model())->setData(index, QDir::toNativeSeparators(filename), Qt::EditRole);
216         }
217         return WiresharkPreference::editor(parent, option, index);
218     }
219 };
220 REGISTER_PREFERENCE_TYPE(PREF_DIRNAME, DirNamePreference)
221 
222 class UatPreference : public WiresharkPreference
223 {
224 public:
UatPreference(QObject * parent=Q_NULLPTR)225     UatPreference(QObject * parent = Q_NULLPTR) : WiresharkPreference(parent) {}
editor(QWidget * parent,const QStyleOptionViewItem & option,const QModelIndex & index)226     virtual QWidget * editor(QWidget * parent, const QStyleOptionViewItem &option, const QModelIndex &index)
227     {
228         if (prefsItem()->getPrefGUIType() == GUI_ALL || prefsItem()->getPrefGUIType() == GUI_QT) {
229             UatDialog uat_dlg(parent, prefs_get_uat_value(prefsItem()->getPref()));
230             uat_dlg.exec();
231         }
232         return WiresharkPreference::editor(parent, option, index);
233     }
234 };
235 REGISTER_PREFERENCE_TYPE(PREF_UAT, UatPreference)
236