1 | /* $Id: UIMediumItem.cpp 103771 2024-03-11 15:16:04Z vboxsync $ */
|
---|
2 | /** @file
|
---|
3 | * VBox Qt GUI - UIMediumItem class implementation.
|
---|
4 | */
|
---|
5 |
|
---|
6 | /*
|
---|
7 | * Copyright (C) 2009-2023 Oracle and/or its affiliates.
|
---|
8 | *
|
---|
9 | * This file is part of VirtualBox base platform packages, as
|
---|
10 | * available from https://www.virtualbox.org.
|
---|
11 | *
|
---|
12 | * This program is free software; you can redistribute it and/or
|
---|
13 | * modify it under the terms of the GNU General Public License
|
---|
14 | * as published by the Free Software Foundation, in version 3 of the
|
---|
15 | * License.
|
---|
16 | *
|
---|
17 | * This program is distributed in the hope that it will be useful, but
|
---|
18 | * WITHOUT ANY WARRANTY; without even the implied warranty of
|
---|
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
---|
20 | * General Public License for more details.
|
---|
21 | *
|
---|
22 | * You should have received a copy of the GNU General Public License
|
---|
23 | * along with this program; if not, see <https://www.gnu.org/licenses>.
|
---|
24 | *
|
---|
25 | * SPDX-License-Identifier: GPL-3.0-only
|
---|
26 | */
|
---|
27 |
|
---|
28 | /* Qt includes: */
|
---|
29 | #include <QApplication>
|
---|
30 | #include <QDir>
|
---|
31 |
|
---|
32 | /* GUI includes: */
|
---|
33 | #include "QIFileDialog.h"
|
---|
34 | #include "QIMessageBox.h"
|
---|
35 | #include "UICommon.h"
|
---|
36 | #include "UIExtraDataManager.h"
|
---|
37 | #include "UIGlobalSession.h"
|
---|
38 | #include "UIIconPool.h"
|
---|
39 | #include "UIMediumItem.h"
|
---|
40 | #include "UIMessageCenter.h"
|
---|
41 | #include "UINotificationCenter.h"
|
---|
42 | #include "UITranslator.h"
|
---|
43 |
|
---|
44 | /* COM includes: */
|
---|
45 | #include "CMachine.h"
|
---|
46 | #include "CMediumAttachment.h"
|
---|
47 | #include "CMediumFormat.h"
|
---|
48 | #include "CStorageController.h"
|
---|
49 |
|
---|
50 |
|
---|
51 | /*********************************************************************************************************************************
|
---|
52 | * Class UIMediumItem implementation. *
|
---|
53 | *********************************************************************************************************************************/
|
---|
54 |
|
---|
55 | UIMediumItem::UIMediumItem(const UIMedium &guiMedium, QITreeWidget *pParent)
|
---|
56 | : QITreeWidgetItem(pParent)
|
---|
57 | , m_guiMedium(guiMedium)
|
---|
58 | {
|
---|
59 | refresh();
|
---|
60 | }
|
---|
61 |
|
---|
62 | UIMediumItem::UIMediumItem(const UIMedium &guiMedium, UIMediumItem *pParent)
|
---|
63 | : QITreeWidgetItem(pParent)
|
---|
64 | , m_guiMedium(guiMedium)
|
---|
65 | {
|
---|
66 | refresh();
|
---|
67 | }
|
---|
68 |
|
---|
69 | UIMediumItem::UIMediumItem(const UIMedium &guiMedium, QITreeWidgetItem *pParent)
|
---|
70 | : QITreeWidgetItem(pParent)
|
---|
71 | , m_guiMedium(guiMedium)
|
---|
72 | {
|
---|
73 | refresh();
|
---|
74 | }
|
---|
75 |
|
---|
76 | bool UIMediumItem::move()
|
---|
77 | {
|
---|
78 | /* Open file-save dialog to choose location for current medium: */
|
---|
79 | const QString strFileName = QIFileDialog::getSaveFileName(location(),
|
---|
80 | tr("Current extension (*.%1)")
|
---|
81 | .arg(QFileInfo(location()).suffix()),
|
---|
82 | treeWidget(),
|
---|
83 | tr("Choose the location of this medium"),
|
---|
84 | 0, true, true);
|
---|
85 | if (strFileName.isNull() || strFileName == location())
|
---|
86 | return false;
|
---|
87 |
|
---|
88 | /* Search for corresponding medium: */
|
---|
89 | CMedium comMedium = medium().medium();
|
---|
90 | if (comMedium.isNull() || !comMedium.isOk())
|
---|
91 | return false;
|
---|
92 |
|
---|
93 | /* Assign new medium location: */
|
---|
94 | UINotificationProgressMediumMove *pNotification = new UINotificationProgressMediumMove(comMedium,
|
---|
95 | strFileName);
|
---|
96 | connect(pNotification, &UINotificationProgressMediumMove::sigProgressFinished,
|
---|
97 | this, &UIMediumItem::sltHandleMoveProgressFinished);
|
---|
98 | gpNotificationCenter->append(pNotification);
|
---|
99 |
|
---|
100 | /* Positive: */
|
---|
101 | return true;
|
---|
102 | }
|
---|
103 |
|
---|
104 | bool UIMediumItem::release(bool fShowMessageBox, bool fInduced)
|
---|
105 | {
|
---|
106 | /* Refresh medium and item: */
|
---|
107 | m_guiMedium.refresh();
|
---|
108 | refresh();
|
---|
109 |
|
---|
110 | /* Make sure medium was not released yet: */
|
---|
111 | if (medium().curStateMachineIds().isEmpty())
|
---|
112 | return true;
|
---|
113 |
|
---|
114 | /* Confirm release: */
|
---|
115 | if (fShowMessageBox)
|
---|
116 | if (!msgCenter().confirmMediumRelease(medium(), fInduced, treeWidget()))
|
---|
117 | return false;
|
---|
118 |
|
---|
119 | /* Release: */
|
---|
120 | foreach (const QUuid &uMachineId, medium().curStateMachineIds())
|
---|
121 | if (!releaseFrom(uMachineId))
|
---|
122 | return false;
|
---|
123 |
|
---|
124 | /* True by default: */
|
---|
125 | return true;
|
---|
126 | }
|
---|
127 |
|
---|
128 | void UIMediumItem::refreshAll()
|
---|
129 | {
|
---|
130 | m_guiMedium.blockAndQueryState();
|
---|
131 | refresh();
|
---|
132 | }
|
---|
133 |
|
---|
134 | void UIMediumItem::setMedium(const UIMedium &guiMedium)
|
---|
135 | {
|
---|
136 | m_guiMedium = guiMedium;
|
---|
137 | refresh();
|
---|
138 | }
|
---|
139 |
|
---|
140 | bool UIMediumItem::operator<(const QTreeWidgetItem &other) const
|
---|
141 | {
|
---|
142 | int iColumn = treeWidget()->sortColumn();
|
---|
143 | ULONG64 uThisValue = UITranslator::parseSize( text(iColumn));
|
---|
144 | ULONG64 uThatValue = UITranslator::parseSize(other.text(iColumn));
|
---|
145 | return uThisValue && uThatValue ? uThisValue < uThatValue : QTreeWidgetItem::operator<(other);
|
---|
146 | }
|
---|
147 |
|
---|
148 | bool UIMediumItem::isMediumModifiable() const
|
---|
149 | {
|
---|
150 | if (medium().isNull())
|
---|
151 | return false;
|
---|
152 | if (m_enmDeviceType == UIMediumDeviceType_DVD || m_enmDeviceType == UIMediumDeviceType_Floppy)
|
---|
153 | return false;
|
---|
154 | foreach (const QUuid &uMachineId, medium().curStateMachineIds())
|
---|
155 | {
|
---|
156 | CMachine comMachine = gpGlobalSession->virtualBox().FindMachine(uMachineId.toString());
|
---|
157 | if (comMachine.isNull())
|
---|
158 | continue;
|
---|
159 | if (comMachine.GetState() != KMachineState_PoweredOff &&
|
---|
160 | comMachine.GetState() != KMachineState_Aborted &&
|
---|
161 | comMachine.GetState() != KMachineState_AbortedSaved)
|
---|
162 | return false;
|
---|
163 | }
|
---|
164 | return true;
|
---|
165 | }
|
---|
166 |
|
---|
167 | bool UIMediumItem::isMediumAttachedTo(QUuid uId)
|
---|
168 | {
|
---|
169 | if (medium().isNull())
|
---|
170 | return false;
|
---|
171 | return medium().curStateMachineIds().contains(uId);
|
---|
172 | }
|
---|
173 |
|
---|
174 | bool UIMediumItem::changeMediumType(KMediumType enmNewType)
|
---|
175 | {
|
---|
176 | /* Cache the list of VMs the medium is attached to. We will need this for the re-attachment: */
|
---|
177 | QList<AttachmentCache> attachmentCacheList;
|
---|
178 | foreach (const QUuid &uMachineId, medium().curStateMachineIds())
|
---|
179 | {
|
---|
180 | const CMachine &comMachine = gpGlobalSession->virtualBox().FindMachine(uMachineId.toString());
|
---|
181 | if (comMachine.isNull())
|
---|
182 | continue;
|
---|
183 | foreach (const CStorageController &comController, comMachine.GetStorageControllers())
|
---|
184 | {
|
---|
185 | if (comController.isNull())
|
---|
186 | continue;
|
---|
187 | const QString strControllerName = comController.GetName();
|
---|
188 | foreach (const CMediumAttachment &comAttachment, comMachine.GetMediumAttachmentsOfController(strControllerName))
|
---|
189 | {
|
---|
190 | if (comAttachment.isNull())
|
---|
191 | continue;
|
---|
192 | const CMedium &comMedium = comAttachment.GetMedium();
|
---|
193 | if (comMedium.isNull() || comMedium.GetId() != id())
|
---|
194 | continue;
|
---|
195 | AttachmentCache attachmentCache;
|
---|
196 | attachmentCache.m_uMachineId = uMachineId;
|
---|
197 | attachmentCache.m_strControllerName = strControllerName;
|
---|
198 | attachmentCache.m_enmControllerBus = comController.GetBus();
|
---|
199 | attachmentCache.m_iAttachmentPort = comAttachment.GetPort();
|
---|
200 | attachmentCache.m_iAttachmentDevice = comAttachment.GetDevice();
|
---|
201 | attachmentCacheList << attachmentCache;
|
---|
202 | }
|
---|
203 | }
|
---|
204 | }
|
---|
205 |
|
---|
206 | /* Detach the medium from all the VMs it's attached to: */
|
---|
207 | if (!release(true, true))
|
---|
208 | return false;
|
---|
209 |
|
---|
210 | /* Attempt to change medium type: */
|
---|
211 | CMedium comMedium = medium().medium();
|
---|
212 | comMedium.SetType(enmNewType);
|
---|
213 | if (!comMedium.isOk())
|
---|
214 | {
|
---|
215 | UINotificationMessage::cannotChangeMediumParameter(comMedium);
|
---|
216 | return false;
|
---|
217 | }
|
---|
218 |
|
---|
219 | /* Reattach the medium to all the VMs it was previously attached: */
|
---|
220 | foreach (const AttachmentCache &attachmentCache, attachmentCacheList)
|
---|
221 | if (!attachTo(attachmentCache))
|
---|
222 | return false;
|
---|
223 |
|
---|
224 | /* True finally: */
|
---|
225 | return true;
|
---|
226 | }
|
---|
227 |
|
---|
228 | QString UIMediumItem::defaultText() const
|
---|
229 | {
|
---|
230 | return tr("%1, %2: %3, %4: %5", "col.1 text, col.2 name: col.2 text, col.3 name: col.3 text")
|
---|
231 | .arg(text(0))
|
---|
232 | .arg(parentTree()->headerItem()->text(1)).arg(text(1))
|
---|
233 | .arg(parentTree()->headerItem()->text(2)).arg(text(2));
|
---|
234 | }
|
---|
235 |
|
---|
236 | void UIMediumItem::sltHandleMoveProgressFinished()
|
---|
237 | {
|
---|
238 | /* Recache item: */
|
---|
239 | refreshAll();
|
---|
240 | }
|
---|
241 |
|
---|
242 | void UIMediumItem::sltHandleMediumRemoveRequest(CMedium comMedium)
|
---|
243 | {
|
---|
244 | /* Close medium finally: */
|
---|
245 | comMedium.Close();
|
---|
246 | if (!comMedium.isOk())
|
---|
247 | UINotificationMessage::cannotCloseMedium(comMedium);
|
---|
248 | }
|
---|
249 |
|
---|
250 | void UIMediumItem::refresh()
|
---|
251 | {
|
---|
252 | /* Fill-in columns: */
|
---|
253 | setIcon(0, m_guiMedium.icon());
|
---|
254 | setText(0, m_guiMedium.name());
|
---|
255 | setText(1, m_guiMedium.logicalSize());
|
---|
256 | setText(2, m_guiMedium.size());
|
---|
257 | /* All columns get the same tooltip: */
|
---|
258 | QString strToolTip = m_guiMedium.toolTip();
|
---|
259 | for (int i = 0; i < treeWidget()->columnCount(); ++i)
|
---|
260 | setToolTip(i, strToolTip);
|
---|
261 |
|
---|
262 | /* Gather medium data: */
|
---|
263 | m_fValid = !m_guiMedium.isNull()
|
---|
264 | && m_guiMedium.state() != KMediumState_Inaccessible;
|
---|
265 | m_enmDeviceType = m_guiMedium.type();
|
---|
266 | m_enmVariant = m_guiMedium.mediumVariant();
|
---|
267 | m_fHasChildren = m_guiMedium.hasChildren();
|
---|
268 | /* Gather medium options data: */
|
---|
269 | m_options.m_enmMediumType = m_guiMedium.mediumType();
|
---|
270 | m_options.m_strLocation = m_guiMedium.location();
|
---|
271 | m_options.m_uLogicalSize = m_guiMedium.logicalSizeInBytes();
|
---|
272 | m_options.m_strDescription = m_guiMedium.description();
|
---|
273 | /* Gather medium details data: */
|
---|
274 | m_details.m_aFields.clear();
|
---|
275 | switch (m_enmDeviceType)
|
---|
276 | {
|
---|
277 | case UIMediumDeviceType_HardDisk:
|
---|
278 | {
|
---|
279 | m_details.m_aLabels << tr("Format:");
|
---|
280 | m_details.m_aLabels << tr("Storage details:");
|
---|
281 | m_details.m_aLabels << tr("Attached to:");
|
---|
282 | m_details.m_aLabels << tr("Encryption key:");
|
---|
283 | m_details.m_aLabels << tr("UUID:");
|
---|
284 |
|
---|
285 | m_details.m_aFields << hardDiskFormat();
|
---|
286 | m_details.m_aFields << details();
|
---|
287 | m_details.m_aFields << (usage().isNull() ?
|
---|
288 | formatFieldText(tr("<i>Not Attached</i>"), false) :
|
---|
289 | formatFieldText(usage()));
|
---|
290 | m_details.m_aFields << (encryptionPasswordID().isNull() ?
|
---|
291 | formatFieldText(tr("<i>Not Encrypted</i>"), false) :
|
---|
292 | formatFieldText(encryptionPasswordID()));
|
---|
293 | m_details.m_aFields << id().toString();
|
---|
294 |
|
---|
295 | break;
|
---|
296 | }
|
---|
297 | case UIMediumDeviceType_DVD:
|
---|
298 | case UIMediumDeviceType_Floppy:
|
---|
299 | {
|
---|
300 | m_details.m_aLabels << tr("Attached to:");
|
---|
301 | m_details.m_aLabels << tr("UUID:");
|
---|
302 |
|
---|
303 | m_details.m_aFields << (usage().isNull() ?
|
---|
304 | formatFieldText(tr("<i>Not Attached</i>"), false) :
|
---|
305 | formatFieldText(usage()));
|
---|
306 | m_details.m_aFields << id().toString();
|
---|
307 | break;
|
---|
308 | }
|
---|
309 | default:
|
---|
310 | break;
|
---|
311 | }
|
---|
312 | }
|
---|
313 |
|
---|
314 | bool UIMediumItem::releaseFrom(const QUuid &uMachineId)
|
---|
315 | {
|
---|
316 | /* Open session: */
|
---|
317 | CSession session = uiCommon().openSession(uMachineId);
|
---|
318 | if (session.isNull())
|
---|
319 | return false;
|
---|
320 |
|
---|
321 | /* Get machine: */
|
---|
322 | CMachine machine = session.GetMachine();
|
---|
323 |
|
---|
324 | /* Prepare result: */
|
---|
325 | bool fSuccess = false;
|
---|
326 |
|
---|
327 | /* Release medium from machine: */
|
---|
328 | if (releaseFrom(machine))
|
---|
329 | {
|
---|
330 | /* Save machine settings: */
|
---|
331 | machine.SaveSettings();
|
---|
332 | if (!machine.isOk())
|
---|
333 | msgCenter().cannotSaveMachineSettings(machine, treeWidget());
|
---|
334 | else
|
---|
335 | fSuccess = true;
|
---|
336 | }
|
---|
337 |
|
---|
338 | /* Close session: */
|
---|
339 | session.UnlockMachine();
|
---|
340 |
|
---|
341 | /* Return result: */
|
---|
342 | return fSuccess;
|
---|
343 | }
|
---|
344 |
|
---|
345 | bool UIMediumItem::attachTo(const AttachmentCache &attachmentCache)
|
---|
346 | {
|
---|
347 | /* Open session: */
|
---|
348 | CSession comSession = uiCommon().openSession(attachmentCache.m_uMachineId);
|
---|
349 | if (comSession.isNull())
|
---|
350 | return false;
|
---|
351 |
|
---|
352 | /* Attach device to machine: */
|
---|
353 | CMedium comMedium = medium().medium();
|
---|
354 | KDeviceType enmDeviceType = comMedium.GetDeviceType();
|
---|
355 | CMachine comMachine = comSession.GetMachine();
|
---|
356 | comMachine.AttachDevice(attachmentCache.m_strControllerName,
|
---|
357 | attachmentCache.m_iAttachmentPort,
|
---|
358 | attachmentCache.m_iAttachmentDevice,
|
---|
359 | enmDeviceType,
|
---|
360 | comMedium);
|
---|
361 | if (!comMachine.isOk())
|
---|
362 | msgCenter().cannotAttachDevice(comMachine,
|
---|
363 | mediumTypeToLocal(enmDeviceType),
|
---|
364 | comMedium.GetLocation(),
|
---|
365 | StorageSlot(attachmentCache.m_enmControllerBus,
|
---|
366 | attachmentCache.m_iAttachmentPort,
|
---|
367 | attachmentCache.m_iAttachmentDevice),
|
---|
368 | parentTree());
|
---|
369 | else
|
---|
370 | {
|
---|
371 | /* Save machine settings: */
|
---|
372 | comMachine.SaveSettings();
|
---|
373 | if (!comMachine.isOk())
|
---|
374 | msgCenter().cannotSaveMachineSettings(comMachine, parentTree());
|
---|
375 | }
|
---|
376 |
|
---|
377 | /* Close session: */
|
---|
378 | comSession.UnlockMachine();
|
---|
379 |
|
---|
380 | /* True finally: */
|
---|
381 | return true;
|
---|
382 | }
|
---|
383 |
|
---|
384 | /* static */
|
---|
385 | QString UIMediumItem::formatFieldText(const QString &strText, bool fCompact /* = true */,
|
---|
386 | const QString &strElipsis /* = "middle" */)
|
---|
387 | {
|
---|
388 | QString strCompactString = QString("<compact elipsis=\"%1\">").arg(strElipsis);
|
---|
389 | QString strInfo = QString("<nobr>%1%2%3</nobr>")
|
---|
390 | .arg(fCompact ? strCompactString : "")
|
---|
391 | .arg(strText.isEmpty() ? tr("--", "no info") : strText)
|
---|
392 | .arg(fCompact ? "</compact>" : "");
|
---|
393 | return strInfo;
|
---|
394 | }
|
---|
395 |
|
---|
396 |
|
---|
397 | /*********************************************************************************************************************************
|
---|
398 | * Class UIMediumItemHD implementation. *
|
---|
399 | *********************************************************************************************************************************/
|
---|
400 |
|
---|
401 | UIMediumItemHD::UIMediumItemHD(const UIMedium &guiMedium, QITreeWidget *pParent)
|
---|
402 | : UIMediumItem(guiMedium, pParent)
|
---|
403 | {
|
---|
404 | }
|
---|
405 |
|
---|
406 | UIMediumItemHD::UIMediumItemHD(const UIMedium &guiMedium, UIMediumItem *pParent)
|
---|
407 | : UIMediumItem(guiMedium, pParent)
|
---|
408 | {
|
---|
409 | }
|
---|
410 |
|
---|
411 | UIMediumItemHD::UIMediumItemHD(const UIMedium &guiMedium, QITreeWidgetItem *pParent)
|
---|
412 | : UIMediumItem(guiMedium, pParent)
|
---|
413 | {
|
---|
414 | }
|
---|
415 |
|
---|
416 | bool UIMediumItemHD::remove(bool fShowMessageBox)
|
---|
417 | {
|
---|
418 | /* Confirm medium removal: */
|
---|
419 | if (fShowMessageBox)
|
---|
420 | if (!msgCenter().confirmMediumRemoval(medium(), treeWidget()))
|
---|
421 | return false;
|
---|
422 |
|
---|
423 | /* Propose to remove medium storage: */
|
---|
424 | if (!maybeRemoveStorage())
|
---|
425 | return false;
|
---|
426 |
|
---|
427 | /* True by default: */
|
---|
428 | return true;
|
---|
429 | }
|
---|
430 |
|
---|
431 | bool UIMediumItemHD::releaseFrom(CMachine comMachine)
|
---|
432 | {
|
---|
433 | /* Was medium released from at least one attachment? */
|
---|
434 | bool fAtLeastOneRelease = false;
|
---|
435 |
|
---|
436 | /* Enumerate attachments: */
|
---|
437 | CMediumAttachmentVector attachments = comMachine.GetMediumAttachments();
|
---|
438 | foreach (const CMediumAttachment &attachment, attachments)
|
---|
439 | {
|
---|
440 | /* Skip non-hard-disks: */
|
---|
441 | if (attachment.GetType() != KDeviceType_HardDisk)
|
---|
442 | continue;
|
---|
443 |
|
---|
444 | /* Skip unrelated hard-disks: */
|
---|
445 | if (attachment.GetMedium().GetId() != id())
|
---|
446 | continue;
|
---|
447 |
|
---|
448 | /* Remember controller: */
|
---|
449 | CStorageController controller = comMachine.GetStorageControllerByName(attachment.GetController());
|
---|
450 |
|
---|
451 | /* Try to detach device: */
|
---|
452 | comMachine.DetachDevice(attachment.GetController(), attachment.GetPort(), attachment.GetDevice());
|
---|
453 | if (!comMachine.isOk())
|
---|
454 | {
|
---|
455 | /* Return failure: */
|
---|
456 | msgCenter().cannotDetachDevice(comMachine, UIMediumDeviceType_HardDisk, location(),
|
---|
457 | StorageSlot(controller.GetBus(), attachment.GetPort(), attachment.GetDevice()),
|
---|
458 | treeWidget());
|
---|
459 | return false;
|
---|
460 | }
|
---|
461 | else
|
---|
462 | fAtLeastOneRelease = true;
|
---|
463 | }
|
---|
464 |
|
---|
465 | /* Return whether there was at least one release: */
|
---|
466 | return fAtLeastOneRelease;
|
---|
467 | }
|
---|
468 |
|
---|
469 | bool UIMediumItemHD::maybeRemoveStorage()
|
---|
470 | {
|
---|
471 | /* Acquire medium: */
|
---|
472 | CMedium comMedium = medium().medium();
|
---|
473 |
|
---|
474 | /* We don't want to try to delete inaccessible storage as it will most likely fail.
|
---|
475 | * Note that UIMessageCenter::confirmMediumRemoval() is aware of that and
|
---|
476 | * will give a corresponding hint. Therefore, once the code is changed below,
|
---|
477 | * the hint should be re-checked for validity. */
|
---|
478 | bool fDeleteStorage = false;
|
---|
479 | qulonglong uCapability = 0;
|
---|
480 | foreach (KMediumFormatCapabilities capability, comMedium.GetMediumFormat().GetCapabilities())
|
---|
481 | uCapability |= capability;
|
---|
482 | if (state() != KMediumState_Inaccessible && uCapability & KMediumFormatCapabilities_File)
|
---|
483 | {
|
---|
484 | int rc = msgCenter().confirmDeleteHardDiskStorage(location(), treeWidget());
|
---|
485 | if (rc == AlertButton_Cancel)
|
---|
486 | return false;
|
---|
487 | fDeleteStorage = rc == AlertButton_Choice1;
|
---|
488 | }
|
---|
489 |
|
---|
490 | /* If user wish to delete storage: */
|
---|
491 | if (fDeleteStorage)
|
---|
492 | {
|
---|
493 | /* Deleting medium storage first of all: */
|
---|
494 | UINotificationProgressMediumDeletingStorage *pNotification = new UINotificationProgressMediumDeletingStorage(comMedium);
|
---|
495 | connect(pNotification, &UINotificationProgressMediumDeletingStorage::sigMediumStorageDeleted,
|
---|
496 | this, &UIMediumItemHD::sltHandleMediumRemoveRequest);
|
---|
497 | gpNotificationCenter->append(pNotification);
|
---|
498 | }
|
---|
499 | /* Otherwise go to last step immediatelly: */
|
---|
500 | else
|
---|
501 | sltHandleMediumRemoveRequest(comMedium);
|
---|
502 |
|
---|
503 | /* True by default: */
|
---|
504 | return true;
|
---|
505 | }
|
---|
506 |
|
---|
507 |
|
---|
508 | /*********************************************************************************************************************************
|
---|
509 | * Class UIMediumItemCD implementation. *
|
---|
510 | *********************************************************************************************************************************/
|
---|
511 |
|
---|
512 | UIMediumItemCD::UIMediumItemCD(const UIMedium &guiMedium, QITreeWidget *pParent)
|
---|
513 | : UIMediumItem(guiMedium, pParent)
|
---|
514 | {
|
---|
515 | }
|
---|
516 |
|
---|
517 | UIMediumItemCD::UIMediumItemCD(const UIMedium &guiMedium, QITreeWidgetItem *pParent)
|
---|
518 | : UIMediumItem(guiMedium, pParent)
|
---|
519 | {
|
---|
520 | }
|
---|
521 |
|
---|
522 | bool UIMediumItemCD::remove(bool fShowMessageBox)
|
---|
523 | {
|
---|
524 | /* Confirm medium removal: */
|
---|
525 | if (fShowMessageBox)
|
---|
526 | if (!msgCenter().confirmMediumRemoval(medium(), treeWidget()))
|
---|
527 | return false;
|
---|
528 |
|
---|
529 | /* Close optical-disk: */
|
---|
530 | sltHandleMediumRemoveRequest(medium().medium());
|
---|
531 |
|
---|
532 | /* True by default: */
|
---|
533 | return true;
|
---|
534 | }
|
---|
535 |
|
---|
536 | bool UIMediumItemCD::releaseFrom(CMachine comMachine)
|
---|
537 | {
|
---|
538 | /* Was medium released from at least one attachment? */
|
---|
539 | bool fAtLeastOneRelease = false;
|
---|
540 |
|
---|
541 | /* Enumerate attachments: */
|
---|
542 | CMediumAttachmentVector attachments = comMachine.GetMediumAttachments();
|
---|
543 | foreach (const CMediumAttachment &attachment, attachments)
|
---|
544 | {
|
---|
545 | /* Skip non-optical-disks: */
|
---|
546 | if (attachment.GetType() != KDeviceType_DVD)
|
---|
547 | continue;
|
---|
548 |
|
---|
549 | /* Skip unrelated optical-disks: */
|
---|
550 | if (attachment.GetMedium().GetId() != id())
|
---|
551 | continue;
|
---|
552 |
|
---|
553 | /* Try to unmount device: */
|
---|
554 | comMachine.MountMedium(attachment.GetController(), attachment.GetPort(), attachment.GetDevice(), CMedium(), false /* force */);
|
---|
555 | if (!comMachine.isOk())
|
---|
556 | {
|
---|
557 | /* Return failure: */
|
---|
558 | msgCenter().cannotRemountMedium(comMachine, medium(), false /* mount? */, false /* retry? */, treeWidget());
|
---|
559 | return false;
|
---|
560 | }
|
---|
561 | else
|
---|
562 | fAtLeastOneRelease = true;
|
---|
563 | }
|
---|
564 |
|
---|
565 | /* Return whether there was at least one release: */
|
---|
566 | return fAtLeastOneRelease;
|
---|
567 | }
|
---|
568 |
|
---|
569 |
|
---|
570 | /*********************************************************************************************************************************
|
---|
571 | * Class UIMediumItemFD implementation. *
|
---|
572 | *********************************************************************************************************************************/
|
---|
573 |
|
---|
574 | UIMediumItemFD::UIMediumItemFD(const UIMedium &guiMedium, QITreeWidget *pParent)
|
---|
575 | : UIMediumItem(guiMedium, pParent)
|
---|
576 | {
|
---|
577 | }
|
---|
578 |
|
---|
579 | UIMediumItemFD::UIMediumItemFD(const UIMedium &guiMedium, QITreeWidgetItem *pParent)
|
---|
580 | : UIMediumItem(guiMedium, pParent)
|
---|
581 | {
|
---|
582 | }
|
---|
583 |
|
---|
584 | bool UIMediumItemFD::remove(bool fShowMessageBox)
|
---|
585 | {
|
---|
586 | /* Confirm medium removal: */
|
---|
587 | if (fShowMessageBox)
|
---|
588 | if (!msgCenter().confirmMediumRemoval(medium(), treeWidget()))
|
---|
589 | return false;
|
---|
590 |
|
---|
591 | /* Close floppy-disk: */
|
---|
592 | sltHandleMediumRemoveRequest(medium().medium());
|
---|
593 |
|
---|
594 | /* True by default: */
|
---|
595 | return true;
|
---|
596 | }
|
---|
597 |
|
---|
598 | bool UIMediumItemFD::releaseFrom(CMachine comMachine)
|
---|
599 | {
|
---|
600 | /* Was medium released from at least one attachment? */
|
---|
601 | bool fAtLeastOneRelease = false;
|
---|
602 |
|
---|
603 | /* Enumerate attachments: */
|
---|
604 | CMediumAttachmentVector attachments = comMachine.GetMediumAttachments();
|
---|
605 | foreach (const CMediumAttachment &attachment, attachments)
|
---|
606 | {
|
---|
607 | /* Skip non-floppy-disks: */
|
---|
608 | if (attachment.GetType() != KDeviceType_Floppy)
|
---|
609 | continue;
|
---|
610 |
|
---|
611 | /* Skip unrelated floppy-disks: */
|
---|
612 | if (attachment.GetMedium().GetId() != id())
|
---|
613 | continue;
|
---|
614 |
|
---|
615 | /* Try to unmount device: */
|
---|
616 | comMachine.MountMedium(attachment.GetController(), attachment.GetPort(), attachment.GetDevice(), CMedium(), false /* force */);
|
---|
617 | if (!comMachine.isOk())
|
---|
618 | {
|
---|
619 | /* Return failure: */
|
---|
620 | msgCenter().cannotRemountMedium(comMachine, medium(), false /* mount? */, false /* retry? */, treeWidget());
|
---|
621 | return false;
|
---|
622 | }
|
---|
623 | else
|
---|
624 | fAtLeastOneRelease = true;
|
---|
625 | }
|
---|
626 |
|
---|
627 | /* Return whether there was at least one release: */
|
---|
628 | return fAtLeastOneRelease;
|
---|
629 | }
|
---|