- Timestamp:
- Jun 14, 2022 12:06:41 PM (3 years ago)
- Location:
- trunk/src/VBox/Frontends/VirtualBox
- Files:
-
- 4 edited
- 2 copied
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Frontends/VirtualBox/Makefile.kmk
r95247 r95277 935 935 src/settings/editors/UIUSBControllerEditor.h \ 936 936 src/settings/editors/UIUSBFilterDetailsEditor.h \ 937 src/settings/editors/UIUSBFiltersEditor.h \ 937 938 src/settings/editors/UIVideoMemoryEditor.h \ 938 939 src/settings/editors/UIVirtualCPUEditor.h \ … … 1091 1092 src/settings/editors/UISharedFoldersEditor.cpp \ 1092 1093 src/settings/editors/UIShortcutConfigurationEditor.cpp \ 1094 src/settings/editors/UIUSBFiltersEditor.cpp \ 1093 1095 src/settings/machine/UIMachineSettingsNetwork.cpp \ 1094 1096 src/settings/machine/UIMachineSettingsSerial.cpp \ 1095 1097 src/settings/machine/UIMachineSettingsStorage.cpp \ 1096 src/settings/machine/UIMachineSettingsUSB.cpp \1097 1098 src/widgets/UIAddDiskEncryptionPasswordDialog.cpp \ 1098 1099 src/widgets/UIFilmContainer.cpp \ … … 1513 1514 src/settings/editors/UIUSBControllerEditor.cpp \ 1514 1515 src/settings/editors/UIUSBFilterDetailsEditor.cpp \ 1516 src/settings/editors/UIUSBFiltersEditor.cpp \ 1515 1517 src/settings/editors/UIVideoMemoryEditor.cpp \ 1516 1518 src/settings/editors/UIVirtualCPUEditor.cpp \ -
trunk/src/VBox/Frontends/VirtualBox/src/settings/editors/UISharedFoldersEditor.cpp
r95129 r95277 269 269 : QIWithRetranslateUI<QWidget>(pParent) 270 270 , m_pLabelSeparator(0) 271 , m_pLayoutTree(0) 271 272 , m_pTreeWidget(0) 273 , m_pToolbar(0) 274 , m_pActionAdd(0) 275 , m_pActionEdit(0) 276 , m_pActionRemove(0) 272 277 { 273 278 prepare(); … … 363 368 m_pActionAdd->setText(tr("Add Shared Folder")); 364 369 m_pActionAdd->setToolTip(tr("Adds new shared folder.")); 365 m_pActionAdd->setToolTip(m_pActionAdd->whatsThis());366 370 } 367 371 if (m_pActionEdit) … … 369 373 m_pActionEdit->setText(tr("Edit Shared Folder")); 370 374 m_pActionEdit->setToolTip(tr("Edits selected shared folder.")); 371 m_pActionEdit->setToolTip(m_pActionEdit->whatsThis());372 375 } 373 376 if (m_pActionRemove) … … 375 378 m_pActionRemove->setText(tr("Remove Shared Folder")); 376 379 m_pActionRemove->setToolTip(tr("Removes selected shared folder.")); 377 m_pActionRemove->setToolTip(m_pActionRemove->whatsThis());378 380 } 379 381 } -
trunk/src/VBox/Frontends/VirtualBox/src/settings/editors/UIUSBFiltersEditor.cpp
r95276 r95277 1 1 /* $Id$ */ 2 2 /** @file 3 * VBox Qt GUI - UI SharedFoldersEditor class implementation.3 * VBox Qt GUI - UIUSBFiltersEditor class implementation. 4 4 */ 5 5 … … 20 20 #include <QMenu> 21 21 #include <QRegExp> 22 #include <QT imer>22 #include <QToolTip> 23 23 #include <QVBoxLayout> 24 24 … … 27 27 #include "QIToolBar.h" 28 28 #include "QITreeWidget.h" 29 #include "UICommon.h" 29 30 #include "UIIconPool.h" 30 #include "UISharedFolderDetailsEditor.h" 31 #include "UISharedFoldersEditor.h" 32 #include "VBoxUtils.h" 31 #include "UIUSBFilterDetailsEditor.h" 32 #include "UIUSBFiltersEditor.h" 33 34 /* COM includes: */ 35 #include "CConsole.h" 36 #include "CHostUSBDevice.h" 37 #include "CUSBDevice.h" 33 38 34 39 /* Other VBox includes: */ 35 40 #include "iprt/assert.h" 36 41 37 38 /** Shared Folder tree-widget item. */ 39 class SFTreeViewItem : public QITreeWidgetItem, public UIDataSharedFolder 42 /* VirtualBox interface declarations: */ 43 #include <VBox/com/VirtualBox.h> 44 45 46 /** USB Filter tree-widget item. */ 47 class USBFilterTreeWidgetItem : public QITreeWidgetItem, public UIDataUSBFilter 40 48 { 41 49 Q_OBJECT; … … 43 51 public: 44 52 45 /** Format type. */ 46 enum FormatType 47 { 48 FormatType_Invalid, 49 FormatType_EllipsisStart, 50 FormatType_EllipsisMiddle, 51 FormatType_EllipsisEnd, 52 FormatType_EllipsisFile 53 }; 54 55 /** Constructs shared folder type (root) item. 56 * @param pParent Brings the item parent. 57 * @param enmFormat Brings the item format type. */ 58 SFTreeViewItem(QITreeWidget *pParent, FormatType enmFormat); 59 /** Constructs shared folder (child) item. 60 * @param pParent Brings the item parent. 61 * @param enmFormat Brings the item format type. */ 62 SFTreeViewItem(SFTreeViewItem *pParent, FormatType enmFormat); 63 64 /** Returns whether this item is less than the @a other one. */ 65 bool operator<(const QTreeWidgetItem &other) const; 66 67 /** Returns child item number @a iIndex. */ 68 SFTreeViewItem *child(int iIndex) const; 69 70 /** Returns text of item number @a iIndex. */ 71 QString getText(int iIndex) const; 53 /** Constructs USB filter type (root) item. */ 54 USBFilterTreeWidgetItem(QITreeWidget *pParent) : QITreeWidgetItem(pParent) {} 72 55 73 56 /** Updates item fields. */ 74 57 void updateFields(); 75 58 76 /** Adjusts item layout. */77 void adjustText();78 79 59 protected: 80 60 81 61 /** Returns default text. */ 82 62 virtual QString defaultText() const RT_OVERRIDE; 63 }; 64 65 66 /** USB Filter popup menu. */ 67 class UIUSBMenu : public QMenu 68 { 69 Q_OBJECT; 70 71 public: 72 73 /** Constructs USB Filter menu passing @a pParent to the base-class. */ 74 UIUSBMenu(QWidget *pParent); 75 76 /** Returns USB device related to passed action. */ 77 const CUSBDevice& getUSB(QAction *pAction); 78 79 /** Defines @a comConsole. */ 80 void setConsole(const CConsole &comConsole); 81 82 protected: 83 84 /** Handles any @a pEvent handler. */ 85 virtual bool event(QEvent *pEvent) RT_OVERRIDE; 86 87 private slots: 88 89 /** Prepares menu contents. */ 90 void processAboutToShow(); 83 91 84 92 private: 85 93 86 /** Performs item @a iColumn processing. */ 87 void processColumn(int iColumn); 88 89 /** Holds the item format type. */ 90 FormatType m_enmFormat; 91 /** Holds the item text fields. */ 92 QStringList m_fields; 94 /** Holds the USB device map. */ 95 QMap<QAction*, CUSBDevice> m_usbDeviceMap; 96 97 /** Holds the console. */ 98 CConsole m_comConsole; 93 99 }; 94 100 95 101 96 102 /********************************************************************************************************************************* 97 * Class SFTreeViewItem implementation.*103 * Class USBFilterTreeWidgetItem implementation. * 98 104 *********************************************************************************************************************************/ 99 105 100 SFTreeViewItem::SFTreeViewItem(QITreeWidget *pParent, FormatType enmFormat) 101 : QITreeWidgetItem(pParent) 102 , m_enmFormat(enmFormat) 103 { 104 setFirstColumnSpanned(true); 105 setFlags(flags() ^ Qt::ItemIsSelectable); 106 } 107 108 SFTreeViewItem::SFTreeViewItem(SFTreeViewItem *pParent, FormatType enmFormat) 109 : QITreeWidgetItem(pParent) 110 , m_enmFormat(enmFormat) 111 { 112 } 113 114 bool SFTreeViewItem::operator<(const QTreeWidgetItem &other) const 115 { 116 /* Root items should always been sorted by type field: */ 117 return parentItem() ? text(0) < other.text(0) : 118 text(1) < other.text(1); 119 } 120 121 SFTreeViewItem *SFTreeViewItem::child(int iIndex) const 122 { 123 QTreeWidgetItem *pItem = QTreeWidgetItem::child(iIndex); 124 return pItem ? static_cast<SFTreeViewItem*>(pItem) : 0; 125 } 126 127 QString SFTreeViewItem::getText(int iIndex) const 128 { 129 return iIndex >= 0 && iIndex < m_fields.size() ? m_fields.at(iIndex) : QString(); 130 } 131 132 void SFTreeViewItem::updateFields() 133 { 134 /* Clear fields: */ 135 m_fields.clear(); 136 137 /* For root items: */ 138 if (!parentItem()) 139 m_fields << m_strName 140 << QString::number((int)m_enmType); 141 /* For child items: */ 106 void USBFilterTreeWidgetItem::updateFields() 107 { 108 setText(0, m_strName); 109 } 110 111 QString USBFilterTreeWidgetItem::defaultText() const 112 { 113 return checkState(0) == Qt::Checked 114 ? tr("%1, Active", "col.1 text, col.1 state").arg(text(0)) 115 : tr("%1", "col.1 text") .arg(text(0)); 116 } 117 118 119 /********************************************************************************************************************************* 120 * Class UIUSBMenu implementation. * 121 *********************************************************************************************************************************/ 122 123 UIUSBMenu::UIUSBMenu(QWidget *) 124 { 125 connect(this, &UIUSBMenu::aboutToShow, 126 this, &UIUSBMenu::processAboutToShow); 127 } 128 129 const CUSBDevice &UIUSBMenu::getUSB(QAction *pAction) 130 { 131 return m_usbDeviceMap[pAction]; 132 } 133 134 void UIUSBMenu::setConsole(const CConsole &comConsole) 135 { 136 m_comConsole = comConsole; 137 } 138 139 bool UIUSBMenu::event(QEvent *pEvent) 140 { 141 /* We provide dynamic tooltips for the usb devices: */ 142 if (pEvent->type() == QEvent::ToolTip) 143 { 144 QHelpEvent *pHelpEvent = static_cast<QHelpEvent*>(pEvent); 145 QAction *pAction = actionAt(pHelpEvent->pos()); 146 if (pAction) 147 { 148 CUSBDevice usb = m_usbDeviceMap[pAction]; 149 if (!usb.isNull()) 150 { 151 QToolTip::showText(pHelpEvent->globalPos(), uiCommon().usbToolTip(usb)); 152 return true; 153 } 154 } 155 } 156 /* Call to base-class: */ 157 return QMenu::event(pEvent); 158 } 159 160 void UIUSBMenu::processAboutToShow() 161 { 162 /* Clear lists initially: */ 163 clear(); 164 m_usbDeviceMap.clear(); 165 166 /* Get host for further activities: */ 167 CHost comHost = uiCommon().host(); 168 169 /* Check whether we have host USB devices at all: */ 170 bool fIsUSBEmpty = comHost.GetUSBDevices().size() == 0; 171 if (fIsUSBEmpty) 172 { 173 /* Empty action for no USB device case: */ 174 QAction *pAction = addAction(tr("<no devices available>", "USB devices")); 175 pAction->setEnabled(false); 176 pAction->setToolTip(tr("No supported devices connected to the host PC", "USB device tooltip")); 177 } 142 178 else 143 m_fields << m_strName 144 << m_strPath 145 << (m_fWritable ? tr("Full") : tr("Read-only")) 146 << (m_fAutoMount ? tr("Yes") : "") 147 << m_strAutoMountPoint; 148 149 /* Adjust item layout: */ 150 adjustText(); 151 } 152 153 void SFTreeViewItem::adjustText() 154 { 155 for (int i = 0; i < treeWidget()->columnCount(); ++i) 156 processColumn(i); 157 } 158 159 QString SFTreeViewItem::defaultText() const 160 { 161 return parentItem() 162 ? tr("%1, %2: %3, %4: %5, %6: %7, %8: %9", 163 "col.1 text, col.2 name: col.2 text, col.3 name: col.3 text, col.4 name: col.4 text, col.5 name: col.5 text") 164 .arg(text(0)) 165 .arg(parentTree()->headerItem()->text(1)).arg(text(1)) 166 .arg(parentTree()->headerItem()->text(2)).arg(text(2)) 167 .arg(parentTree()->headerItem()->text(3)).arg(text(3)) 168 .arg(parentTree()->headerItem()->text(4)).arg(text(4)) 169 : text(0); 170 } 171 172 void SFTreeViewItem::processColumn(int iColumn) 173 { 174 QString strOneString = getText(iColumn); 175 if (strOneString.isNull()) 176 return; 177 const QFontMetrics fm = treeWidget()->fontMetrics(); 178 #if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0) 179 const int iOldSize = fm.horizontalAdvance(strOneString); 180 #else 181 const int iOldSize = fm.width(strOneString); 182 #endif 183 const int iItemIndent = parentItem() ? treeWidget()->indentation() * 2 : treeWidget()->indentation(); 184 #if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0) 185 int iIndentSize = fm.horizontalAdvance(" ... "); 186 #else 187 int iIndentSize = fm.width(" ... "); 188 #endif 189 if (iColumn == 0) 190 iIndentSize += iItemIndent; 191 const int cWidth = !parentItem() ? treeWidget()->viewport()->width() : treeWidget()->columnWidth(iColumn); 192 193 /* Compress text: */ 194 int iStart = 0; 195 int iFinish = 0; 196 int iPosition = 0; 197 int iTextWidth = 0; 198 do 199 { 200 #if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0) 201 iTextWidth = fm.horizontalAdvance(strOneString); 202 #else 203 iTextWidth = fm.width(strOneString); 204 #endif 205 if ( iTextWidth 206 && iTextWidth + iIndentSize > cWidth) 179 { 180 /* Action per each host USB device: */ 181 foreach (const CHostUSBDevice &comHostUsb, comHost.GetUSBDevices()) 207 182 { 208 iStart = 0; 209 iFinish = strOneString.length(); 210 211 /* Selecting remove position: */ 212 switch (m_enmFormat) 183 CUSBDevice comUsb(comHostUsb); 184 QAction *pAction = addAction(uiCommon().usbDetails(comUsb)); 185 pAction->setCheckable(true); 186 m_usbDeviceMap[pAction] = comUsb; 187 /* Check if created item was already attached to this session: */ 188 if (!m_comConsole.isNull()) 213 189 { 214 case FormatType_EllipsisStart: 215 iPosition = iStart; 216 break; 217 case FormatType_EllipsisMiddle: 218 iPosition = (iFinish - iStart) / 2; 219 break; 220 case FormatType_EllipsisEnd: 221 iPosition = iFinish - 1; 222 break; 223 case FormatType_EllipsisFile: 224 { 225 const QRegExp regExp("([\\\\/][^\\\\^/]+[\\\\/]?$)"); 226 const int iNewFinish = regExp.indexIn(strOneString); 227 if (iNewFinish != -1) 228 iFinish = iNewFinish; 229 iPosition = (iFinish - iStart) / 2; 230 break; 231 } 232 default: 233 AssertMsgFailed(("Invalid format type\n")); 190 CUSBDevice attachedUSB = m_comConsole.FindUSBDeviceById(comUsb.GetId()); 191 pAction->setChecked(!attachedUSB.isNull()); 192 pAction->setEnabled(comHostUsb.GetState() != KUSBDeviceState_Unavailable); 234 193 } 235 236 if (iPosition == iFinish)237 break;238 239 strOneString.remove(iPosition, 1);240 194 } 241 195 } 242 while ( iTextWidth243 && (iTextWidth + iIndentSize > cWidth));244 245 if (iPosition || m_enmFormat == FormatType_EllipsisFile)246 strOneString.insert(iPosition, "...");247 #if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0)248 const int iNewSize = fm.horizontalAdvance(strOneString);249 #else250 const int iNewSize = fm.width(strOneString);251 #endif252 setText(iColumn, iNewSize < iOldSize ? strOneString : m_fields.at(iColumn));253 setToolTip(iColumn, text(iColumn) == getText(iColumn) ? QString() : getText(iColumn));254 255 /* Calculate item's size-hint: */256 #if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0)257 setSizeHint(iColumn, QSize(fm.horizontalAdvance(QString(" %1 ").arg(getText(iColumn))), fm.height()));258 #else259 setSizeHint(iColumn, QSize(fm.width(QString(" %1 ").arg(getText(iColumn))), fm.height()));260 #endif261 196 } 262 197 263 198 264 199 /********************************************************************************************************************************* 265 * Class UI SharedFoldersEditor implementation.*200 * Class UIUSBFiltersEditor implementation. * 266 201 *********************************************************************************************************************************/ 267 202 268 UI SharedFoldersEditor::UISharedFoldersEditor(QWidget *pParent /* = 0 */)203 UIUSBFiltersEditor::UIUSBFiltersEditor(QWidget *pParent /* = 0 */) 269 204 : QIWithRetranslateUI<QWidget>(pParent) 270 205 , m_pLabelSeparator(0) 206 , m_pLayoutTree(0) 271 207 , m_pTreeWidget(0) 208 , m_pToolbar(0) 209 , m_pActionNew(0) 210 , m_pActionAdd(0) 211 , m_pActionEdit(0) 212 , m_pActionRemove(0) 213 , m_pActionMoveUp(0) 214 , m_pActionMoveDown(0) 215 , m_pMenuUSBDevices(0) 272 216 { 273 217 prepare(); 274 218 } 275 219 276 void UI SharedFoldersEditor::setValue(const QList<UIDataSharedFolder> &guiValue)220 void UIUSBFiltersEditor::setValue(const QList<UIDataUSBFilter> &guiValue) 277 221 { 278 222 /* Update cached value and … … 285 229 } 286 230 287 QList<UIData SharedFolder> UISharedFoldersEditor::value() const231 QList<UIDataUSBFilter> UIUSBFiltersEditor::value() const 288 232 { 289 233 /* Sanity check: */ … … 292 236 293 237 /* Prepare result: */ 294 QList<UIData SharedFolder> result;295 296 /* For each f older type: */238 QList<UIDataUSBFilter> result; 239 240 /* For each filter: */ 297 241 QTreeWidgetItem *pMainRootItem = m_pTreeWidget->invisibleRootItem(); 298 for (int iFolderTypeIndex = 0; iFolderTypeIndex < pMainRootItem->childCount(); ++iFolderTypeIndex) 299 { 300 /* Get folder root item: */ 301 const SFTreeViewItem *pFolderTypeRoot = static_cast<SFTreeViewItem*>(pMainRootItem->child(iFolderTypeIndex)); 302 303 /* For each folder of current type: */ 304 for (int iFolderIndex = 0; iFolderIndex < pFolderTypeRoot->childCount(); ++iFolderIndex) 305 { 306 /* Gather and cache new data: */ 307 const SFTreeViewItem *pItem = static_cast<SFTreeViewItem*>(pFolderTypeRoot->child(iFolderIndex)); 308 result << *pItem; 309 } 242 for (int iFilterIndex = 0; iFilterIndex < pMainRootItem->childCount(); ++iFilterIndex) 243 { 244 /* Gather and cache new data: */ 245 const USBFilterTreeWidgetItem *pItem = static_cast<USBFilterTreeWidgetItem*>(pMainRootItem->child(iFilterIndex)); 246 result << *pItem; 310 247 } 311 248 … … 314 251 } 315 252 316 void UISharedFoldersEditor::setFeatureAvailable(bool fAvailable) 317 { 318 if (m_pLabelSeparator) 319 m_pLabelSeparator->setEnabled(fAvailable); 320 if (m_pTreeWidget) 321 m_pTreeWidget->setEnabled(fAvailable); 322 if (m_pToolbar) 323 m_pToolbar->setEnabled(fAvailable); 324 } 325 326 void UISharedFoldersEditor::setFoldersAvailable(UISharedFolderType enmType, bool fAvailable) 327 { 328 m_foldersAvailable[enmType] = fAvailable; 329 updateRootItemsVisibility(); 330 } 331 332 void UISharedFoldersEditor::retranslateUi() 333 { 253 void UIUSBFiltersEditor::retranslateUi() 254 { 255 /* Tags: */ 256 m_strTrUSBFilterName = tr("New Filter %1", "usb"); 257 334 258 /* Translate separator label: */ 335 259 if (m_pLabelSeparator) 336 m_pLabelSeparator->setText(tr(" Shared &Folders"));260 m_pLabelSeparator->setText(tr("USB Device &Filters")); 337 261 338 262 /* Translate tree-widget: */ 339 263 if (m_pTreeWidget) 340 { 341 m_pTreeWidget->setWhatsThis(tr("Lists all shared folders accessible to this machine. Use 'net use x: \\\\vboxsvr\\share' " 342 "to access a shared folder named <i>share</i> from a DOS-like OS, or 'mount -t vboxsf " 343 "share mount_point' to access it from a Linux OS. This feature requires Guest Additions.")); 344 345 /* Translate tree-widget header: */ 346 QTreeWidgetItem *pTreeWidgetHeaderItem = m_pTreeWidget->headerItem(); 347 if (pTreeWidgetHeaderItem) 348 { 349 pTreeWidgetHeaderItem->setText(4, tr("At")); 350 pTreeWidgetHeaderItem->setText(3, tr("Auto Mount")); 351 pTreeWidgetHeaderItem->setText(2, tr("Access")); 352 pTreeWidgetHeaderItem->setText(1, tr("Path")); 353 pTreeWidgetHeaderItem->setText(0, tr("Name")); 354 } 355 356 /* Update tree-widget contents finally: */ 357 reloadTree(); 358 } 264 m_pTreeWidget->setWhatsThis(tr("Lists all USB filters of this machine. The checkbox to the left defines whether the " 265 "particular filter is enabled or not. Use the context menu or buttons to the right to " 266 "add or remove USB filters.")); 359 267 360 268 /* Translate actions: */ 269 if (m_pActionNew) 270 { 271 m_pActionNew->setText(tr("Add Empty Filter")); 272 m_pActionNew->setToolTip(tr("Adds new USB filter with all fields initially set to empty strings. " 273 "Note that such a filter will match any attached USB device.")); 274 } 361 275 if (m_pActionAdd) 362 276 { 363 m_pActionAdd->setText(tr("Add Shared Folder"));364 m_pActionAdd->setToolTip(tr("Adds new shared folder."));365 m_pActionAdd->setToolTip(m_pActionAdd->whatsThis());277 m_pActionAdd->setText(tr("Add Filter From Device")); 278 m_pActionAdd->setToolTip(tr("Adds new USB filter with all fields set to the values of the " 279 "selected USB device attached to the host PC.")); 366 280 } 367 281 if (m_pActionEdit) 368 282 { 369 m_pActionEdit->setText(tr("Edit Shared Folder")); 370 m_pActionEdit->setToolTip(tr("Edits selected shared folder.")); 371 m_pActionEdit->setToolTip(m_pActionEdit->whatsThis()); 283 m_pActionEdit->setText(tr("Edit Filter")); 284 m_pActionEdit->setToolTip(tr("Edits selected USB filter.")); 372 285 } 373 286 if (m_pActionRemove) 374 287 { 375 m_pActionRemove->setText(tr("Remove Shared Folder")); 376 m_pActionRemove->setToolTip(tr("Removes selected shared folder.")); 377 m_pActionRemove->setToolTip(m_pActionRemove->whatsThis()); 378 } 379 } 380 381 void UISharedFoldersEditor::showEvent(QShowEvent *pEvent) 382 { 383 /* Call to base-class: */ 384 QIWithRetranslateUI<QWidget>::showEvent(pEvent); 385 386 /* Connect header-resize signal just before widget is shown 387 * after all the items properly loaded and initialized: */ 388 connect(m_pTreeWidget->header(), &QHeaderView::sectionResized, 389 this, &UISharedFoldersEditor::sltAdjustTreeFields, 390 Qt::UniqueConnection); 391 392 /* Adjusting size after all pending show events are processed: */ 393 QTimer::singleShot(0, this, SLOT(sltAdjustTree())); 394 } 395 396 void UISharedFoldersEditor::resizeEvent(QResizeEvent * /* pEvent */) 397 { 398 sltAdjustTree(); 399 } 400 401 void UISharedFoldersEditor::sltAdjustTree() 402 { 403 /* 404 * Calculates required columns sizes to max out column 2 405 * and let all other columns stay at their minimum sizes. 406 * 407 * Columns 408 * 0 = Tree view / name 409 * 1 = Path 410 * 2 = Writable flag 411 * 3 = Auto-mount flag 412 * 4 = Auto mount point 413 */ 414 QAbstractItemView *pItemView = m_pTreeWidget; 415 QHeaderView *pItemHeader = m_pTreeWidget->header(); 416 const int iTotal = m_pTreeWidget->viewport()->width(); 417 418 const int mw0 = qMax(pItemView->sizeHintForColumn(0), pItemHeader->sectionSizeHint(0)); 419 const int mw2 = qMax(pItemView->sizeHintForColumn(2), pItemHeader->sectionSizeHint(2)); 420 const int mw3 = qMax(pItemView->sizeHintForColumn(3), pItemHeader->sectionSizeHint(3)); 421 const int mw4 = qMax(pItemView->sizeHintForColumn(4), pItemHeader->sectionSizeHint(4)); 422 #if 0 /** @todo Neither approach is perfect. Short folder names, short paths, plenty of white space, but there is often '...' in column 0. */ 423 424 const int w0 = mw0 < iTotal / 5 ? mw0 : iTotal / 5; 425 const int w2 = mw2 < iTotal / 5 ? mw2 : iTotal / 5; 426 const int w3 = mw3 < iTotal / 5 ? mw3 : iTotal / 5; 427 const int w4 = mw4 < iTotal / 5 ? mw4 : iTotal / 5; 428 429 /* Giving 1st column all the available space. */ 430 const int w1 = iTotal - w0 - w2 - w3 - w4; 431 #else 432 const int mw1 = qMax(pItemView->sizeHintForColumn(1), pItemHeader->sectionSizeHint(1)); 433 const int iHintTotal = mw0 + mw1 + mw2 + mw3 + mw4; 434 int w0, w1, w2, w3, w4; 435 int cExcess = iTotal - iHintTotal; 436 if (cExcess >= 0) 437 { 438 /* give excess width to column 1 (path) */ 439 w0 = mw0; 440 w1 = mw1 + cExcess; 441 w2 = mw2; 442 w3 = mw3; 443 w4 = mw4; 444 } 445 else 446 { 447 w0 = mw0 < iTotal / 5 ? mw0 : iTotal / 5; 448 w2 = mw2 < iTotal / 5 ? mw2 : iTotal / 5; 449 w3 = mw3 < iTotal / 5 ? mw3 : iTotal / 5; 450 w4 = mw4 < iTotal / 5 ? mw4 : iTotal / 5; 451 w1 = iTotal - w0 - w2 - w3 - w4; 452 } 453 #endif 454 m_pTreeWidget->setColumnWidth(0, w0); 455 m_pTreeWidget->setColumnWidth(1, w1); 456 m_pTreeWidget->setColumnWidth(2, w2); 457 m_pTreeWidget->setColumnWidth(3, w3); 458 m_pTreeWidget->setColumnWidth(4, w4); 459 } 460 461 void UISharedFoldersEditor::sltAdjustTreeFields() 462 { 463 QTreeWidgetItem *pMainRoot = m_pTreeWidget->invisibleRootItem(); 464 for (int i = 0; i < pMainRoot->childCount(); ++i) 465 { 466 SFTreeViewItem *pSubRoot = static_cast<SFTreeViewItem*>(pMainRoot->child(i)); 467 pSubRoot->adjustText(); 468 for (int j = 0; j < pSubRoot->childCount(); ++j) 469 { 470 SFTreeViewItem *pItem = static_cast<SFTreeViewItem*>(pSubRoot->child(j)); 471 pItem->adjustText(); 472 } 473 } 474 } 475 476 void UISharedFoldersEditor::sltHandleCurrentItemChange(QTreeWidgetItem *pCurrentItem) 477 { 478 if (pCurrentItem && pCurrentItem->parent() && !pCurrentItem->isSelected()) 288 m_pActionRemove->setText(tr("Remove Filter")); 289 m_pActionRemove->setToolTip(tr("Removes selected USB filter.")); 290 } 291 if (m_pActionMoveUp) 292 { 293 m_pActionMoveUp->setText(tr("Move Filter Up")); 294 m_pActionMoveUp->setToolTip(tr("Moves selected USB filter up.")); 295 } 296 if (m_pActionMoveDown) 297 { 298 m_pActionMoveDown->setText(tr("Move Filter Down")); 299 m_pActionMoveDown->setToolTip(tr("Moves selected USB filter down.")); 300 } 301 } 302 303 void UIUSBFiltersEditor::sltHandleCurrentItemChange(QTreeWidgetItem *pCurrentItem) 304 { 305 if (pCurrentItem && !pCurrentItem->isSelected()) 479 306 pCurrentItem->setSelected(true); 480 const bool fAddEnabled = pCurrentItem; 481 const bool fRemoveEnabled = fAddEnabled && pCurrentItem->parent(); 482 m_pActionAdd->setEnabled(fAddEnabled); 483 m_pActionEdit->setEnabled(fRemoveEnabled); 484 m_pActionRemove->setEnabled(fRemoveEnabled); 485 } 486 487 void UISharedFoldersEditor::sltHandleDoubleClick(QTreeWidgetItem *pItem) 488 { 489 const bool fEditEnabled = pItem && pItem->parent(); 490 if (fEditEnabled) 491 sltEditFolder(); 492 } 493 494 void UISharedFoldersEditor::sltHandleContextMenuRequest(const QPoint &position) 307 m_pActionEdit->setEnabled(pCurrentItem); 308 m_pActionRemove->setEnabled(pCurrentItem); 309 m_pActionMoveUp->setEnabled(pCurrentItem && m_pTreeWidget->itemAbove(pCurrentItem)); 310 m_pActionMoveDown->setEnabled(pCurrentItem && m_pTreeWidget->itemBelow(pCurrentItem)); 311 } 312 313 void UIUSBFiltersEditor::sltHandleDoubleClick(QTreeWidgetItem *pItem) 314 { 315 AssertPtrReturnVoid(pItem); 316 sltEditFilter(); 317 } 318 319 void UIUSBFiltersEditor::sltHandleContextMenuRequest(const QPoint &position) 495 320 { 496 321 QMenu menu; … … 500 325 menu.addAction(m_pActionEdit); 501 326 menu.addAction(m_pActionRemove); 327 menu.addSeparator(); 328 menu.addAction(m_pActionMoveUp); 329 menu.addAction(m_pActionMoveDown); 502 330 } 503 331 else 504 332 { 333 menu.addAction(m_pActionNew); 505 334 menu.addAction(m_pActionAdd); 506 335 } … … 509 338 } 510 339 511 void UISharedFoldersEditor::sltAddFolder() 512 { 513 /* Configure shared folder details editor: */ 514 UISharedFolderDetailsEditor dlgFolderDetails(UISharedFolderDetailsEditor::EditorType_Add, 515 m_foldersAvailable.value(UISharedFolderType_Console), 516 usedList(true), 517 this); 518 519 /* Run folder details dialog: */ 340 void UIUSBFiltersEditor::sltCreateFilter() 341 { 342 /* Search for the max available filter index: */ 343 int iMaxFilterIndex = 0; 344 const QRegExp regExp(QString("^") + m_strTrUSBFilterName.arg("([0-9]+)") + QString("$")); 345 QTreeWidgetItemIterator iterator(m_pTreeWidget); 346 while (*iterator) 347 { 348 const QString filterName = (*iterator)->text(0); 349 const int pos = regExp.indexIn(filterName); 350 if (pos != -1) 351 iMaxFilterIndex = regExp.cap(1).toInt() > iMaxFilterIndex ? 352 regExp.cap(1).toInt() : iMaxFilterIndex; 353 ++iterator; 354 } 355 356 /* Prepare new data: */ 357 UIDataUSBFilter newFilterData; 358 newFilterData.m_fActive = true; 359 newFilterData.m_strName = m_strTrUSBFilterName.arg(iMaxFilterIndex + 1); 360 361 /* Add new filter item: */ 362 addUSBFilterItem(newFilterData, true /* its new? */); 363 364 /* Notify listeners: */ 365 emit sigValueChanged(); 366 } 367 368 void UIUSBFiltersEditor::sltAddFilter() 369 { 370 m_pMenuUSBDevices->exec(QCursor::pos()); 371 } 372 373 void UIUSBFiltersEditor::sltAddFilterConfirmed(QAction *pAction) 374 { 375 /* Get USB device: */ 376 const CUSBDevice comUsb = m_pMenuUSBDevices->getUSB(pAction); 377 if (comUsb.isNull()) 378 return; 379 380 /* Prepare new USB filter data: */ 381 UIDataUSBFilter newFilterData; 382 newFilterData.m_fActive = true; 383 newFilterData.m_strName = uiCommon().usbDetails(comUsb); 384 newFilterData.m_strVendorId = QString::number(comUsb.GetVendorId(), 16).toUpper().rightJustified(4, '0'); 385 newFilterData.m_strProductId = QString::number(comUsb.GetProductId(), 16).toUpper().rightJustified(4, '0'); 386 newFilterData.m_strRevision = QString::number(comUsb.GetRevision(), 16).toUpper().rightJustified(4, '0'); 387 /* The port property depends on the host computer rather than on the USB 388 * device itself; for this reason only a few people will want to use it 389 * in the filter since the same device plugged into a different socket 390 * will not match the filter in this case. */ 391 #if 0 392 newFilterData.m_strPort = QString().sprintf("%04hX", comUsb.GetPort()); 393 #endif 394 newFilterData.m_strManufacturer = comUsb.GetManufacturer(); 395 newFilterData.m_strProduct = comUsb.GetProduct(); 396 newFilterData.m_strSerialNumber = comUsb.GetSerialNumber(); 397 newFilterData.m_enmRemoteMode = comUsb.GetRemote() ? UIRemoteMode_On : UIRemoteMode_Off; 398 399 /* Add new USB filter item: */ 400 addUSBFilterItem(newFilterData, true /* its new? */); 401 402 /* Notify listeners: */ 403 emit sigValueChanged(); 404 } 405 406 void UIUSBFiltersEditor::sltEditFilter() 407 { 408 /* Check current filter item: */ 409 USBFilterTreeWidgetItem *pItem = static_cast<USBFilterTreeWidgetItem*>(m_pTreeWidget->currentItem()); 410 AssertPtrReturnVoid(pItem); 411 412 /* Configure USB filter details editor: */ 413 UIUSBFilterDetailsEditor dlgFolderDetails(this); /// @todo convey usedList! 414 dlgFolderDetails.setName(pItem->m_strName); 415 dlgFolderDetails.setVendorID(pItem->m_strVendorId); 416 dlgFolderDetails.setProductID(pItem->m_strProductId); 417 dlgFolderDetails.setRevision(pItem->m_strRevision); 418 dlgFolderDetails.setManufacturer(pItem->m_strManufacturer); 419 dlgFolderDetails.setProduct(pItem->m_strProduct); 420 dlgFolderDetails.setSerialNo(pItem->m_strSerialNumber); 421 dlgFolderDetails.setPort(pItem->m_strPort); 422 dlgFolderDetails.setRemoteMode(pItem->m_enmRemoteMode); 423 424 /* Run filter details dialog: */ 520 425 if (dlgFolderDetails.exec() == QDialog::Accepted) 521 426 { 522 const QString strName = dlgFolderDetails.name();523 const QString strPath = dlgFolderDetails.path();524 const UISharedFolderType enmType = dlgFolderDetails.isPermanent() ? UISharedFolderType_Machine : UISharedFolderType_Console;525 /* Shared folder's name & path could not be empty: */526 Assert(!strName.isEmpty() && !strPath.isEmpty());527 528 427 /* Prepare new data: */ 529 UIDataSharedFolder newFolderData; 530 newFolderData.m_enmType = enmType; 531 newFolderData.m_strName = strName; 532 newFolderData.m_strPath = strPath; 533 newFolderData.m_fWritable = dlgFolderDetails.isWriteable(); 534 newFolderData.m_fAutoMount = dlgFolderDetails.isAutoMounted(); 535 newFolderData.m_strAutoMountPoint = dlgFolderDetails.autoMountPoint(); 536 537 /* Add new folder item: */ 538 addSharedFolderItem(newFolderData, true /* its new? */); 539 540 /* Sort tree-widget before adjusting: */ 541 m_pTreeWidget->sortItems(0, Qt::AscendingOrder); 542 /* Adjust tree-widget finally: */ 543 sltAdjustTree(); 544 } 545 } 546 547 void UISharedFoldersEditor::sltEditFolder() 548 { 549 /* Check current folder item: */ 550 SFTreeViewItem *pItem = static_cast<SFTreeViewItem*>(m_pTreeWidget->currentItem()); 551 AssertPtrReturnVoid(pItem); 552 AssertPtrReturnVoid(pItem->parentItem()); 553 554 /* Configure shared folder details editor: */ 555 UISharedFolderDetailsEditor dlgFolderDetails(UISharedFolderDetailsEditor::EditorType_Edit, 556 m_foldersAvailable.value(UISharedFolderType_Console), 557 usedList(false), 558 this); 559 dlgFolderDetails.setPath(pItem->m_strPath); 560 dlgFolderDetails.setName(pItem->m_strName); 561 dlgFolderDetails.setPermanent(pItem->m_enmType == UISharedFolderType_Machine); 562 dlgFolderDetails.setWriteable(pItem->m_fWritable); 563 dlgFolderDetails.setAutoMount(pItem->m_fAutoMount); 564 dlgFolderDetails.setAutoMountPoint(pItem->m_strAutoMountPoint); 565 566 /* Run folder details dialog: */ 567 if (dlgFolderDetails.exec() == QDialog::Accepted) 568 { 569 const QString strName = dlgFolderDetails.name(); 570 const QString strPath = dlgFolderDetails.path(); 571 const UISharedFolderType enmType = dlgFolderDetails.isPermanent() ? UISharedFolderType_Machine : UISharedFolderType_Console; 572 /* Shared folder's name & path could not be empty: */ 573 Assert(!strName.isEmpty() && !strPath.isEmpty()); 574 575 /* Update edited tree-widget item: */ 576 pItem->m_enmType = enmType; 577 pItem->m_strName = strName; 578 pItem->m_strPath = strPath; 579 pItem->m_fWritable = dlgFolderDetails.isWriteable(); 580 pItem->m_fAutoMount = dlgFolderDetails.isAutoMounted(); 581 pItem->m_strAutoMountPoint = dlgFolderDetails.autoMountPoint(); 428 pItem->m_strName = dlgFolderDetails.name(); 429 pItem->m_strVendorId = dlgFolderDetails.vendorID(); 430 pItem->m_strProductId = dlgFolderDetails.productID(); 431 pItem->m_strRevision = dlgFolderDetails.revision(); 432 pItem->m_strManufacturer = dlgFolderDetails.manufacturer(); 433 pItem->m_strProduct = dlgFolderDetails.product(); 434 pItem->m_strSerialNumber = dlgFolderDetails.serialNo(); 435 pItem->m_strPort = dlgFolderDetails.port(); 436 pItem->m_enmRemoteMode = dlgFolderDetails.remoteMode(); 582 437 pItem->updateFields(); 583 438 584 /* Searching for a root of the edited tree-widget item: */ 585 SFTreeViewItem *pRoot = root(enmType); 586 if (pItem->parentItem() != pRoot) 587 { 588 /* Move the tree-widget item to a new location: */ 589 pItem->parentItem()->takeChild(pItem->parentItem()->indexOfChild(pItem)); 590 pRoot->insertChild(pRoot->childCount(), pItem); 591 592 /* Update tree-widget: */ 593 m_pTreeWidget->scrollToItem(pItem); 594 m_pTreeWidget->setCurrentItem(pItem); 595 sltHandleCurrentItemChange(pItem); 596 } 597 598 /* Sort tree-widget before adjusting: */ 599 m_pTreeWidget->sortItems(0, Qt::AscendingOrder); 600 /* Adjust tree-widget finally: */ 601 sltAdjustTree(); 602 } 603 } 604 605 void UISharedFoldersEditor::sltRemoveFolder() 606 { 607 /* Check current folder item: */ 439 /* Notify listeners: */ 440 emit sigValueChanged(); 441 } 442 } 443 444 void UIUSBFiltersEditor::sltRemoveFilter() 445 { 446 /* Check current USB filter item: */ 608 447 QTreeWidgetItem *pItem = m_pTreeWidget->currentItem(); 609 448 AssertPtrReturnVoid(pItem); … … 612 451 delete pItem; 613 452 614 /* Adjust tree-widget finally: */ 615 sltAdjustTree(); 616 } 617 618 void UISharedFoldersEditor::prepare() 453 /* Notify listeners: */ 454 emit sigValueChanged(); 455 } 456 457 void UIUSBFiltersEditor::sltMoveFilterUp() 458 { 459 /* Check current USB filter item: */ 460 QTreeWidgetItem *pItem = m_pTreeWidget->currentItem(); 461 AssertPtrReturnVoid(pItem); 462 463 /* Move the item up: */ 464 const int iIndex = m_pTreeWidget->indexOfTopLevelItem(pItem); 465 QTreeWidgetItem *pTakenItem = m_pTreeWidget->takeTopLevelItem(iIndex); 466 Assert(pItem == pTakenItem); 467 m_pTreeWidget->insertTopLevelItem(iIndex - 1, pTakenItem); 468 469 /* Make sure moved item still chosen: */ 470 m_pTreeWidget->setCurrentItem(pTakenItem); 471 } 472 473 void UIUSBFiltersEditor::sltMoveFilterDown() 474 { 475 /* Check current USB filter item: */ 476 QTreeWidgetItem *pItem = m_pTreeWidget->currentItem(); 477 AssertPtrReturnVoid(pItem); 478 479 /* Move the item down: */ 480 const int iIndex = m_pTreeWidget->indexOfTopLevelItem(pItem); 481 QTreeWidgetItem *pTakenItem = m_pTreeWidget->takeTopLevelItem(iIndex); 482 Assert(pItem == pTakenItem); 483 m_pTreeWidget->insertTopLevelItem(iIndex + 1, pTakenItem); 484 485 /* Make sure moved item still chosen: */ 486 m_pTreeWidget->setCurrentItem(pTakenItem); 487 } 488 489 void UIUSBFiltersEditor::sltHandleActivityStateChange(QTreeWidgetItem *pChangedItem) 490 { 491 /* Check changed USB filter item: */ 492 USBFilterTreeWidgetItem *pItem = static_cast<USBFilterTreeWidgetItem*>(pChangedItem); 493 AssertPtrReturnVoid(pItem); 494 495 /* Update corresponding item: */ 496 pItem->m_fActive = pItem->checkState(0) == Qt::Checked; 497 } 498 499 void UIUSBFiltersEditor::prepare() 619 500 { 620 501 /* Prepare everything: */ … … 626 507 } 627 508 628 void UI SharedFoldersEditor::prepareWidgets()509 void UIUSBFiltersEditor::prepareWidgets() 629 510 { 630 511 /* Prepare main layout: */ … … 651 532 prepareToolbar(); 652 533 534 /* Update action availability: */ 535 sltHandleCurrentItemChange(m_pTreeWidget->currentItem()); 536 653 537 pLayout->addLayout(m_pLayoutTree); 654 538 } … … 656 540 } 657 541 658 void UI SharedFoldersEditor::prepareTreeWidget()542 void UIUSBFiltersEditor::prepareTreeWidget() 659 543 { 660 544 /* Prepare shared folders tree-widget: */ … … 664 548 if (m_pLabelSeparator) 665 549 m_pLabelSeparator->setBuddy(m_pTreeWidget); 666 m_pTreeWidget->header()->setSectionsMovable(false); 667 m_pTreeWidget->setMinimumSize(QSize(0, 200)); 550 m_pTreeWidget->header()->hide(); 551 m_pTreeWidget->setRootIsDecorated(false); 552 m_pTreeWidget->setUniformRowHeights(true); 668 553 m_pTreeWidget->setContextMenuPolicy(Qt::CustomContextMenu); 669 m_pTreeWidget->setUniformRowHeights(true);670 m_pTreeWidget->setAllColumnsShowFocus(true);671 554 672 555 m_pLayoutTree->addWidget(m_pTreeWidget); … … 674 557 } 675 558 676 void UI SharedFoldersEditor::prepareToolbar()559 void UIUSBFiltersEditor::prepareToolbar() 677 560 { 678 561 /* Prepare shared folders toolbar: */ … … 684 567 m_pToolbar->setOrientation(Qt::Vertical); 685 568 686 /* Prepare 'add shared folder' action: */ 687 m_pActionAdd = m_pToolbar->addAction(UIIconPool::iconSet(":/sf_add_16px.png", 688 ":/sf_add_disabled_16px.png"), 689 QString(), this, SLOT(sltAddFolder())); 569 /* Prepare 'New USB Filter' action: */ 570 m_pActionNew = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_new_16px.png", 571 ":/usb_new_disabled_16px.png"), 572 QString(), this, SLOT(sltCreateFilter())); 573 if (m_pActionNew) 574 m_pActionNew->setShortcuts(QList<QKeySequence>() << QKeySequence("Ins") << QKeySequence("Ctrl+N")); 575 576 /* Prepare 'Add USB Filter' action: */ 577 m_pActionAdd = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_add_16px.png", 578 ":/usb_add_disabled_16px.png"), 579 QString(), this, SLOT(sltAddFilter())); 690 580 if (m_pActionAdd) 691 m_pActionAdd->setShortcuts(QList<QKeySequence>() << QKeySequence(" Ins") << QKeySequence("Ctrl+N"));692 693 /* Prepare ' edit shared folder' action: */694 m_pActionEdit = m_pToolbar->addAction(UIIconPool::iconSet(":/ sf_edit_16px.png",695 ":/ sf_edit_disabled_16px.png"),696 QString(), this, SLOT(sltEditF older()));581 m_pActionAdd->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Ins") << QKeySequence("Ctrl+A")); 582 583 /* Prepare 'Edit USB Filter' action: */ 584 m_pActionEdit = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_filter_edit_16px.png", 585 ":/usb_filter_edit_disabled_16px.png"), 586 QString(), this, SLOT(sltEditFilter())); 697 587 if (m_pActionEdit) 698 m_pActionEdit->setShortcuts(QList<QKeySequence>() << QKeySequence(" Space") << QKeySequence("F2"));699 700 /* Prepare ' remove shared folder' action: */701 m_pActionRemove = m_pToolbar->addAction(UIIconPool::iconSet(":/ sf_remove_16px.png",702 ":/ sf_remove_disabled_16px.png"),703 QString(), this, SLOT(sltRemoveF older()));588 m_pActionEdit->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Return") << QKeySequence("Ctrl+Return")); 589 590 /* Prepare 'Remove USB Filter' action: */ 591 m_pActionRemove = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_remove_16px.png", 592 ":/usb_remove_disabled_16px.png"), 593 QString(), this, SLOT(sltRemoveFilter())); 704 594 if (m_pActionRemove) 705 595 m_pActionRemove->setShortcuts(QList<QKeySequence>() << QKeySequence("Del") << QKeySequence("Ctrl+R")); 706 596 597 /* Prepare 'Move USB Filter Up' action: */ 598 m_pActionMoveUp = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_moveup_16px.png", 599 ":/usb_moveup_disabled_16px.png"), 600 QString(), this, SLOT(sltMoveFilterUp())); 601 if (m_pActionMoveUp) 602 m_pActionMoveUp->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Up") << QKeySequence("Ctrl+Up")); 603 604 /* Prepare 'Move USB Filter Down' action: */ 605 m_pActionMoveDown = m_pToolbar->addAction(UIIconPool::iconSet(":/usb_movedown_16px.png", 606 ":/usb_movedown_disabled_16px.png"), 607 QString(), this, SLOT(sltMoveFilterDown())); 608 if (m_pActionMoveDown) 609 m_pActionMoveDown->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Down") << QKeySequence("Ctrl+Down")); 610 611 /* Prepare USB devices menu: */ 612 m_pMenuUSBDevices = new UIUSBMenu(this); 613 707 614 m_pLayoutTree->addWidget(m_pToolbar); 708 615 } 709 616 } 710 617 711 void UI SharedFoldersEditor::prepareConnections()618 void UIUSBFiltersEditor::prepareConnections() 712 619 { 713 620 /* Configure tree-widget connections: */ 714 connect(m_pTreeWidget, &QITreeWidget::currentItemChanged, 715 this, &UISharedFoldersEditor::sltHandleCurrentItemChange); 716 connect(m_pTreeWidget, &QITreeWidget::itemDoubleClicked, 717 this, &UISharedFoldersEditor::sltHandleDoubleClick); 718 connect(m_pTreeWidget, &QITreeWidget::customContextMenuRequested, 719 this, &UISharedFoldersEditor::sltHandleContextMenuRequest); 720 } 721 722 QStringList UISharedFoldersEditor::usedList(bool fIncludeSelected) 723 { 724 /* Make the used names list: */ 725 QStringList list; 726 QTreeWidgetItemIterator it(m_pTreeWidget); 727 while (*it) 728 { 729 if ((*it)->parent() && (fIncludeSelected || !(*it)->isSelected())) 730 list << static_cast<SFTreeViewItem*>(*it)->getText(0); 731 ++it; 732 } 733 return list; 734 } 735 736 SFTreeViewItem *UISharedFoldersEditor::root(UISharedFolderType enmSharedFolderType) 737 { 738 /* Search for the corresponding root item among all the top-level items: */ 739 SFTreeViewItem *pRootItem = 0; 740 QTreeWidgetItem *pMainRootItem = m_pTreeWidget->invisibleRootItem(); 741 for (int iFolderTypeIndex = 0; iFolderTypeIndex < pMainRootItem->childCount(); ++iFolderTypeIndex) 742 { 743 /* Get iterated item: */ 744 SFTreeViewItem *pIteratedItem = static_cast<SFTreeViewItem*>(pMainRootItem->child(iFolderTypeIndex)); 745 /* If iterated item type is what we are looking for: */ 746 if (pIteratedItem->m_enmType == enmSharedFolderType) 747 { 748 /* Remember the item: */ 749 pRootItem = static_cast<SFTreeViewItem*>(pIteratedItem); 750 /* And break further search: */ 751 break; 752 } 753 } 754 /* Return root item: */ 755 return pRootItem; 756 } 757 758 void UISharedFoldersEditor::setRootItemVisible(UISharedFolderType enmSharedFolderType, bool fVisible) 759 { 760 /* Search for the corresponding root item among all the top-level items: */ 761 SFTreeViewItem *pRootItem = root(enmSharedFolderType); 762 /* If root item, we are looking for, still not found: */ 763 if (!pRootItem) 764 { 765 /* Create new shared folder type item: */ 766 pRootItem = new SFTreeViewItem(m_pTreeWidget, SFTreeViewItem::FormatType_EllipsisEnd); 767 if (pRootItem) 768 { 769 /* Configure item: */ 770 pRootItem->m_enmType = enmSharedFolderType; 771 switch (enmSharedFolderType) 772 { 773 case UISharedFolderType_Machine: pRootItem->m_strName = tr(" Machine Folders"); break; 774 case UISharedFolderType_Console: pRootItem->m_strName = tr(" Transient Folders"); break; 775 default: break; 776 } 777 pRootItem->updateFields(); 778 } 779 } 780 /* Expand/collaps it if necessary: */ 781 pRootItem->setExpanded(fVisible); 782 /* And hide/show it if necessary: */ 783 pRootItem->setHidden(!fVisible); 784 } 785 786 void UISharedFoldersEditor::updateRootItemsVisibility() 787 { 788 /* Update (show/hide) machine (permanent) root item: */ 789 setRootItemVisible(UISharedFolderType_Machine, m_foldersAvailable.value(UISharedFolderType_Machine)); 790 /* Update (show/hide) console (temporary) root item: */ 791 setRootItemVisible(UISharedFolderType_Console, m_foldersAvailable.value(UISharedFolderType_Console)); 792 } 793 794 void UISharedFoldersEditor::addSharedFolderItem(const UIDataSharedFolder &sharedFolderData, bool fChoose) 795 { 796 /* Create shared folder item: */ 797 SFTreeViewItem *pItem = new SFTreeViewItem(root(sharedFolderData.m_enmType), SFTreeViewItem::FormatType_EllipsisFile); 621 if (m_pTreeWidget) 622 { 623 connect(m_pTreeWidget, &QITreeWidget::currentItemChanged, 624 this, &UIUSBFiltersEditor::sltHandleCurrentItemChange); 625 connect(m_pTreeWidget, &QITreeWidget::itemDoubleClicked, 626 this, &UIUSBFiltersEditor::sltHandleDoubleClick); 627 connect(m_pTreeWidget, &QITreeWidget::customContextMenuRequested, 628 this, &UIUSBFiltersEditor::sltHandleContextMenuRequest); 629 connect(m_pTreeWidget, &QITreeWidget::itemChanged, 630 this, &UIUSBFiltersEditor::sltHandleActivityStateChange); 631 } 632 633 /* Configure USB device menu connections: */ 634 if (m_pMenuUSBDevices) 635 connect(m_pMenuUSBDevices, &UIUSBMenu::triggered, 636 this, &UIUSBFiltersEditor::sltAddFilterConfirmed); 637 } 638 639 void UIUSBFiltersEditor::addUSBFilterItem(const UIDataUSBFilter &data, bool fChoose) 640 { 641 /* Create USB filter item: */ 642 USBFilterTreeWidgetItem *pItem = new USBFilterTreeWidgetItem(m_pTreeWidget); 798 643 if (pItem) 799 644 { 800 645 /* Configure item: */ 801 pItem->m_enmType = sharedFolderData.m_enmType; 802 pItem->m_strName = sharedFolderData.m_strName; 803 pItem->m_strPath = sharedFolderData.m_strPath; 804 pItem->m_fWritable = sharedFolderData.m_fWritable; 805 pItem->m_fAutoMount = sharedFolderData.m_fAutoMount; 806 pItem->m_strAutoMountPoint = sharedFolderData.m_strAutoMountPoint; 646 pItem->setCheckState(0, data.m_fActive ? Qt::Checked : Qt::Unchecked); 647 pItem->m_fActive = data.m_fActive; 648 pItem->m_strName = data.m_strName; 649 pItem->m_strVendorId = data.m_strVendorId; 650 pItem->m_strProductId = data.m_strProductId; 651 pItem->m_strRevision = data.m_strRevision; 652 pItem->m_strManufacturer = data.m_strManufacturer; 653 pItem->m_strProduct = data.m_strProduct; 654 pItem->m_strSerialNumber = data.m_strSerialNumber; 655 pItem->m_strPort = data.m_strPort; 656 pItem->m_enmRemoteMode = data.m_enmRemoteMode; 807 657 pItem->updateFields(); 808 658 … … 817 667 } 818 668 819 void UI SharedFoldersEditor::reloadTree()669 void UIUSBFiltersEditor::reloadTree() 820 670 { 821 671 /* Sanity check: */ … … 826 676 m_pTreeWidget->clear(); 827 677 828 /* Update root items visibility: */ 829 updateRootItemsVisibility(); 830 831 /* For each folder => load it from cache: */ 832 foreach (const UIDataSharedFolder &guiData, m_guiValue) 833 addSharedFolderItem(guiData, false /* its new? */); 834 835 /* Choose first folder as current: */ 678 /* For each filter => load it from cache: */ 679 foreach (const UIDataUSBFilter &guiData, m_guiValue) 680 addUSBFilterItem(guiData, false /* its new? */); 681 682 /* Choose first filter as current: */ 836 683 m_pTreeWidget->setCurrentItem(m_pTreeWidget->topLevelItem(0)); 837 684 sltHandleCurrentItemChange(m_pTreeWidget->currentItem()); … … 839 686 840 687 841 #include "UI SharedFoldersEditor.moc"688 #include "UIUSBFiltersEditor.moc" -
trunk/src/VBox/Frontends/VirtualBox/src/settings/editors/UIUSBFiltersEditor.h
r95276 r95277 1 1 /* $Id$ */ 2 2 /** @file 3 * VBox Qt GUI - UI SharedFoldersEditor class declaration.3 * VBox Qt GUI - UIUSBFiltersEditor class declaration. 4 4 */ 5 5 … … 16 16 */ 17 17 18 #ifndef FEQT_INCLUDED_SRC_settings_editors_UI SharedFoldersEditor_h19 #define FEQT_INCLUDED_SRC_settings_editors_UI SharedFoldersEditor_h18 #ifndef FEQT_INCLUDED_SRC_settings_editors_UIUSBFiltersEditor_h 19 #define FEQT_INCLUDED_SRC_settings_editors_UIUSBFiltersEditor_h 20 20 #ifndef RT_WITHOUT_PRAGMA_ONCE 21 21 # pragma once … … 32 32 class QIToolBar; 33 33 class QITreeWidget; 34 class SFTreeViewItem;34 class UIUSBMenu; 35 35 36 /** Shared Folder data. */37 struct UIData SharedFolder36 /** USB Filter data. */ 37 struct UIDataUSBFilter 38 38 { 39 39 /** Constructs data. */ 40 UIDataSharedFolder() 41 : m_enmType(UISharedFolderType_Machine) 42 , m_strName() 43 , m_strPath() 44 , m_fWritable(false) 45 , m_fAutoMount(false) 46 , m_strAutoMountPoint() 40 UIDataUSBFilter() 41 : m_fActive(true) 42 , m_enmRemoteMode(UIRemoteMode_Any) 47 43 {} 48 44 49 45 /** Returns whether the @a other passed data is equal to this one. */ 50 bool equal(const UIData SharedFolder &other) const46 bool equal(const UIDataUSBFilter &other) const 51 47 { 52 48 return true 53 && m_ enmType == other.m_enmType49 && m_fActive == other.m_fActive 54 50 && m_strName == other.m_strName 55 && m_strPath == other.m_strPath 56 && m_fWritable == other.m_fWritable 57 && m_fAutoMount == other.m_fAutoMount 58 && m_strAutoMountPoint == other.m_strAutoMountPoint 51 && m_strVendorId == other.m_strVendorId 52 && m_strProductId == other.m_strProductId 53 && m_strRevision == other.m_strRevision 54 && m_strManufacturer == other.m_strManufacturer 55 && m_strProduct == other.m_strProduct 56 && m_strSerialNumber == other.m_strSerialNumber 57 && m_strPort == other.m_strPort 58 && m_enmRemoteMode == other.m_enmRemoteMode 59 59 ; 60 60 } 61 61 62 62 /** Returns whether the @a other passed data is equal to this one. */ 63 bool operator==(const UIData SharedFolder &other) const { return equal(other); }63 bool operator==(const UIDataUSBFilter &other) const { return equal(other); } 64 64 /** Returns whether the @a other passed data is different from this one. */ 65 bool operator!=(const UIData SharedFolder &other) const { return !equal(other); }65 bool operator!=(const UIDataUSBFilter &other) const { return !equal(other); } 66 66 67 /** Holds the shared folder type. */ 68 UISharedFolderType m_enmType; 69 /** Holds the shared folder name. */ 70 QString m_strName; 71 /** Holds the shared folder path. */ 72 QString m_strPath; 73 /** Holds whether the shared folder should be writeable. */ 74 bool m_fWritable; 75 /** Holds whether the shared folder should be auto-mounted at startup. */ 76 bool m_fAutoMount; 77 /** Where in the guest to try auto mount the shared folder (drive for 78 * Windows & OS/2, path for unixy guests). */ 79 QString m_strAutoMountPoint; 67 /** Holds whether USB filter is active. */ 68 bool m_fActive; 69 /** Holds the USB filter name. */ 70 QString m_strName; 71 /** Holds the USB filter vendor ID. */ 72 QString m_strVendorId; 73 /** Holds the USB filter product ID. */ 74 QString m_strProductId; 75 /** Holds the USB filter revision. */ 76 QString m_strRevision; 77 /** Holds the USB filter manufacturer. */ 78 QString m_strManufacturer; 79 /** Holds the USB filter product. */ 80 QString m_strProduct; 81 /** Holds the USB filter serial number. */ 82 QString m_strSerialNumber; 83 /** Holds the USB filter port. */ 84 QString m_strPort; 85 /** Holds the USB filter remote. */ 86 UIRemoteMode m_enmRemoteMode; 80 87 }; 81 88 82 /** QWidget subclass used as a shared folders editor. */83 class SHARED_LIBRARY_STUFF UI SharedFoldersEditor : public QIWithRetranslateUI<QWidget>89 /** QWidget subclass used as a USB filters editor. */ 90 class SHARED_LIBRARY_STUFF UIUSBFiltersEditor : public QIWithRetranslateUI<QWidget> 84 91 { 85 92 Q_OBJECT; 93 94 signals: 95 96 /** Notifies listeners about value change. */ 97 void sigValueChanged(); 86 98 87 99 public: 88 100 89 101 /** Constructs editor passing @a pParent to the base-class. */ 90 UI SharedFoldersEditor(QWidget *pParent = 0);102 UIUSBFiltersEditor(QWidget *pParent = 0); 91 103 92 104 /** Defines editor @a strValue. */ 93 void setValue(const QList<UIData SharedFolder> &guiValue);105 void setValue(const QList<UIDataUSBFilter> &guiValue); 94 106 /** Returns editor value. */ 95 QList<UIDataSharedFolder> value() const; 96 97 /** Defines whether feature @a fAvailable. */ 98 void setFeatureAvailable(bool fAvailable); 99 /** Defines whether folders of certain @a enmType are @a fAvailable. */ 100 void setFoldersAvailable(UISharedFolderType enmType, bool fAvailable); 107 QList<UIDataUSBFilter> value() const; 101 108 102 109 protected: … … 105 112 virtual void retranslateUi() RT_OVERRIDE; 106 113 107 /** Handles show @a pEvent. */108 virtual void showEvent(QShowEvent *pEvent) RT_OVERRIDE;109 110 /** Handles resize @a pEvent. */111 virtual void resizeEvent(QResizeEvent *pEvent) RT_OVERRIDE;112 113 114 private slots: 114 115 /** Performs request to adjust tree. */116 void sltAdjustTree();117 /** Performs request to adjust tree fields. */118 void sltAdjustTreeFields();119 115 120 116 /** Handles @a pCurrentItem change. */ … … 125 121 void sltHandleContextMenuRequest(const QPoint &position); 126 122 127 /** Handles command to add shared folder. */ 128 void sltAddFolder(); 129 /** Handles command to edit shared folder. */ 130 void sltEditFolder(); 131 /** Handles command to remove shared folder. */ 132 void sltRemoveFolder(); 123 /** Handles command to create USB filter. */ 124 void sltCreateFilter(); 125 /** Handles command to add USB filter. */ 126 void sltAddFilter(); 127 /** Handles command to confirm add of existing USB filter defined by @a pAction. */ 128 void sltAddFilterConfirmed(QAction *pAction); 129 /** Handles command to edit USB filter. */ 130 void sltEditFilter(); 131 /** Handles command to remove USB filter. */ 132 void sltRemoveFilter(); 133 /** Handles command to move chosen USB filter up. */ 134 void sltMoveFilterUp(); 135 /** Handles command to move chosen USB filter down. */ 136 void sltMoveFilterDown(); 137 138 /** Handles USB filter tree activity state change for @a pChangedItem. */ 139 void sltHandleActivityStateChange(QTreeWidgetItem *pChangedItem); 133 140 134 141 private: … … 145 152 void prepareConnections(); 146 153 147 /** Returns a list of used shared folder names. */ 148 QStringList usedList(bool fIncludeSelected); 149 150 /** Returns the tree-view root item for corresponding shared folder @a type. */ 151 SFTreeViewItem *root(UISharedFolderType type); 152 /** Defines whether the root item of @a enmFoldersType is @a fVisible. */ 153 void setRootItemVisible(UISharedFolderType enmFoldersType, bool fVisible); 154 /** Updates root item visibility. */ 155 void updateRootItemsVisibility(); 156 /** Creates shared folder item based on passed @a data. */ 157 void addSharedFolderItem(const UIDataSharedFolder &sharedFolderData, bool fChoose); 154 /** Creates USB filter item based on passed @a data. */ 155 void addUSBFilterItem(const UIDataUSBFilter &data, bool fChoose); 158 156 /** Reloads tree. */ 159 157 void reloadTree(); 160 158 161 159 /** Holds the value to be set. */ 162 QList<UIData SharedFolder> m_guiValue;160 QList<UIDataUSBFilter> m_guiValue; 163 161 164 /** Holds whether folders of certain type are available. */ 165 QMap<UISharedFolderType, bool> m_foldersAvailable; 162 /** @name Internal 163 * @{ */ 164 /** Holds the "New Filter %1" translation tag. */ 165 QString m_strTrUSBFilterName; 166 /** @} */ 166 167 167 168 /** @name Widgets … … 175 176 /** Holds the toolbar instance. */ 176 177 QIToolBar *m_pToolbar; 177 /** Holds the 'add shared folder' action instance. */ 178 /** Holds the 'new USB filter' action instance. */ 179 QAction *m_pActionNew; 180 /** Holds the 'add USB filter' action instance. */ 178 181 QAction *m_pActionAdd; 179 /** Holds the 'edit shared folder' action instance. */182 /** Holds the 'edit USB filter' action instance. */ 180 183 QAction *m_pActionEdit; 181 /** Holds the 'remove shared folder' action instance. */184 /** Holds the 'remove USB filter' action instance. */ 182 185 QAction *m_pActionRemove; 186 /** Holds the Move Up action instance. */ 187 QAction *m_pActionMoveUp; 188 /** Holds the Move Down action instance. */ 189 QAction *m_pActionMoveDown; 190 /** Holds the USB devices menu instance. */ 191 UIUSBMenu *m_pMenuUSBDevices; 183 192 /** @} */ 184 193 }; 185 194 186 #endif /* !FEQT_INCLUDED_SRC_settings_editors_UI SharedFoldersEditor_h */195 #endif /* !FEQT_INCLUDED_SRC_settings_editors_UIUSBFiltersEditor_h */ -
trunk/src/VBox/Frontends/VirtualBox/src/settings/machine/UIMachineSettingsUSB.cpp
r95247 r95277 26 26 #include <QRegExp> 27 27 #include <QSpacerItem> 28 #include <QToolTip>29 28 #include <QVBoxLayout> 30 29 … … 41 40 #include "UIUSBControllerEditor.h" 42 41 #include "UIUSBFilterDetailsEditor.h" 42 #include "UIUSBFiltersEditor.h" 43 43 44 44 /* COM includes: */ 45 #include "CConsole.h"46 45 #include "CExtPack.h" 47 46 #include "CExtPackManager.h" 48 #include "CHostUSBDevice.h"49 #include "CHostUSBDeviceFilter.h"50 47 #include "CUSBController.h" 51 #include "CUSBDevice.h"52 48 #include "CUSBDeviceFilter.h" 53 49 #include "CUSBDeviceFilters.h" 54 50 55 /* VirtualBox interface declarations: */56 #include <VBox/com/VirtualBox.h>57 58 51 59 52 /** Machine settings: USB filter data structure. */ … … 61 54 { 62 55 /** Constructs data. */ 63 UIDataSettingsMachineUSBFilter() 64 : m_fActive(false) 65 , m_strName(QString()) 66 , m_strVendorId(QString()) 67 , m_strProductId(QString()) 68 , m_strRevision(QString()) 69 , m_strManufacturer(QString()) 70 , m_strProduct(QString()) 71 , m_strSerialNumber(QString()) 72 , m_strPort(QString()) 73 , m_strRemote(QString()) 74 , m_enmAction(KUSBDeviceFilterAction_Null) 75 , m_enmHostUSBDeviceState(KUSBDeviceState_NotSupported) 76 , m_fHostUSBDevice(false) 77 {} 56 UIDataSettingsMachineUSBFilter() {} 78 57 79 58 /** Returns whether the @a other passed data is equal to this one. */ … … 81 60 { 82 61 return true 83 && (m_fActive == other.m_fActive) 84 && (m_strName == other.m_strName) 85 && (m_strVendorId == other.m_strVendorId) 86 && (m_strProductId == other.m_strProductId) 87 && (m_strRevision == other.m_strRevision) 88 && (m_strManufacturer == other.m_strManufacturer) 89 && (m_strProduct == other.m_strProduct) 90 && (m_strSerialNumber == other.m_strSerialNumber) 91 && (m_strPort == other.m_strPort) 92 && (m_strRemote == other.m_strRemote) 93 && (m_enmAction == other.m_enmAction) 94 && (m_enmHostUSBDeviceState == other.m_enmHostUSBDeviceState) 62 && (m_guiData == other.m_guiData) 95 63 ; 96 64 } … … 101 69 bool operator!=(const UIDataSettingsMachineUSBFilter &other) const { return !equal(other); } 102 70 103 /** Holds whether the USB filter is enabled. */ 104 bool m_fActive; 105 /** Holds the USB filter name. */ 106 QString m_strName; 107 /** Holds the USB filter vendor ID. */ 108 QString m_strVendorId; 109 /** Holds the USB filter product ID. */ 110 QString m_strProductId; 111 /** Holds the USB filter revision. */ 112 QString m_strRevision; 113 /** Holds the USB filter manufacturer. */ 114 QString m_strManufacturer; 115 /** Holds the USB filter product. */ 116 QString m_strProduct; 117 /** Holds the USB filter serial number. */ 118 QString m_strSerialNumber; 119 /** Holds the USB filter port. */ 120 QString m_strPort; 121 /** Holds the USB filter remote. */ 122 QString m_strRemote; 123 124 /** Holds the USB filter action. */ 125 KUSBDeviceFilterAction m_enmAction; 126 /** Holds the USB device state. */ 127 KUSBDeviceState m_enmHostUSBDeviceState; 128 /** Holds whether the USB filter is host USB device. */ 129 bool m_fHostUSBDevice; 71 /** Holds the USB filter data. */ 72 UIDataUSBFilter m_guiData; 130 73 }; 131 74 … … 161 104 162 105 163 /** Machine settings: USB Filter popup menu. */164 class VBoxUSBMenu : public QMenu165 {166 Q_OBJECT;167 168 public:169 170 /* Constructor: */171 VBoxUSBMenu(QWidget *)172 {173 connect(this, &VBoxUSBMenu::aboutToShow, this, &VBoxUSBMenu::processAboutToShow);174 }175 176 /* Returns USB device related to passed action: */177 const CUSBDevice& getUSB(QAction *pAction)178 {179 return m_usbDeviceMap[pAction];180 }181 182 /* Console setter: */183 void setConsole(const CConsole &console)184 {185 m_console = console;186 }187 188 private slots:189 190 /* Prepare menu appearance: */191 void processAboutToShow()192 {193 clear();194 m_usbDeviceMap.clear();195 196 CHost host = uiCommon().host();197 198 bool fIsUSBEmpty = host.GetUSBDevices().size() == 0;199 200 if (fIsUSBEmpty)201 {202 QAction *pAction = addAction(tr("<no devices available>", "USB devices"));203 pAction->setEnabled(false);204 pAction->setToolTip(tr("No supported devices connected to the host PC", "USB device tooltip"));205 }206 else207 {208 CHostUSBDeviceVector devvec = host.GetUSBDevices();209 for (int i = 0; i < devvec.size(); ++i)210 {211 CHostUSBDevice dev = devvec[i];212 CUSBDevice usb(dev);213 QAction *pAction = addAction(uiCommon().usbDetails(usb));214 pAction->setCheckable(true);215 m_usbDeviceMap[pAction] = usb;216 /* Check if created item was already attached to this session: */217 if (!m_console.isNull())218 {219 CUSBDevice attachedUSB = m_console.FindUSBDeviceById(usb.GetId());220 pAction->setChecked(!attachedUSB.isNull());221 pAction->setEnabled(dev.GetState() != KUSBDeviceState_Unavailable);222 }223 }224 }225 }226 227 private:228 229 /* Event handler: */230 bool event(QEvent *pEvent)231 {232 /* We provide dynamic tooltips for the usb devices: */233 if (pEvent->type() == QEvent::ToolTip)234 {235 QHelpEvent *pHelpEvent = static_cast<QHelpEvent*>(pEvent);236 QAction *pAction = actionAt(pHelpEvent->pos());237 if (pAction)238 {239 CUSBDevice usb = m_usbDeviceMap[pAction];240 if (!usb.isNull())241 {242 QToolTip::showText(pHelpEvent->globalPos(), uiCommon().usbToolTip(usb));243 return true;244 }245 }246 }247 /* Call to base-class: */248 return QMenu::event(pEvent);249 }250 251 QMap<QAction*, CUSBDevice> m_usbDeviceMap;252 CConsole m_console;253 };254 255 256 /** Machine settings: USB Filter tree-widget item. */257 class UIUSBFilterItem : public QITreeWidgetItem, public UIDataSettingsMachineUSBFilter258 {259 Q_OBJECT;260 261 public:262 263 /** Constructs USB filter (root) item.264 * @param pParent Brings the item parent. */265 UIUSBFilterItem(QITreeWidget *pParent)266 : QITreeWidgetItem(pParent)267 {268 }269 270 /** Updates item fields. */271 void updateFields()272 {273 setText(0, m_strName);274 setToolTip(0, toolTipFor());275 }276 277 protected:278 279 /** Returns default text. */280 virtual QString defaultText() const RT_OVERRIDE281 {282 return checkState(0) == Qt::Checked ?283 tr("%1, Active", "col.1 text, col.1 state").arg(text(0)) :284 tr("%1", "col.1 text") .arg(text(0));285 }286 287 private:288 289 /** Returns tool-tip generated from item data. */290 QString toolTipFor()291 {292 /* Prepare tool-tip: */293 QString strToolTip;294 295 const QString strVendorId = m_strVendorId;296 if (!strVendorId.isEmpty())297 strToolTip += tr("<nobr>Vendor ID: %1</nobr>", "USB filter tooltip").arg(strVendorId);298 299 const QString strProductId = m_strProductId;300 if (!strProductId.isEmpty())301 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Product ID: %2</nobr>", "USB filter tooltip").arg(strProductId);302 303 const QString strRevision = m_strRevision;304 if (!strRevision.isEmpty())305 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Revision: %3</nobr>", "USB filter tooltip").arg(strRevision);306 307 const QString strProduct = m_strProduct;308 if (!strProduct.isEmpty())309 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Product: %4</nobr>", "USB filter tooltip").arg(strProduct);310 311 const QString strManufacturer = m_strManufacturer;312 if (!strManufacturer.isEmpty())313 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Manufacturer: %5</nobr>", "USB filter tooltip").arg(strManufacturer);314 315 const QString strSerial = m_strSerialNumber;316 if (!strSerial.isEmpty())317 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Serial No.: %1</nobr>", "USB filter tooltip").arg(strSerial);318 319 const QString strPort = m_strPort;320 if (!strPort.isEmpty())321 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>Port: %1</nobr>", "USB filter tooltip").arg(strPort);322 323 /* Add the state field if it's a host USB device: */324 if (m_fHostUSBDevice)325 {326 strToolTip += strToolTip.isEmpty() ? "":"<br/>" + tr("<nobr>State: %1</nobr>", "USB filter tooltip")327 .arg(gpConverter->toString(m_enmHostUSBDeviceState));328 }329 330 /* Return tool-tip: */331 return strToolTip;332 }333 };334 335 336 106 UIMachineSettingsUSB::UIMachineSettingsUSB() 337 107 : m_pCache(0) … … 339 109 , m_pWidgetUSBSettings(0) 340 110 , m_pEditorController(0) 341 , m_pLabelSeparatorFilters(0) 342 , m_pLayoutFilters(0) 343 , m_pTreeWidgetFilters(0) 344 , m_pToolbarFilters(0) 345 , m_pActionNew(0) 346 , m_pActionAdd(0) 347 , m_pActionEdit(0) 348 , m_pActionRemove(0) 349 , m_pActionMoveUp(0) 350 , m_pActionMoveDown(0) 351 , m_pMenuUSBDevices(0) 111 , m_pEditorFilters(0) 352 112 { 353 113 prepare(); … … 407 167 { 408 168 /* Gather old data: */ 409 oldFilterData.m_fActive = filter.GetActive(); 410 oldFilterData.m_strName = filter.GetName(); 411 oldFilterData.m_strVendorId = filter.GetVendorId(); 412 oldFilterData.m_strProductId = filter.GetProductId(); 413 oldFilterData.m_strRevision = filter.GetRevision(); 414 oldFilterData.m_strManufacturer = filter.GetManufacturer(); 415 oldFilterData.m_strProduct = filter.GetProduct(); 416 oldFilterData.m_strSerialNumber = filter.GetSerialNumber(); 417 oldFilterData.m_strPort = filter.GetPort(); 418 oldFilterData.m_strRemote = filter.GetRemote(); 169 oldFilterData.m_guiData.m_fActive = filter.GetActive(); 170 oldFilterData.m_guiData.m_strName = filter.GetName(); 171 oldFilterData.m_guiData.m_strVendorId = filter.GetVendorId(); 172 oldFilterData.m_guiData.m_strProductId = filter.GetProductId(); 173 oldFilterData.m_guiData.m_strRevision = filter.GetRevision(); 174 oldFilterData.m_guiData.m_strManufacturer = filter.GetManufacturer(); 175 oldFilterData.m_guiData.m_strProduct = filter.GetProduct(); 176 oldFilterData.m_guiData.m_strSerialNumber = filter.GetSerialNumber(); 177 oldFilterData.m_guiData.m_strPort = filter.GetPort(); 178 const QString strRemote = filter.GetRemote(); 179 UIRemoteMode enmRemoteMode = UIRemoteMode_Any; 180 if (strRemote == "true" || strRemote == "yes" || strRemote == "1") 181 enmRemoteMode = UIRemoteMode_On; 182 else if (strRemote == "false" || strRemote == "no" || strRemote == "0") 183 enmRemoteMode = UIRemoteMode_Off; 184 oldFilterData.m_guiData.m_enmRemoteMode = enmRemoteMode; 419 185 } 420 186 … … 434 200 { 435 201 /* Sanity check: */ 436 if ( !m_pCache 437 || !m_pTreeWidgetFilters) 202 if (!m_pCache) 438 203 return; 439 440 /* Clear list initially: */441 m_pTreeWidgetFilters->clear();442 204 443 205 /* Get old USB data from cache: */ … … 449 211 if (m_pEditorController) 450 212 m_pEditorController->setValue(oldUsbData.m_enmUSBControllerType); 451 452 /* For each filter => load it from cache: */ 453 for (int iFilterIndex = 0; iFilterIndex < m_pCache->childCount(); ++iFilterIndex) 454 addUSBFilterItem(m_pCache->child(iFilterIndex).base(), false /* its new? */); 455 456 /* Choose first filter as current: */ 457 m_pTreeWidgetFilters->setCurrentItem(m_pTreeWidgetFilters->topLevelItem(0)); 213 if (m_pEditorFilters) 214 { 215 /* For each filter => load it from cache: */ 216 QList<UIDataUSBFilter> filters; 217 for (int iFilterIndex = 0; iFilterIndex < m_pCache->childCount(); ++iFilterIndex) 218 { 219 const UIDataSettingsMachineUSBFilter &oldUsbFilterData = m_pCache->child(iFilterIndex).base(); 220 UIDataUSBFilter filter; 221 filter.m_fActive = oldUsbFilterData.m_guiData.m_fActive; 222 filter.m_strName = oldUsbFilterData.m_guiData.m_strName; 223 filter.m_strVendorId = oldUsbFilterData.m_guiData.m_strVendorId; 224 filter.m_strProductId = oldUsbFilterData.m_guiData.m_strProductId; 225 filter.m_strRevision = oldUsbFilterData.m_guiData.m_strRevision; 226 filter.m_strManufacturer = oldUsbFilterData.m_guiData.m_strManufacturer; 227 filter.m_strProduct = oldUsbFilterData.m_guiData.m_strProduct; 228 filter.m_strSerialNumber = oldUsbFilterData.m_guiData.m_strSerialNumber; 229 filter.m_strPort = oldUsbFilterData.m_guiData.m_strPort; 230 filter.m_enmRemoteMode = oldUsbFilterData.m_guiData.m_enmRemoteMode; 231 filters << filter; 232 } 233 m_pEditorFilters->setValue(filters); 234 } 235 236 /* Update widget availability: */ 458 237 if (m_pCheckBoxUSB) 459 238 sltHandleUsbAdapterToggle(m_pCheckBoxUSB->isChecked()); … … 470 249 /* Sanity check: */ 471 250 if ( !m_pCache 472 || !m_p TreeWidgetFilters)251 || !m_pEditorFilters) 473 252 return; 474 253 … … 481 260 if (m_pEditorController) 482 261 newUsbData.m_enmUSBControllerType = newUsbData.m_fUSBEnabled ? m_pEditorController->value() : KUSBControllerType_Null; 483 484 /* For each filter: */ 485 QTreeWidgetItem *pMainRootItem = m_pTreeWidgetFilters->invisibleRootItem(); 486 for (int iFilterIndex = 0; iFilterIndex < pMainRootItem->childCount(); ++iFilterIndex) 487 { 488 /* Gather and cache new data: */ 489 const UIUSBFilterItem *pItem = static_cast<UIUSBFilterItem*>(pMainRootItem->child(iFilterIndex)); 490 m_pCache->child(iFilterIndex).cacheCurrentData(*pItem); 262 if (m_pEditorFilters) 263 { 264 /* For each filter => save it to cache: */ 265 const QList<UIDataUSBFilter> filters = m_pEditorFilters->value(); 266 for (int iFilterIndex = 0; iFilterIndex < filters.size(); ++iFilterIndex) 267 { 268 /* Gather and cache new data: */ 269 UIDataUSBFilter filter = filters.at(iFilterIndex); 270 UIDataSettingsMachineUSBFilter newUsbFilterData; 271 newUsbFilterData.m_guiData.m_fActive = filter.m_fActive; 272 newUsbFilterData.m_guiData.m_strName = filter.m_strName; 273 newUsbFilterData.m_guiData.m_strVendorId = filter.m_strVendorId; 274 newUsbFilterData.m_guiData.m_strProductId = filter.m_strProductId; 275 newUsbFilterData.m_guiData.m_strRevision = filter.m_strRevision; 276 newUsbFilterData.m_guiData.m_strManufacturer = filter.m_strManufacturer; 277 newUsbFilterData.m_guiData.m_strProduct = filter.m_strProduct; 278 newUsbFilterData.m_guiData.m_strSerialNumber = filter.m_strSerialNumber; 279 newUsbFilterData.m_guiData.m_enmRemoteMode = filter.m_enmRemoteMode; 280 m_pCache->child(iFilterIndex).cacheCurrentData(newUsbFilterData); 281 } 491 282 } 492 283 … … 543 334 setTabOrder(pWidget, m_pCheckBoxUSB); 544 335 setTabOrder(m_pCheckBoxUSB, m_pEditorController); 545 setTabOrder(m_pEditorController, m_p TreeWidgetFilters);336 setTabOrder(m_pEditorController, m_pEditorFilters); 546 337 } 547 338 … … 550 341 m_pCheckBoxUSB->setToolTip(tr("When checked, enables the virtual USB controller of this machine.")); 551 342 m_pCheckBoxUSB->setText(tr("Enable &USB Controller")); 552 m_pLabelSeparatorFilters->setText(tr("USB Device &Filters"));553 QTreeWidgetItem *pQtreewidgetitem = m_pTreeWidgetFilters->headerItem();554 pQtreewidgetitem->setText(0, tr("[filter]"));555 m_pTreeWidgetFilters->setWhatsThis(tr("Lists all USB filters of this machine. The checkbox "556 "to the left defines whether the particular filter is enabled or not. Use the "557 "context menu or buttons to the right to add or remove USB filters."));558 559 m_pActionNew->setText(tr("Add Empty Filter"));560 m_pActionAdd->setText(tr("Add Filter From Device"));561 m_pActionEdit->setText(tr("Edit Filter"));562 m_pActionRemove->setText(tr("Remove Filter"));563 m_pActionMoveUp->setText(tr("Move Filter Up"));564 m_pActionMoveDown->setText(tr("Move Filter Down"));565 566 m_pActionNew->setToolTip(tr("Adds new USB filter with all fields initially set to empty strings. "567 "Note that such a filter will match any attached USB device."));568 m_pActionAdd->setToolTip(tr("Adds new USB filter with all fields set to the values of the "569 "selected USB device attached to the host PC."));570 m_pActionEdit->setToolTip(tr("Edits selected USB filter."));571 m_pActionRemove->setToolTip(tr("Removes selected USB filter."));572 m_pActionMoveUp->setToolTip(tr("Moves selected USB filter up."));573 m_pActionMoveDown->setToolTip(tr("Moves selected USB filter down."));574 575 m_pActionNew->setToolTip(m_pActionNew->whatsThis());576 m_pActionAdd->setToolTip(m_pActionAdd->whatsThis());577 m_pActionEdit->setToolTip(m_pActionEdit->whatsThis());578 m_pActionRemove->setToolTip(m_pActionRemove->whatsThis());579 m_pActionMoveUp->setToolTip(m_pActionMoveUp->whatsThis());580 m_pActionMoveDown->setToolTip(m_pActionMoveDown->whatsThis());581 582 m_strTrUSBFilterName = tr("New Filter %1", "usb");583 343 } 584 344 … … 596 356 m_pWidgetUSBSettings->setEnabled(isMachineInValidMode() && fEnabled); 597 357 m_pEditorController->setEnabled(isMachineOffline() && fEnabled); 598 if (fEnabled)599 {600 /* If there is no chosen item but there is something to choose => choose it: */601 if (m_pTreeWidgetFilters->currentItem() == 0 && m_pTreeWidgetFilters->topLevelItemCount() != 0)602 m_pTreeWidgetFilters->setCurrentItem(m_pTreeWidgetFilters->topLevelItem(0));603 }604 /* Update current item: */605 sltHandleCurrentItemChange(m_pTreeWidgetFilters->currentItem());606 }607 608 void UIMachineSettingsUSB::sltHandleCurrentItemChange(QTreeWidgetItem *pCurrentItem)609 {610 /* Get selected items: */611 QList<QTreeWidgetItem*> selectedItems = m_pTreeWidgetFilters->selectedItems();612 /* Deselect all selected items first: */613 for (int iItemIndex = 0; iItemIndex < selectedItems.size(); ++iItemIndex)614 selectedItems[iItemIndex]->setSelected(false);615 616 /* If tree-widget is NOT enabled => we should NOT select anything: */617 if (!m_pTreeWidgetFilters->isEnabled())618 return;619 620 /* Select item if requested: */621 if (pCurrentItem)622 pCurrentItem->setSelected(true);623 624 /* Update corresponding action states: */625 m_pActionEdit->setEnabled(pCurrentItem);626 m_pActionRemove->setEnabled(pCurrentItem);627 m_pActionMoveUp->setEnabled(pCurrentItem && m_pTreeWidgetFilters->itemAbove(pCurrentItem));628 m_pActionMoveDown->setEnabled(pCurrentItem && m_pTreeWidgetFilters->itemBelow(pCurrentItem));629 }630 631 void UIMachineSettingsUSB::sltHandleContextMenuRequest(const QPoint &pos)632 {633 QMenu menu;634 if (m_pTreeWidgetFilters->isEnabled())635 {636 menu.addAction(m_pActionNew);637 menu.addAction(m_pActionAdd);638 menu.addSeparator();639 menu.addAction(m_pActionEdit);640 menu.addSeparator();641 menu.addAction(m_pActionRemove);642 menu.addSeparator();643 menu.addAction(m_pActionMoveUp);644 menu.addAction(m_pActionMoveDown);645 }646 if (!menu.isEmpty())647 menu.exec(m_pTreeWidgetFilters->mapToGlobal(pos));648 }649 650 void UIMachineSettingsUSB::sltHandleActivityStateChange(QTreeWidgetItem *pChangedItem)651 {652 /* Check changed USB filter item: */653 UIUSBFilterItem *pItem = static_cast<UIUSBFilterItem*>(pChangedItem);654 AssertPtrReturnVoid(pItem);655 656 /* Update corresponding item: */657 pItem->m_fActive = pItem->checkState(0) == Qt::Checked;658 }659 660 void UIMachineSettingsUSB::sltNewFilter()661 {662 /* Search for the max available filter index: */663 int iMaxFilterIndex = 0;664 const QRegExp regExp(QString("^") + m_strTrUSBFilterName.arg("([0-9]+)") + QString("$"));665 QTreeWidgetItemIterator iterator(m_pTreeWidgetFilters);666 while (*iterator)667 {668 const QString filterName = (*iterator)->text(0);669 const int pos = regExp.indexIn(filterName);670 if (pos != -1)671 iMaxFilterIndex = regExp.cap(1).toInt() > iMaxFilterIndex ?672 regExp.cap(1).toInt() : iMaxFilterIndex;673 ++iterator;674 }675 676 /* Prepare new USB filter data: */677 UIDataSettingsMachineUSBFilter filterData;678 filterData.m_fActive = true;679 filterData.m_strName = m_strTrUSBFilterName.arg(iMaxFilterIndex + 1);680 filterData.m_fHostUSBDevice = false;681 682 /* Add new USB filter item: */683 addUSBFilterItem(filterData, true /* its new? */);684 685 /* Revalidate: */686 revalidate();687 }688 689 void UIMachineSettingsUSB::sltAddFilter()690 {691 m_pMenuUSBDevices->exec(QCursor::pos());692 }693 694 void UIMachineSettingsUSB::sltAddFilterConfirmed(QAction *pAction)695 {696 /* Get USB device: */697 const CUSBDevice usb = m_pMenuUSBDevices->getUSB(pAction);698 if (usb.isNull())699 return;700 701 /* Prepare new USB filter data: */702 UIDataSettingsMachineUSBFilter filterData;703 filterData.m_fActive = true;704 filterData.m_strName = uiCommon().usbDetails(usb);705 filterData.m_fHostUSBDevice = false;706 filterData.m_strVendorId = QString::number(usb.GetVendorId(), 16).toUpper().rightJustified(4, '0');707 filterData.m_strProductId = QString::number(usb.GetProductId(), 16).toUpper().rightJustified(4, '0');708 filterData.m_strRevision = QString::number(usb.GetRevision(), 16).toUpper().rightJustified(4, '0');709 /* The port property depends on the host computer rather than on the USB710 * device itself; for this reason only a few people will want to use it711 * in the filter since the same device plugged into a different socket712 * will not match the filter in this case. */713 #if 0714 filterData.m_strPort = QString().sprintf("%04hX", usb.GetPort());715 #endif716 filterData.m_strManufacturer = usb.GetManufacturer();717 filterData.m_strProduct = usb.GetProduct();718 filterData.m_strSerialNumber = usb.GetSerialNumber();719 filterData.m_strRemote = QString::number(usb.GetRemote());720 721 /* Add new USB filter item: */722 addUSBFilterItem(filterData, true /* its new? */);723 724 /* Revalidate: */725 revalidate();726 }727 728 void UIMachineSettingsUSB::sltEditFilter()729 {730 /* Check current USB filter item: */731 UIUSBFilterItem *pItem = static_cast<UIUSBFilterItem*>(m_pTreeWidgetFilters->currentItem());732 AssertPtrReturnVoid(pItem);733 734 /* Configure USB filter details dialog: */735 UIUSBFilterDetailsEditor dlgFilterDetails(this);736 dlgFilterDetails.setName(pItem->m_strName);737 dlgFilterDetails.setVendorID(pItem->m_strVendorId);738 dlgFilterDetails.setProductID(pItem->m_strProductId);739 dlgFilterDetails.setRevision(pItem->m_strRevision);740 dlgFilterDetails.setManufacturer(pItem->m_strManufacturer);741 dlgFilterDetails.setProduct(pItem->m_strProduct);742 dlgFilterDetails.setSerialNo(pItem->m_strSerialNumber);743 dlgFilterDetails.setPort(pItem->m_strPort);744 const QString strRemote = pItem->m_strRemote.toLower();745 UIRemoteMode enmRemoteMode = UIRemoteMode_Any;746 if (strRemote == "yes" || strRemote == "true" || strRemote == "1")747 enmRemoteMode = UIRemoteMode_On;748 else if (strRemote == "no" || strRemote == "false" || strRemote == "0")749 enmRemoteMode = UIRemoteMode_Off;750 dlgFilterDetails.setRemoteMode(enmRemoteMode);751 752 /* Run USB filter details dialog: */753 if (dlgFilterDetails.exec() == QDialog::Accepted)754 {755 /* Update edited tree-widget item: */756 pItem->m_strName = dlgFilterDetails.name();757 pItem->m_strVendorId = dlgFilterDetails.vendorID();758 pItem->m_strProductId = dlgFilterDetails.productID();759 pItem->m_strRevision = dlgFilterDetails.revision();760 pItem->m_strManufacturer = dlgFilterDetails.manufacturer();761 pItem->m_strProduct = dlgFilterDetails.product();762 pItem->m_strSerialNumber = dlgFilterDetails.serialNo();763 pItem->m_strPort = dlgFilterDetails.port();764 switch (dlgFilterDetails.remoteMode())765 {766 case UIRemoteMode_Any: pItem->m_strRemote = QString(); break;767 case UIRemoteMode_On: pItem->m_strRemote = QString::number(1); break;768 case UIRemoteMode_Off: pItem->m_strRemote = QString::number(0); break;769 default: break;770 }771 pItem->updateFields();772 }773 }774 775 void UIMachineSettingsUSB::sltRemoveFilter()776 {777 /* Check current USB filter item: */778 QTreeWidgetItem *pItem = m_pTreeWidgetFilters->currentItem();779 AssertPtrReturnVoid(pItem);780 781 /* Delete corresponding item: */782 delete pItem;783 784 /* Update current item: */785 sltHandleCurrentItemChange(m_pTreeWidgetFilters->currentItem());786 787 /* Revalidate: */788 revalidate();789 }790 791 void UIMachineSettingsUSB::sltMoveFilterUp()792 {793 /* Check current USB filter item: */794 QTreeWidgetItem *pItem = m_pTreeWidgetFilters->currentItem();795 AssertPtrReturnVoid(pItem);796 797 /* Move the item up: */798 const int iIndex = m_pTreeWidgetFilters->indexOfTopLevelItem(pItem);799 QTreeWidgetItem *pTakenItem = m_pTreeWidgetFilters->takeTopLevelItem(iIndex);800 Assert(pItem == pTakenItem);801 m_pTreeWidgetFilters->insertTopLevelItem(iIndex - 1, pTakenItem);802 803 /* Make sure moved item still chosen: */804 m_pTreeWidgetFilters->setCurrentItem(pTakenItem);805 }806 807 void UIMachineSettingsUSB::sltMoveFilterDown()808 {809 /* Check current USB filter item: */810 QTreeWidgetItem *pItem = m_pTreeWidgetFilters->currentItem();811 AssertPtrReturnVoid(pItem);812 813 /* Move the item down: */814 const int iIndex = m_pTreeWidgetFilters->indexOfTopLevelItem(pItem);815 QTreeWidgetItem *pTakenItem = m_pTreeWidgetFilters->takeTopLevelItem(iIndex);816 Assert(pItem == pTakenItem);817 m_pTreeWidgetFilters->insertTopLevelItem(iIndex + 1, pTakenItem);818 819 /* Make sure moved item still chosen: */820 m_pTreeWidgetFilters->setCurrentItem(pTakenItem);821 358 } 822 359 … … 869 406 pLayoutUSBSettings->addWidget(m_pEditorController); 870 407 871 /* Prepare separator: */ 872 m_pLabelSeparatorFilters = new QILabelSeparator(m_pWidgetUSBSettings); 873 if (m_pLabelSeparatorFilters) 874 pLayoutUSBSettings->addWidget(m_pLabelSeparatorFilters); 875 876 /* Prepare USB filters layout: */ 877 m_pLayoutFilters = new QHBoxLayout; 878 if (m_pLayoutFilters) 879 { 880 m_pLayoutFilters->setContentsMargins(0, 0, 0, 0); 881 m_pLayoutFilters->setSpacing(3); 882 883 /* Prepare USB filters tree-widget: */ 884 prepareFiltersTreeWidget(); 885 /* Prepare USB filters toolbar: */ 886 prepareFiltersToolbar(); 887 888 pLayoutUSBSettings->addLayout(m_pLayoutFilters); 889 } 408 /* Prepare USB filters editor: */ 409 m_pEditorFilters = new UIUSBFiltersEditor(m_pWidgetUSBSettings); 410 if (m_pEditorFilters) 411 pLayoutUSBSettings->addWidget(m_pEditorFilters); 890 412 } 891 413 892 414 pLayoutMain->addWidget(m_pWidgetUSBSettings, 1, 1, 1, 2); 893 415 } 894 }895 }896 897 void UIMachineSettingsUSB::prepareFiltersTreeWidget()898 {899 /* Prepare USB filters tree-widget: */900 m_pTreeWidgetFilters = new QITreeWidget(m_pWidgetUSBSettings);901 if (m_pTreeWidgetFilters)902 {903 if (m_pLabelSeparatorFilters)904 m_pLabelSeparatorFilters->setBuddy(m_pTreeWidgetFilters);905 m_pTreeWidgetFilters->header()->hide();906 m_pTreeWidgetFilters->setRootIsDecorated(false);907 m_pTreeWidgetFilters->setContextMenuPolicy(Qt::CustomContextMenu);908 909 m_pLayoutFilters->addWidget(m_pTreeWidgetFilters);910 }911 }912 913 void UIMachineSettingsUSB::prepareFiltersToolbar()914 {915 /* Prepare USB filters toolbar: */916 m_pToolbarFilters = new QIToolBar(m_pWidgetUSBSettings);917 if (m_pToolbarFilters)918 {919 const int iIconMetric = QApplication::style()->pixelMetric(QStyle::PM_SmallIconSize);920 m_pToolbarFilters->setIconSize(QSize(iIconMetric, iIconMetric));921 m_pToolbarFilters->setOrientation(Qt::Vertical);922 923 /* Prepare 'New USB Filter' action: */924 m_pActionNew = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_new_16px.png",925 ":/usb_new_disabled_16px.png"),926 QString(), this, SLOT(sltNewFilter()));927 if (m_pActionNew)928 m_pActionNew->setShortcuts(QList<QKeySequence>() << QKeySequence("Ins") << QKeySequence("Ctrl+N"));929 930 /* Prepare 'Add USB Filter' action: */931 m_pActionAdd = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_add_16px.png",932 ":/usb_add_disabled_16px.png"),933 QString(), this, SLOT(sltAddFilter()));934 if (m_pActionAdd)935 m_pActionAdd->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Ins") << QKeySequence("Ctrl+A"));936 937 /* Prepare 'Edit USB Filter' action: */938 m_pActionEdit = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_filter_edit_16px.png",939 ":/usb_filter_edit_disabled_16px.png"),940 QString(), this, SLOT(sltEditFilter()));941 if (m_pActionEdit)942 m_pActionEdit->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Return") << QKeySequence("Ctrl+Return"));943 944 /* Prepare 'Remove USB Filter' action: */945 m_pActionRemove = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_remove_16px.png",946 ":/usb_remove_disabled_16px.png"),947 QString(), this, SLOT(sltRemoveFilter()));948 if (m_pActionRemove)949 m_pActionRemove->setShortcuts(QList<QKeySequence>() << QKeySequence("Del") << QKeySequence("Ctrl+R"));950 951 /* Prepare 'Move USB Filter Up' action: */952 m_pActionMoveUp = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_moveup_16px.png",953 ":/usb_moveup_disabled_16px.png"),954 QString(), this, SLOT(sltMoveFilterUp()));955 if (m_pActionMoveUp)956 m_pActionMoveUp->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Up") << QKeySequence("Ctrl+Up"));957 958 /* Prepare 'Move USB Filter Down' action: */959 m_pActionMoveDown = m_pToolbarFilters->addAction(UIIconPool::iconSet(":/usb_movedown_16px.png",960 ":/usb_movedown_disabled_16px.png"),961 QString(), this, SLOT(sltMoveFilterDown()));962 if (m_pActionMoveDown)963 m_pActionMoveDown->setShortcuts(QList<QKeySequence>() << QKeySequence("Alt+Down") << QKeySequence("Ctrl+Down"));964 965 /* Prepare USB devices menu: */966 m_pMenuUSBDevices = new VBoxUSBMenu(this);967 968 m_pLayoutFilters->addWidget(m_pToolbarFilters);969 416 } 970 417 } … … 977 424 connect(m_pEditorController, &UIUSBControllerEditor::sigValueChanged, 978 425 this, &UIMachineSettingsUSB::revalidate); 426 connect(m_pEditorFilters, &UIUSBFiltersEditor::sigValueChanged, 427 this, &UIMachineSettingsUSB::revalidate); 979 428 980 429 /* Configure widget connections: */ 981 430 connect(m_pCheckBoxUSB, &QCheckBox::toggled, 982 431 this, &UIMachineSettingsUSB::sltHandleUsbAdapterToggle); 983 connect(m_pTreeWidgetFilters, &QITreeWidget::currentItemChanged,984 this, &UIMachineSettingsUSB::sltHandleCurrentItemChange);985 connect(m_pTreeWidgetFilters, &QITreeWidget::customContextMenuRequested,986 this, &UIMachineSettingsUSB::sltHandleContextMenuRequest);987 connect(m_pTreeWidgetFilters, &QITreeWidget::itemDoubleClicked,988 this, &UIMachineSettingsUSB::sltEditFilter);989 connect(m_pTreeWidgetFilters, &QITreeWidget::itemChanged,990 this, &UIMachineSettingsUSB::sltHandleActivityStateChange);991 992 /* Configure USB device menu connections: */993 connect(m_pMenuUSBDevices, &VBoxUSBMenu::triggered,994 this, &UIMachineSettingsUSB::sltAddFilterConfirmed);995 432 } 996 433 997 434 void UIMachineSettingsUSB::cleanup() 998 435 { 999 /* Cleanup USB devices menu: */1000 delete m_pMenuUSBDevices;1001 m_pMenuUSBDevices = 0;1002 1003 436 /* Cleanup cache: */ 1004 437 delete m_pCache; 1005 438 m_pCache = 0; 1006 }1007 1008 void UIMachineSettingsUSB::addUSBFilterItem(const UIDataSettingsMachineUSBFilter &filterData, bool fChoose)1009 {1010 /* Create USB filter item: */1011 UIUSBFilterItem *pItem = new UIUSBFilterItem(m_pTreeWidgetFilters);1012 AssertPtrReturnVoid(pItem);1013 {1014 /* Configure item: */1015 pItem->setCheckState(0, filterData.m_fActive ? Qt::Checked : Qt::Unchecked);1016 pItem->m_strName = filterData.m_strName;1017 pItem->m_strVendorId = filterData.m_strVendorId;1018 pItem->m_strProductId = filterData.m_strProductId;1019 pItem->m_strRevision = filterData.m_strRevision;1020 pItem->m_strManufacturer = filterData.m_strManufacturer;1021 pItem->m_strProduct = filterData.m_strProduct;1022 pItem->m_strSerialNumber = filterData.m_strSerialNumber;1023 pItem->m_strPort = filterData.m_strPort;1024 pItem->m_strRemote = filterData.m_strRemote;1025 pItem->m_enmAction = filterData.m_enmAction;1026 pItem->m_fHostUSBDevice = filterData.m_fHostUSBDevice;1027 pItem->m_enmHostUSBDeviceState = filterData.m_enmHostUSBDeviceState;1028 pItem->updateFields();1029 1030 /* Select this item if it's new: */1031 if (fChoose)1032 {1033 m_pTreeWidgetFilters->scrollToItem(pItem);1034 m_pTreeWidgetFilters->setCurrentItem(pItem);1035 sltHandleCurrentItemChange(pItem);1036 }1037 }1038 439 } 1039 440 … … 1310 711 { 1311 712 /* Create filter: */ 1312 CUSBDeviceFilter comFilter = comFiltersObject.CreateDeviceFilter(filterData.m_ strName);713 CUSBDeviceFilter comFilter = comFiltersObject.CreateDeviceFilter(filterData.m_guiData.m_strName); 1313 714 fSuccess = comFiltersObject.isOk() && comFilter.isNotNull(); 1314 715 … … 1321 722 if (fSuccess) 1322 723 { 1323 comFilter.SetActive(filterData.m_ fActive);724 comFilter.SetActive(filterData.m_guiData.m_fActive); 1324 725 fSuccess = comFilter.isOk(); 1325 726 } … … 1327 728 if (fSuccess) 1328 729 { 1329 comFilter.SetVendorId(filterData.m_ strVendorId);730 comFilter.SetVendorId(filterData.m_guiData.m_strVendorId); 1330 731 fSuccess = comFilter.isOk(); 1331 732 } … … 1333 734 if (fSuccess) 1334 735 { 1335 comFilter.SetProductId(filterData.m_ strProductId);736 comFilter.SetProductId(filterData.m_guiData.m_strProductId); 1336 737 fSuccess = comFilter.isOk(); 1337 738 } … … 1339 740 if (fSuccess) 1340 741 { 1341 comFilter.SetRevision(filterData.m_ strRevision);742 comFilter.SetRevision(filterData.m_guiData.m_strRevision); 1342 743 fSuccess = comFilter.isOk(); 1343 744 } … … 1345 746 if (fSuccess) 1346 747 { 1347 comFilter.SetManufacturer(filterData.m_ strManufacturer);748 comFilter.SetManufacturer(filterData.m_guiData.m_strManufacturer); 1348 749 fSuccess = comFilter.isOk(); 1349 750 } … … 1351 752 if (fSuccess) 1352 753 { 1353 comFilter.SetProduct(filterData.m_ strProduct);754 comFilter.SetProduct(filterData.m_guiData.m_strProduct); 1354 755 fSuccess = comFilter.isOk(); 1355 756 } … … 1357 758 if (fSuccess) 1358 759 { 1359 comFilter.SetSerialNumber(filterData.m_ strSerialNumber);760 comFilter.SetSerialNumber(filterData.m_guiData.m_strSerialNumber); 1360 761 fSuccess = comFilter.isOk(); 1361 762 } … … 1363 764 if (fSuccess) 1364 765 { 1365 comFilter.SetPort(filterData.m_ strPort);766 comFilter.SetPort(filterData.m_guiData.m_strPort); 1366 767 fSuccess = comFilter.isOk(); 1367 768 } … … 1369 770 if (fSuccess) 1370 771 { 1371 comFilter.SetRemote(filterData.m_strRemote); 772 QString strRemote; 773 switch (filterData.m_guiData.m_enmRemoteMode) 774 { 775 case UIRemoteMode_On: strRemote = "1"; break; 776 case UIRemoteMode_Off: strRemote = "0"; break; 777 default: break; 778 } 779 comFilter.SetRemote(strRemote); 1372 780 fSuccess = comFilter.isOk(); 1373 781 } … … 1391 799 return fSuccess; 1392 800 } 1393 1394 1395 #include "UIMachineSettingsUSB.moc" -
trunk/src/VBox/Frontends/VirtualBox/src/settings/machine/UIMachineSettingsUSB.h
r95247 r95277 27 27 /* Forward declarations: */ 28 28 class QCheckBox; 29 class QHBoxLayout;30 class QTreeWidgetItem;31 class QILabelSeparator;32 class QIToolBar;33 class QITreeWidget;34 class VBoxUSBMenu;35 29 class UIUSBControllerEditor; 30 class UIUSBFiltersEditor; 36 31 struct UIDataSettingsMachineUSB; 37 32 struct UIDataSettingsMachineUSBFilter; … … 90 85 void sltHandleUsbAdapterToggle(bool fEnabled); 91 86 92 /** Handles USB filter tree @a pCurrentItem change. */93 void sltHandleCurrentItemChange(QTreeWidgetItem *pCurrentItem);94 /** Handles context menu request for @a position of USB filter tree. */95 void sltHandleContextMenuRequest(const QPoint &position);96 /** Handles USB filter tree activity state change for @a pChangedItem. */97 void sltHandleActivityStateChange(QTreeWidgetItem *pChangedItem);98 99 /** Handles command to add new USB filter. */100 void sltNewFilter();101 /** Handles command to add existing USB filter. */102 void sltAddFilter();103 /** Handles command to edit USB filter. */104 void sltEditFilter();105 /** Handles command to confirm add of existing USB filter defined by @a pAction. */106 void sltAddFilterConfirmed(QAction *pAction);107 /** Handles command to remove chosen USB filter. */108 void sltRemoveFilter();109 /** Handles command to move chosen USB filter up. */110 void sltMoveFilterUp();111 /** Handles command to move chosen USB filter down. */112 void sltMoveFilterDown();113 114 87 private: 115 88 … … 118 91 /** Prepares widgets. */ 119 92 void prepareWidgets(); 120 /** Prepares filters tree-widget. */121 void prepareFiltersTreeWidget();122 /** Prepares filters toolbar. */123 void prepareFiltersToolbar();124 93 /** Prepares connections. */ 125 94 void prepareConnections(); 126 95 /** Cleanups all. */ 127 96 void cleanup(); 128 129 /** Adds USB filter item based on a given @a filterData, fChoose if requested. */130 void addUSBFilterItem(const UIDataSettingsMachineUSBFilter &filterData, bool fChoose);131 97 132 98 /** Saves existing data from cache. */ … … 141 107 bool createUSBFilter(CUSBDeviceFilters &comFiltersObject, int iPosition, const UIDataSettingsMachineUSBFilter &filterData); 142 108 143 /** Holds the "New Filter %1" translation tag. */144 QString m_strTrUSBFilterName;145 146 109 /** Holds the page data cache instance. */ 147 110 UISettingsCacheMachineUSB *m_pCache; … … 155 118 /** Holds the USB controller editor instance. */ 156 119 UIUSBControllerEditor *m_pEditorController; 157 /** Holds the USB widget separator instance. */ 158 QILabelSeparator *m_pLabelSeparatorFilters; 159 /** Holds the USB filters layout instance. */ 160 QHBoxLayout *m_pLayoutFilters; 161 /** Holds the USB filters tree-widget instance. */ 162 QITreeWidget *m_pTreeWidgetFilters; 163 /** Holds the USB filters toolbar instance. */ 164 QIToolBar *m_pToolbarFilters; 165 /** Holds the New action instance. */ 166 QAction *m_pActionNew; 167 /** Holds the Add action instance. */ 168 QAction *m_pActionAdd; 169 /** Holds the Edit action instance. */ 170 QAction *m_pActionEdit; 171 /** Holds the Remove action instance. */ 172 QAction *m_pActionRemove; 173 /** Holds the Move Up action instance. */ 174 QAction *m_pActionMoveUp; 175 /** Holds the Move Down action instance. */ 176 QAction *m_pActionMoveDown; 177 /** Holds the USB devices menu instance. */ 178 VBoxUSBMenu *m_pMenuUSBDevices; 120 /** Holds the USB filters editor instance. */ 121 UIUSBFiltersEditor *m_pEditorFilters; 179 122 /** @} */ 180 123 };
Note:
See TracChangeset
for help on using the changeset viewer.