@@ -343,3 +343,178 @@ void Drive::setRestoreStatus(Drive::RestoreStatus o)
343343 emit restoreStatusChanged ();
344344 }
345345}
346+
347+ RestoreableDriveManager::RestoreableDriveManager (QObject *parent)
348+ : QSortFilterProxyModel(parent)
349+ {
350+ setSourceModel (DriveManager::instance ());
351+
352+ connect (DriveManager::instance (), &DriveManager::drivesChanged, this , &RestoreableDriveManager::onSourceModelChanged);
353+
354+ // Connect to existing drives
355+ connectToDrives ();
356+
357+ if (rowCount () > 0 ) {
358+ m_selectedIndex = 0 ;
359+ }
360+ }
361+
362+ void RestoreableDriveManager::connectToDrives ()
363+ {
364+ DriveManager *dm = DriveManager::instance ();
365+ for (int i = 0 ; i < dm->rowCount (); i++) {
366+ QModelIndex idx = dm->index (i, 0 );
367+ Drive *drive = qvariant_cast<Drive *>(dm->data (idx, Qt::UserRole + 1 ));
368+ if (drive) {
369+ // Use unique connection to avoid duplicates
370+ connect (drive, &Drive::restoreStatusChanged, this , &RestoreableDriveManager::onDriveRestoreStatusChanged, Qt::UniqueConnection);
371+ }
372+ }
373+ }
374+
375+ void RestoreableDriveManager::onDriveRestoreStatusChanged ()
376+ {
377+ // Store the previously selected drive
378+ Drive *previouslySelected = selected ();
379+
380+ // Invalidate filter to update which drives are shown
381+ invalidateFilter ();
382+ emit lengthChanged ();
383+
384+ // Check if the previously selected drive is still in the filtered list
385+ if (previouslySelected) {
386+ bool stillInList = false ;
387+ for (int i = 0 ; i < rowCount (); i++) {
388+ QModelIndex idx = index (i, 0 );
389+ Drive *drive = qvariant_cast<Drive *>(data (idx, Qt::UserRole + 1 ));
390+ if (drive == previouslySelected) {
391+ stillInList = true ;
392+ if (m_selectedIndex != i) {
393+ m_selectedIndex = i;
394+ emit selectedChanged ();
395+ }
396+ break ;
397+ }
398+ }
399+
400+ // If the previously selected drive is no longer in the list, select a new one
401+ if (!stillInList) {
402+ if (rowCount () > 0 ) {
403+ m_selectedIndex = 0 ;
404+ } else {
405+ m_selectedIndex = -1 ;
406+ }
407+ emit selectedChanged ();
408+ }
409+ } else {
410+ // No previous selection - select first drive if available
411+ if (rowCount () > 0 ) {
412+ m_selectedIndex = 0 ;
413+ emit selectedChanged ();
414+ }
415+ }
416+ }
417+
418+ bool RestoreableDriveManager::filterAcceptsRow (int source_row, const QModelIndex &source_parent) const
419+ {
420+ Q_UNUSED (source_parent)
421+
422+ DriveManager *dm = DriveManager::instance ();
423+ if (source_row < 0 || source_row >= dm->rowCount ())
424+ return false ;
425+
426+ QModelIndex idx = dm->index (source_row, 0 );
427+ Drive *drive = qvariant_cast<Drive *>(dm->data (idx, Qt::UserRole + 1 ));
428+
429+ if (drive && drive->restoreStatus () == Drive::CONTAINS_LIVE)
430+ return true ;
431+
432+ return false ;
433+ }
434+
435+ QHash<int , QByteArray> RestoreableDriveManager::roleNames () const
436+ {
437+ QHash<int , QByteArray> ret;
438+ ret.insert (Qt::UserRole + 1 , " drive" );
439+ ret.insert (Qt::UserRole + 2 , " display" );
440+ ret.insert (Qt::DisplayRole, " name" );
441+ return ret;
442+ }
443+
444+ QVariant RestoreableDriveManager::data (const QModelIndex &index, int role) const
445+ {
446+ if (!index.isValid ())
447+ return QVariant ();
448+
449+ QModelIndex sourceIndex = mapToSource (index);
450+ DriveManager *dm = DriveManager::instance ();
451+
452+ if (role == Qt::UserRole + 1 )
453+ return dm->data (sourceIndex, Qt::UserRole + 1 );
454+ else if (role == Qt::UserRole + 2 || role == Qt::DisplayRole) {
455+ Drive *drive = qvariant_cast<Drive *>(dm->data (sourceIndex, Qt::UserRole + 1 ));
456+ if (drive)
457+ return drive->name ();
458+ }
459+
460+ return QVariant ();
461+ }
462+
463+ Drive *RestoreableDriveManager::selected () const
464+ {
465+ if (m_selectedIndex >= 0 && m_selectedIndex < rowCount ()) {
466+ QModelIndex idx = index (m_selectedIndex, 0 );
467+ return qvariant_cast<Drive *>(data (idx, Qt::UserRole + 1 ));
468+ }
469+ return nullptr ;
470+ }
471+
472+ int RestoreableDriveManager::selectedIndex () const
473+ {
474+ return m_selectedIndex;
475+ }
476+
477+ void RestoreableDriveManager::setSelectedIndex (int index)
478+ {
479+ if (m_selectedIndex != index && index >= 0 && index < rowCount ()) {
480+ m_selectedIndex = index;
481+ emit selectedChanged ();
482+ }
483+ }
484+
485+ int RestoreableDriveManager::length () const
486+ {
487+ return rowCount ();
488+ }
489+
490+ void RestoreableDriveManager::onSourceModelChanged ()
491+ {
492+ // Connect to any new drives
493+ connectToDrives ();
494+
495+ // Remember previous state
496+ int previousCount = rowCount ();
497+ Drive *previousSelected = selected ();
498+
499+ invalidateFilter ();
500+
501+ int newCount = rowCount ();
502+
503+ // Always emit length changed
504+ emit lengthChanged ();
505+
506+ // Reset selection if out of bounds
507+ if (m_selectedIndex >= newCount) {
508+ m_selectedIndex = newCount > 0 ? 0 : -1 ;
509+ }
510+
511+ // If there are restoreable drives and nothing is selected, select the first one
512+ if (m_selectedIndex < 0 && newCount > 0 ) {
513+ m_selectedIndex = 0 ;
514+ }
515+
516+ // Emit selectedChanged if the selected drive changed
517+ if (selected () != previousSelected) {
518+ emit selectedChanged ();
519+ }
520+ }
0 commit comments