summaryrefslogtreecommitdiffstats
path: root/kcontrol/hwmanager/hwdevicetray.cpp
diff options
context:
space:
mode:
authorTimothy Pearson <kb9vqf@pearsoncomputing.net>2015-09-21 15:39:58 -0500
committerTimothy Pearson <kb9vqf@pearsoncomputing.net>2015-09-21 15:39:58 -0500
commitb5cb2797d65f2541a4c48ea00e6c325bb375ea46 (patch)
tree61dad727529d9a69977f44a05aca3a719422558c /kcontrol/hwmanager/hwdevicetray.cpp
parentc73eb5f814d1096cd398fbec3084f816ba8a7269 (diff)
downloadtdebase-b5cb2797d65f2541a4c48ea00e6c325bb375ea46.tar.gz
tdebase-b5cb2797d65f2541a4c48ea00e6c325bb375ea46.zip
Add new hardware device tray application
Allow removable media action request popups to be suppressed
Diffstat (limited to 'kcontrol/hwmanager/hwdevicetray.cpp')
-rw-r--r--kcontrol/hwmanager/hwdevicetray.cpp407
1 files changed, 407 insertions, 0 deletions
diff --git a/kcontrol/hwmanager/hwdevicetray.cpp b/kcontrol/hwmanager/hwdevicetray.cpp
new file mode 100644
index 000000000..6927bc12e
--- /dev/null
+++ b/kcontrol/hwmanager/hwdevicetray.cpp
@@ -0,0 +1,407 @@
+/*
+ * Copyright 2015 Timothy Pearson <kb9vqf@pearsoncomputing.net>
+ *
+ * This file is part of hwdevicetray, the TDE Hardware Device Monitor System Tray Application
+ *
+ * hwdevicetray is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation, either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * hwdevicetray is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with cryptocardwatcher. If not, see http://www.gnu.org/licenses/.
+ */
+
+#include <tqtimer.h>
+#include <tqimage.h>
+#include <tqtooltip.h>
+#include <tqfileinfo.h>
+
+#include <krun.h>
+#include <tdeaction.h>
+#include <tdeapplication.h>
+#include <kcmultidialog.h>
+#include <kdebug.h>
+#include <khelpmenu.h>
+#include <kiconloader.h>
+#include <tdelocale.h>
+#include <tdepopupmenu.h>
+#include <kstdaction.h>
+#include <kstdguiitem.h>
+#include <tdeglobal.h>
+#include <tdemessagebox.h>
+#include <kpassivepopup.h>
+#include <kstandarddirs.h>
+
+#include <dcopclient.h>
+
+#include <cstdlib>
+#include <unistd.h>
+
+#include "hwdevicetray_configdialog.h"
+
+#include "hwdevicetray.h"
+
+HwDeviceSystemTray::HwDeviceSystemTray(TQWidget* parent, const char *name)
+ : KSystemTray(parent, name) {
+
+ // Create notifier
+ m_hardwareNotifierContainer = new TDEPassivePopupStackContainer();
+ connect(m_hardwareNotifierContainer, TQT_SIGNAL(popupClicked(KPassivePopup*, TQPoint, TQString)), this, TQT_SLOT(devicePopupClicked(KPassivePopup*, TQPoint, TQString)));
+
+ // Create help submenu
+ m_help = new KHelpMenu(this, TDEGlobal::instance()->aboutData(), false, actionCollection());
+ TDEPopupMenu *help = m_help->menu();
+ help->connectItem(KHelpMenu::menuHelpContents, this, TQT_SLOT(slotHelpContents()));
+
+ setPixmap(KSystemTray::loadIcon("kcmdevices"));
+ setAlignment(Qt::AlignHCenter | Qt::AlignVCenter);
+ connect(this, TQT_SIGNAL(quitSelected()), this, TQT_SLOT(_quit()));
+ TQToolTip::add(this, i18n("Hardware device monitor"));
+ m_parent = parent;
+
+ globalKeys = new TDEGlobalAccel(TQT_TQOBJECT(this));
+ TDEGlobalAccel* keys = globalKeys;
+ #include "hwdevicetray_bindings.cpp"
+ // the keys need to be read from tdeglobals, not kickerrc
+ globalKeys->readSettings();
+ globalKeys->setEnabled(true);
+ globalKeys->updateConnections();
+
+ connect(kapp, TQT_SIGNAL(settingsChanged(int)), TQT_SLOT(slotSettingsChanged(int)));
+
+ new TDEActionMenu(i18n("Open Device"), SmallIcon("connect_creating", TQIconSet::Automatic), actionCollection(), "mount_menu");
+ new TDEActionMenu(i18n("Eject Device"), SmallIcon("connect_no", TQIconSet::Automatic), actionCollection(), "unmount_menu");
+
+#ifdef __TDE_HAVE_TDEHWLIB
+ TDEHardwareDevices *hwdevices = TDEGlobal::hardwareDevices();
+ connect(hwdevices, TQT_SIGNAL(hardwareAdded(TDEGenericDevice*)), this, TQT_SLOT(deviceAdded(TDEGenericDevice*)));
+ connect(hwdevices, TQT_SIGNAL(hardwareRemoved(TDEGenericDevice*)), this, TQT_SLOT(deviceRemoved(TDEGenericDevice*)));
+ connect(hwdevices, TQT_SIGNAL(hardwareUpdated(TDEGenericDevice*)), this, TQT_SLOT(deviceChanged(TDEGenericDevice*)));
+#endif
+}
+
+HwDeviceSystemTray::~HwDeviceSystemTray() {
+ delete m_hardwareNotifierContainer;
+}
+
+/*!
+ * \b TQT_SLOT which called if hwdevicetray is exited by the user. In this case the user
+ * is asked through a yes/no box if "HwDeviceTray should start automatically on log in" and the
+ * result is written to the KDE configfile.
+ */
+void HwDeviceSystemTray::_quit () {
+ r_config = new KSimpleConfig("hwdevicetrayrc");
+
+ TQString tmp1 = i18n ("Start hardware device tray automatically when you log in?");
+ int tmp2 = KMessageBox::questionYesNo (0, tmp1, i18n("Question"), i18n("Start Automatically"), i18n("Do Not Start"));
+ r_config->setGroup("General");
+ r_config->writeEntry ("Autostart", tmp2 == KMessageBox::Yes);
+ r_config->sync ();
+
+ exit(0);
+}
+
+void HwDeviceSystemTray::resizeTrayIcon () {
+ // Honor Free Desktop specifications that allow for arbitrary system tray icon sizes
+ TQPixmap origpixmap;
+ TQPixmap scaledpixmap;
+ TQImage newIcon;
+ origpixmap = KSystemTray::loadSizedIcon("kcmdevices", width());
+ newIcon = origpixmap;
+ newIcon = newIcon.smoothScale(width(), height());
+ scaledpixmap = newIcon;
+ setPixmap(scaledpixmap);
+}
+
+void HwDeviceSystemTray::resizeEvent (TQResizeEvent *) {
+ // Honor Free Desktop specifications that allow for arbitrary system tray icon sizes
+ resizeTrayIcon();
+}
+
+void HwDeviceSystemTray::showEvent (TQShowEvent *) {
+ // Honor Free Desktop specifications that allow for arbitrary system tray icon sizes
+ resizeTrayIcon();
+}
+
+void HwDeviceSystemTray::mousePressEvent(TQMouseEvent* e) {
+ // Popup the context menu with left-click
+ if (e->button() == Qt::LeftButton) {
+ contextMenuAboutToShow(contextMenu());
+ contextMenu()->popup(e->globalPos());
+ e->accept();
+ return;
+ }
+
+ KSystemTray::mousePressEvent(e);
+}
+
+bool HwDeviceSystemTray::isMonitoredDevice(TDEStorageDevice* sdevice) {
+ // Type selection logic largely duplicated from the media manager tdeioslave
+ if ((sdevice->isDiskOfType(TDEDiskDeviceType::LUKS)
+ || sdevice->checkDiskStatus(TDEDiskDeviceStatus::ContainsFilesystem)
+ || sdevice->isDiskOfType(TDEDiskDeviceType::CDAudio)
+ || sdevice->checkDiskStatus(TDEDiskDeviceStatus::Blank))
+ && !sdevice->checkDiskStatus(TDEDiskDeviceStatus::UsedByDevice)
+ && !sdevice->checkDiskStatus(TDEDiskDeviceStatus::Hidden)
+ && (sdevice->isDiskOfType(TDEDiskDeviceType::HDD)
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDROM))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDR))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDMO))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDMRRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDMRRWW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDROM))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDRAM))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDR))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDRDL))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDRWDL))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDPLUSR))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDPLUSRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDPLUSRDL))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDPLUSRWDL))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::BDROM))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::BDR))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::BDRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::HDDVDROM))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::HDDVDR))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::HDDVDRW))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDAudio))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::CDVideo))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::DVDVideo))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::BDVideo))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::Floppy))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::Zip))
+ || (sdevice->isDiskOfType(TDEDiskDeviceType::Jaz)))) {
+ return true;
+ }
+ else {
+ return false;
+ }
+}
+
+void HwDeviceSystemTray::contextMenuAboutToShow(TDEPopupMenu* menu) {
+ menu->clear();
+ menu->setCheckable(true);
+
+ populateMenu(menu);
+
+ menu->insertTitle(SmallIcon("configure"), i18n("Global Configuration"));
+
+ TDEAction *actHardwareConfig = new TDEAction(i18n("Configure Hardware..."), SmallIconSet("kcmpci"), TDEShortcut(), TQT_TQOBJECT(this), TQT_SLOT(slotHardwareConfig()), actionCollection());
+ actHardwareConfig->plug(menu);
+
+ TDEAction *actShortcutKeys = new TDEAction(i18n("Configure Shortcut Keys..."), SmallIconSet("configure"), TDEShortcut(), TQT_TQOBJECT(this), TQT_SLOT(slotEditShortcutKeys()), actionCollection());
+ actShortcutKeys->plug(menu);
+
+ menu->insertItem(SmallIcon("help"), KStdGuiItem::help().text(), m_help->menu());
+ TDEAction *quitAction = actionCollection()->action(KStdAction::name(KStdAction::Quit));
+ quitAction->plug(menu);
+
+ m_menu = menu;
+}
+
+void HwDeviceSystemTray::configChanged() {
+ //
+}
+
+void HwDeviceSystemTray::populateMenu(TDEPopupMenu* menu) {
+ int lastMountIndex;
+ int lastUnmountIndex;
+ TDEGenericDevice *hwdevice;
+
+ TDEActionMenu* mountDiskActionMenu = static_cast<TDEActionMenu*>(actionCollection()->action("mount_menu"));
+ mountDiskActionMenu->popupMenu()->clear();
+ m_mountMenuIndexMap.clear();
+ TDEActionMenu* unmountDiskActionMenu = static_cast<TDEActionMenu*>(actionCollection()->action("unmount_menu"));
+ unmountDiskActionMenu->popupMenu()->clear();
+ m_mountMenuIndexMap.clear();
+
+ menu->insertTitle(SmallIcon("drive-harddisk"), i18n("Storage Devices"));
+
+ // Find all storage devices and add them to the popup menu
+ lastMountIndex = 1;
+ lastUnmountIndex = 1;
+ TDEHardwareDevices *hwdevices = TDEGlobal::hardwareDevices();
+ TDEGenericHardwareList diskDeviceList = hwdevices->listByDeviceClass(TDEGenericDeviceType::Disk);
+ for (hwdevice = diskDeviceList.first(); hwdevice; hwdevice = diskDeviceList.next()) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(hwdevice);
+ if (isMonitoredDevice(sdevice)) {
+ lastMountIndex = mountDiskActionMenu->popupMenu()->insertItem(hwdevice->icon(TDEIcon::SizeSmall), i18n("%1 (%2)").arg(sdevice->friendlyName(), sdevice->deviceNode()));
+ mountDiskActionMenu->popupMenu()->connectItem(lastMountIndex, this, TQT_SLOT(slotMountDevice(int)));
+ m_mountMenuIndexMap[lastMountIndex] = sdevice->diskUUID();
+ if (sdevice->mountPath() != TQString::null) {
+ lastUnmountIndex = unmountDiskActionMenu->popupMenu()->insertItem(hwdevice->icon(TDEIcon::SizeSmall), i18n("%1 (%2)").arg(sdevice->friendlyName(), sdevice->deviceNode()));
+ unmountDiskActionMenu->popupMenu()->connectItem(lastUnmountIndex, this, TQT_SLOT(slotUnmountDevice(int)));
+ m_unmountMenuIndexMap[lastUnmountIndex] = sdevice->diskUUID();
+ }
+ }
+ }
+
+ if (lastMountIndex == 0) {
+ mountDiskActionMenu->setEnabled(false);
+ }
+ else {
+ mountDiskActionMenu->setEnabled(true);
+ }
+ if (lastUnmountIndex == 0) {
+ unmountDiskActionMenu->setEnabled(false);
+ }
+ else {
+ unmountDiskActionMenu->setEnabled(true);
+ }
+
+ mountDiskActionMenu->plug(menu);
+ unmountDiskActionMenu->plug(menu);
+}
+
+void HwDeviceSystemTray::slotMountDevice(int parameter)
+{
+ TDEGenericDevice *hwdevice;
+ TQString uuid = m_mountMenuIndexMap[parameter];
+ if (uuid != "") {
+ TDEHardwareDevices *hwdevices = TDEGlobal::hardwareDevices();
+ TDEGenericHardwareList diskDeviceList = hwdevices->listByDeviceClass(TDEGenericDeviceType::Disk);
+ for (hwdevice = diskDeviceList.first(); hwdevice; hwdevice = diskDeviceList.next()) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(hwdevice);
+ if (sdevice->diskUUID() == uuid) {
+ if (sdevice->isDiskOfType(TDEDiskDeviceType::Camera)) {
+ new KRun(TQString("system:/media/%1").arg(sdevice->friendlyName()));
+ }
+ else {
+ new KRun(TQString("system:/media/%1").arg(TQFileInfo(sdevice->deviceNode()).baseName(true)));
+ }
+ return;
+ }
+ }
+ }
+}
+
+void HwDeviceSystemTray::slotUnmountDevice(int parameter)
+{
+ TDEGenericDevice *hwdevice;
+ TQString uuid = m_unmountMenuIndexMap[parameter];
+ if (uuid != "") {
+ TDEHardwareDevices *hwdevices = TDEGlobal::hardwareDevices();
+ TDEGenericHardwareList diskDeviceList = hwdevices->listByDeviceClass(TDEGenericDeviceType::Disk);
+ for (hwdevice = diskDeviceList.first(); hwdevice; hwdevice = diskDeviceList.next()) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(hwdevice);
+ if (sdevice->diskUUID() == uuid) {
+ if (sdevice->mountPath() != TQString::null) {
+ int retcode;
+ TQString errstr;
+ if (!sdevice->unmountDevice(&errstr, &retcode)) {
+ KMessageBox::error(0, i18n("<qt><b>Unable to eject device</b><p>Detailed error information:<br>%1 (code %2)</qt>").arg(errstr).arg(retcode), i18n("Eject Failed"));
+ }
+ return;
+ }
+ }
+ }
+ }
+}
+
+void HwDeviceSystemTray::slotHardwareConfig() {
+ KCMultiDialog *kcm = new KCMultiDialog(KDialogBase::Plain, i18n("Configure"), this);
+
+ kcm->addModule("hwmanager");
+ kcm->setPlainCaption(i18n("Configure Hardware"));
+ kcm->exec();
+}
+
+void HwDeviceSystemTray::slotSettingsChanged(int category) {
+ if (category == (int) TDEApplication::SETTINGS_SHORTCUTS) {
+ globalKeys->readSettings();
+ globalKeys->updateConnections();
+ }
+}
+
+void HwDeviceSystemTray::slotEditShortcutKeys() {
+ ConfigDialog *dlg = new ConfigDialog(globalKeys, true);
+
+ if (dlg->exec() == TQDialog::Accepted) {
+ dlg->commitShortcuts();
+ globalKeys->writeSettings(0, true);
+ globalKeys->updateConnections();
+ }
+
+ delete dlg;
+}
+
+void HwDeviceSystemTray::deviceAdded(TDEGenericDevice* device) {
+#ifdef __TDE_HAVE_TDEHWLIB
+ if (device->type() == TDEGenericDeviceType::Disk) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(device);
+ if (isMonitoredDevice(sdevice)) {
+ m_hardwareNotifierContainer->displayMessage(
+ i18n("A disk device has been added!"),
+ i18n("%1 (%2)").arg(sdevice->friendlyName(), sdevice->deviceNode()), SmallIcon("drive-harddisk"),
+ 0, 0, "ADD: " + sdevice->diskUUID());
+ }
+ }
+#endif
+}
+
+void HwDeviceSystemTray::deviceRemoved(TDEGenericDevice* device) {
+#ifdef __TDE_HAVE_TDEHWLIB
+ if (device->type() == TDEGenericDeviceType::Disk) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(device);
+ if (isMonitoredDevice(sdevice)) {
+ m_hardwareNotifierContainer->displayMessage(
+ i18n("A disk device has been removed!"),
+ i18n("%1 (%2)").arg(sdevice->friendlyName(), sdevice->deviceNode()), SmallIcon("drive-harddisk"),
+ 0, 0, "REMOVE: " + sdevice->diskUUID());
+ }
+ }
+#endif
+}
+
+void HwDeviceSystemTray::deviceChanged(TDEGenericDevice* device) {
+#ifdef __TDE_HAVE_TDEHWLIB
+ if (device->type() == TDEGenericDeviceType::Disk) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(device);
+ if (isMonitoredDevice(sdevice)) {
+ m_hardwareNotifierContainer->displayMessage(
+ i18n("A disk device has been changed!"),
+ i18n("%1 (%2)").arg(sdevice->friendlyName(), sdevice->deviceNode()), SmallIcon("drive-harddisk"),
+ 0, 0, "CHANGE: " + sdevice->diskUUID());
+ }
+ }
+#endif
+}
+
+void HwDeviceSystemTray::devicePopupClicked(KPassivePopup* popup, TQPoint point, TQString uuid) {
+ TDEGenericDevice *hwdevice;
+ if (uuid.startsWith("ADD: ")) {
+ uuid = uuid.right(uuid.length() - strlen("ADD: "));
+ if (uuid != "") {
+ TDEHardwareDevices *hwdevices = TDEGlobal::hardwareDevices();
+ TDEGenericHardwareList diskDeviceList = hwdevices->listByDeviceClass(TDEGenericDeviceType::Disk);
+ for (hwdevice = diskDeviceList.first(); hwdevice; hwdevice = diskDeviceList.next()) {
+ TDEStorageDevice* sdevice = static_cast<TDEStorageDevice*>(hwdevice);
+ if (sdevice->diskUUID() == uuid) {
+ // Pop up full media notification dialog
+ DCOPClient* dcopClient = TDEApplication::dcopClient();
+ TQByteArray data;
+ TQDataStream arg(data, IO_WriteOnly);
+ bool allowNotification = true;
+ arg << TQFileInfo(sdevice->deviceNode()).baseName(true);
+ arg << allowNotification;
+ dcopClient->send("kded", "medianotifier", "onMediumChange(TQString, bool)", data);
+ return;
+ }
+ }
+ }
+ }
+}
+
+void HwDeviceSystemTray::slotHelpContents() {
+ kapp->invokeHelp(TQString::null, "hwdevicetray");
+}
+
+#include "hwdevicetray.moc" \ No newline at end of file