MythTV  master
videoscan.cpp
Go to the documentation of this file.
1 
2 #include "videoscan.h"
3 
4 #include <QApplication>
5 #include <QImageReader>
6 #include <QUrl>
7 #include <utility>
8 
9 // mythtv
10 #include "libmyth/mythcontext.h"
11 #include "libmyth/remoteutil.h"
12 #include "libmythbase/mythdate.h"
13 #include "libmythbase/mythevent.h"
19 
20 // libmythmetadata
22 #include "videoutils.h"
23 #include "globals.h"
24 #include "dbaccess.h"
25 #include "dirscan.h"
26 
27 QEvent::Type VideoScanChanges::kEventType =
28  (QEvent::Type) QEvent::registerEventType();
29 
30 namespace
31 {
32  template <typename DirListType>
33  class dirhandler : public DirectoryHandler
34  {
35  public:
36  dirhandler(DirListType &video_files,
37  const QStringList &image_extensions) :
38  m_videoFiles(video_files)
39  {
40  for (const auto& ext : qAsConst(image_extensions))
41  m_imageExt.insert(ext.toLower());
42  }
43 
44  DirectoryHandler *newDir(const QString &dir_name,
45  const QString &fq_dir_name) override // DirectoryHandler
46  {
47  (void) dir_name;
48  (void) fq_dir_name;
49  return this;
50  }
51 
52  void handleFile(const QString &file_name,
53  const QString &fq_file_name,
54  const QString &extension,
55  const QString &host) override // DirectoryHandler
56 
57  {
58 #if 0
59  LOG(VB_GENERAL, LOG_DEBUG,
60  QString("handleFile: %1 :: %2").arg(fq_file_name).arg(host));
61 #endif
62  (void) file_name;
63  if (m_imageExt.find(extension.toLower()) == m_imageExt.end())
64  {
65  m_videoFiles[fq_file_name].check = false;
66  m_videoFiles[fq_file_name].host = host;
67  }
68  }
69 
70  private:
71  using image_ext = std::set<QString>;
72  image_ext m_imageExt;
73  DirListType &m_videoFiles;
74  };
75 }
76 
79 
81  MThread("VideoScanner")
82 {
83  m_parent = parent;
86  m_listUnknown = gCoreContext->GetBoolSetting("VideoListUnknownFiletypes", false);
87 }
88 
90 {
91  delete m_dbMetadata;
92 }
93 
94 void VideoScannerThread::SetHosts(const QStringList &hosts)
95 {
96  m_liveSGHosts.clear();
97  for (const auto& host : qAsConst(hosts))
98  m_liveSGHosts << host.toLower();
99 }
100 
101 void VideoScannerThread::SetDirs(QStringList dirs)
102 {
103  QString master = gCoreContext->GetMasterHostName().toLower();
104  QStringList searchhosts;
105  QStringList mdirs;
106  m_offlineSGHosts.clear();
107 
108  QStringList::iterator iter = dirs.begin();
109  QStringList::iterator iter2;
110  while ( iter != dirs.end() )
111  {
112  if (iter->startsWith("myth://"))
113  {
114  QUrl sgurl = *iter;
115  QString host = sgurl.host().toLower();
116  QString path = sgurl.path();
117 
118  if (!m_liveSGHosts.contains(host))
119  {
120  // mark host as offline to warn user
121  if (!m_offlineSGHosts.contains(host))
122  m_offlineSGHosts.append(host);
123  // erase from directory list to skip scanning
124  iter = dirs.erase(iter);
125  continue;
126  }
127  if ((host == master) && (!mdirs.contains(path)))
128  {
129  // collect paths defined on master backend so other
130  // online backends can be set to fall through to them
131  mdirs.append(path);
132  }
133  else if (!searchhosts.contains(host))
134  {
135  // mark host as having directories defined so it
136  // does not fall through to those on the master
137  searchhosts.append(host);
138  }
139  }
140 
141  ++iter;
142  }
143 
144  for (iter = m_liveSGHosts.begin(); iter != m_liveSGHosts.end(); ++iter)
145  {
146  if ((!searchhosts.contains(*iter)) && (master != *iter))
147  {
148  for (iter2 = mdirs.begin(); iter2 != mdirs.end(); ++iter2)
149  {
150  // backend is online, but has no directories listed
151  // fall back to those on the master backend
152  dirs.append(MythCoreContext::GenMythURL(*iter,
153  0, *iter2, "Videos"));
154  }
155  }
156  }
157 
158  m_directories = dirs;
159 }
160 
162 {
163  RunProlog();
164 
167  m_dbMetadata->setList(ml);
168 
169  QList<QByteArray> image_types = QImageReader::supportedImageFormats();
170  QStringList imageExtensions;
171  for (const auto & format : qAsConst(image_types))
172  imageExtensions.push_back(QString(format));
173 
174  LOG(VB_GENERAL, LOG_INFO, QString("Beginning Video Scan."));
175 
176  uint counter = 0;
177  FileCheckList fs_files;
178 
179  if (m_hasGUI)
180  SendProgressEvent(counter, (uint)m_directories.size(),
181  tr("Searching for video files"));
182  for (const auto & dir : qAsConst(m_directories))
183  {
184  if (!buildFileList(dir, imageExtensions, fs_files))
185  {
186  if (dir.startsWith("myth://"))
187  {
188  QUrl sgurl = dir;
189  QString host = sgurl.host().toLower();
190 
191  m_liveSGHosts.removeAll(host);
192 
193  LOG(VB_GENERAL, LOG_ERR,
194  QString("Failed to scan :%1:").arg(dir));
195  }
196  }
197  if (m_hasGUI)
198  SendProgressEvent(++counter);
199  }
200 
201  PurgeList db_remove;
202  verifyFiles(fs_files, db_remove);
203  m_dbDataChanged = updateDB(fs_files, db_remove);
204 
205  if (m_dbDataChanged)
206  {
207  QCoreApplication::postEvent(m_parent,
209  m_delList));
210 
211  QStringList slist;
212 
213  for (int id : qAsConst(m_addList))
214  slist << QString("added::%1").arg(id);
215  for (int id : qAsConst(m_movList))
216  slist << QString("moved::%1").arg(id);
217  for (int id : qAsConst(m_delList))
218  slist << QString("deleted::%1").arg(id);
219 
220  MythEvent me("VIDEO_LIST_CHANGE", slist);
221 
222  gCoreContext->SendEvent(me);
223  }
224  else
225  gCoreContext->SendMessage("VIDEO_LIST_NO_CHANGE");
226 
227  RunEpilog();
228 }
229 
230 
232  const QString &filename)
233 {
234  (void) filename;
235 
236  // TODO: use single DB connection for all calls
237  if (m_removeAll)
238  m_dbMetadata->purgeByID(id);
239 
240  if (!m_keepAll && !m_removeAll)
241  {
242  m_removeAll = true;
243  m_dbMetadata->purgeByID(id);
244  }
245 }
246 
248  PurgeList &remove)
249 {
250  int counter = 0;
251  FileCheckList::iterator iter;
252 
253  if (m_hasGUI)
254  SendProgressEvent(counter, (uint)m_dbMetadata->getList().size(),
255  tr("Verifying video files"));
256 
257  // For every file we know about, check to see if it still exists.
258  for (const auto & file : m_dbMetadata->getList())
259  {
260  QString lname = file->GetFilename();
261  QString lhost = file->GetHost().toLower();
262  if (!lname.isEmpty())
263  {
264  iter = files.find(lname);
265  if (iter != files.end())
266  {
267  if (lhost != iter->second.host)
268  {
269  // file has changed hosts
270  // add to delete list for further processing
271  remove.push_back(std::make_pair(file->GetID(), lname));
272  }
273  else
274  {
275  // file is on disk on the proper host and in the database
276  // we're done with it
277  iter->second.check = true;
278  }
279  }
280  else if (lhost.isEmpty())
281  {
282  // If it's only in the database, and not on a host we
283  // cannot reach, mark it as for removal later.
284  remove.push_back(std::make_pair(file->GetID(), lname));
285  }
286  else if (m_liveSGHosts.contains(lhost))
287  {
288  LOG(VB_GENERAL, LOG_INFO,
289  QString("Removing file SG(%1) :%2:")
290  .arg(lhost, lname));
291  remove.push_back(std::make_pair(file->GetID(), lname));
292  }
293  else
294  {
295  LOG(VB_GENERAL, LOG_WARNING,
296  QString("SG(%1) not available. Not removing file :%2:")
297  .arg(lhost, lname));
298  if (!m_offlineSGHosts.contains(lhost))
299  m_offlineSGHosts.append(lhost);
300  }
301  }
302  if (m_hasGUI)
303  SendProgressEvent(++counter);
304  }
305 }
306 
307 bool VideoScannerThread::updateDB(const FileCheckList &add, const PurgeList &remove)
308 {
309  int ret = 0;
310  uint counter = 0;
311  if (m_hasGUI)
312  SendProgressEvent(counter, (uint)(add.size() + remove.size()),
313  tr("Updating video database"));
314 
315  for (auto p = add.cbegin(); p != add.cend(); ++p)
316  {
317  // add files not already in the DB
318  if (!p->second.check)
319  {
320  int id = -1;
321 
322  // Are we sure this needs adding? Let's check our Hash list.
323  QString hash = VideoMetadata::VideoFileHash(p->first, p->second.host);
324  if (hash != "NULL" && !hash.isEmpty())
325  {
326  id = VideoMetadata::UpdateHashedDBRecord(hash, p->first, p->second.host);
327  if (id != -1)
328  {
329  // Whew, that was close. Let's remove that thing from
330  // our purge list, too.
331  LOG(VB_GENERAL, LOG_ERR,
332  QString("Hash %1 already exists in the "
333  "database, updating record %2 "
334  "with new filename %3")
335  .arg(hash).arg(id).arg(p->first));
336  m_movList.append(id);
337  }
338  }
339  if (id == -1)
340  {
341  VideoMetadata newFile(
342  p->first, QString(), hash,
348  QString(), QString(), QString(), QString(),
349  QString(),
351  QDate::fromString("0000-00-00","YYYY-MM-DD"),
352  VIDEO_INETREF_DEFAULT, 0, QString(),
354  0.0, VIDEO_RATING_DEFAULT, 0, 0,
355  0, 0,
356  MythDate::current().date(),
358 
359  LOG(VB_GENERAL, LOG_INFO, QString("Adding : %1 : %2 : %3")
360  .arg(newFile.GetHost(), newFile.GetFilename(), hash));
361  newFile.SetHost(p->second.host);
362  newFile.SaveToDatabase();
363  m_addList << newFile.GetID();
364  }
365  ret += 1;
366  }
367  if (m_hasGUI)
368  SendProgressEvent(++counter);
369  }
370 
371  // When prompting is restored, account for the answer here.
372  ret += remove.size();
373  for (const auto & item : remove)
374  {
375  if (!m_movList.contains(item.first))
376  {
377  removeOrphans(item.first, item.second);
378  m_delList << item.first;
379  }
380  if (m_hasGUI)
381  SendProgressEvent(++counter);
382  }
383 
384  return ret > 0;
385 }
386 
387 bool VideoScannerThread::buildFileList(const QString &directory,
388  const QStringList &imageExtensions,
389  FileCheckList &filelist) const
390 {
391  // TODO: FileCheckList is a std::map, keyed off the filename. In the event
392  // multiple backends have access to shared storage, the potential exists
393  // for files to be scanned onto the wrong host. Add in some logic to prefer
394  // the backend with the content stored in a storage group determined to be
395  // local.
396 
397  LOG(VB_GENERAL,LOG_INFO, QString("buildFileList directory = %1")
398  .arg(directory));
401 
402  dirhandler<FileCheckList> dh(filelist, imageExtensions);
403  return ScanVideoDirectory(directory, &dh, ext_list, m_listUnknown);
404 }
405 
407  QString messsage)
408 {
409  if (!m_dialog)
410  return;
411 
412  auto *pue = new ProgressUpdateEvent(progress, total, std::move(messsage));
413  QApplication::postEvent(m_dialog, pue);
414 }
415 
417 {
418  m_scanThread = new VideoScannerThread(this);
419 }
420 
422 {
423  if (m_scanThread && m_scanThread->wait())
424  delete m_scanThread;
425 }
426 
427 void VideoScanner::doScan(const QStringList &dirs)
428 {
429  if (m_scanThread->isRunning())
430  return;
431 
432  if (gCoreContext->HasGUI())
433  {
434  MythScreenStack *popupStack = GetMythMainWindow()->GetStack("popup stack");
435 
436  auto *progressDlg = new MythUIProgressDialog("", popupStack,
437  "videoscanprogressdialog");
438 
439  if (progressDlg->Create())
440  {
441  popupStack->AddScreen(progressDlg, false);
442  connect(m_scanThread->qthread(), &QThread::finished,
443  progressDlg, &MythScreenType::Close);
444  connect(m_scanThread->qthread(), &QThread::finished,
446  }
447  else
448  {
449  delete progressDlg;
450  progressDlg = nullptr;
451  }
452  m_scanThread->SetProgressDialog(progressDlg);
453  }
454 
455  QStringList hosts;
456  if (!RemoteGetActiveBackends(&hosts))
457  {
458  LOG(VB_GENERAL, LOG_WARNING, "Could not retrieve list of "
459  "available backends.");
460  hosts.clear();
461  }
462  m_scanThread->SetHosts(hosts);
463  m_scanThread->SetDirs(dirs);
464  m_scanThread->start();
465 }
466 
468 {
469  doScan(GetVideoDirs());
470 }
471 
473 {
474  QStringList failedHosts = m_scanThread->GetOfflineSGHosts();
475  if (!failedHosts.empty())
476  {
477  QString hosts = failedHosts.join(" ");
478  QString msg = tr("Failed to Scan SG Video Hosts:\n\n%1\n\n"
479  "If they no longer exist please remove them")
480  .arg(hosts);
481 
482  ShowOkPopup(msg);
483  }
484 
486 }
487 
VideoScanner::finished
void finished(bool)
VideoMetadata
Definition: videometadata.h:24
mythevent.h
MythCoreContext::SendMessage
void SendMessage(const QString &message)
Definition: mythcorecontext.cpp:1521
MThread::start
void start(QThread::Priority p=QThread::InheritPriority)
Tell MThread to start running the thread in the near future.
Definition: mthread.cpp:286
MythCoreContext::GetMasterHostName
QString GetMasterHostName(void)
Definition: mythcorecontext.cpp:811
VideoScannerThread::m_listUnknown
bool m_listUnknown
Definition: videoscan.h:101
VideoScanner::VideoScanner
VideoScanner()
Definition: videoscan.cpp:416
VideoScannerThread::SendProgressEvent
void SendProgressEvent(uint progress, uint total=0, QString messsage=QString())
Definition: videoscan.cpp:406
VideoScannerThread::m_keepAll
bool m_keepAll
Definition: videoscan.h:103
FileAssociations::getExtensionIgnoreList
void getExtensionIgnoreList(ext_ignore_list &ext_ignore) const
Definition: dbaccess.cpp:811
dirscan.h
ParentalLevel::plLowest
@ plLowest
Definition: parentalcontrols.h:12
VideoMetadata::GetHost
const QString & GetHost() const
Definition: videometadata.cpp:1837
VideoMetadataListManager
Definition: videometadatalistmanager.h:10
MythScreenType::Close
virtual void Close()
Definition: mythscreentype.cpp:386
VideoScanner::doScan
void doScan(const QStringList &dirs)
Definition: videoscan.cpp:427
progress
bool progress
Definition: mythcommflag.cpp:69
MThread::wait
bool wait(std::chrono::milliseconds time=std::chrono::milliseconds::max())
Wait for the MThread to exit, with a maximum timeout.
Definition: mthread.cpp:303
mythscreenstack.h
MythEvent
This class is used as a container for messages.
Definition: mythevent.h:16
mythdialogbox.h
MythScreenStack
Definition: mythscreenstack.h:16
VideoScanChanges::kEventType
static Type kEventType
Definition: videoscan.h:57
LOG
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
Definition: mythlogging.h:23
MThread::RunProlog
void RunProlog(void)
Sets up a thread, call this if you reimplement run().
Definition: mthread.cpp:196
VideoMetadataListManager::getList
const metadata_list & getList() const
Definition: videometadatalistmanager.cpp:165
VideoMetadataListManager::setList
void setList(metadata_list &list)
Definition: videometadatalistmanager.cpp:159
build_compdb.file
file
Definition: build_compdb.py:55
VideoScannerThread::GetOfflineSGHosts
QStringList GetOfflineSGHosts(void)
Definition: videoscan.h:72
remoteutil.h
VideoScannerThread::m_movList
QList< int > m_movList
Definition: videoscan.h:113
MythDate::current
QDateTime current(bool stripped)
Returns current Date and Time in UTC.
Definition: mythdate.cpp:14
mythprogressdialog.h
VideoScannerThread::buildFileList
bool buildFileList(const QString &directory, const QStringList &imageExtensions, FileCheckList &filelist) const
Definition: videoscan.cpp:387
VideoMetadataListManager::loadAllFromDatabase
static void loadAllFromDatabase(metadata_list &items, const QString &sql="")
Load videometadata database into memory.
Definition: videometadatalistmanager.cpp:128
MythUIProgressDialog::MythUIProgressDialog
MythUIProgressDialog(QString message, MythScreenStack *parent, const char *name)
Definition: mythprogressdialog.h:63
dbaccess.h
VideoScanner::m_scanThread
class VideoScannerThread * m_scanThread
Definition: videoscan.h:40
dirhandler::handleFile
void handleFile(const QString &file_name, const QString &fq_file_name, const QString &extension)
Definition: videolist.cpp:1169
videoscan.h
VideoScannerThread
Definition: videoscan.h:60
ProgressUpdateEvent
Definition: mythprogressdialog.h:16
mythdate.h
VideoMetadata::GetFilename
const QString & GetFilename() const
Definition: videometadata.cpp:1817
mythlogging.h
MythCoreContext::GenMythURL
static QString GenMythURL(const QString &host=QString(), int port=0, QString path=QString(), const QString &storageGroup=QString())
Definition: mythcorecontext.cpp:764
VideoScannerThread::m_dialog
MythUIProgressDialog * m_dialog
Definition: videoscan.h:110
GetVideoDirs
QStringList GetVideoDirs()
Definition: videoutils.cpp:121
MythCoreContext::SendEvent
void SendEvent(const MythEvent &event)
Definition: mythcorecontext.cpp:1534
hardwareprofile.config.p
p
Definition: config.py:33
MythUIProgressDialog
Definition: mythprogressdialog.h:59
globals.h
FileAssociations::ext_ignore_list
std::vector< std::pair< QString, bool > > ext_ignore_list
Definition: dbaccess.h:155
VideoScannerThread::m_addList
QList< int > m_addList
Definition: videoscan.h:112
VideoMetadata::UpdateHashedDBRecord
static int UpdateHashedDBRecord(const QString &hash, const QString &file_name, const QString &host)
Definition: videometadata.cpp:1075
VideoScannerThread::SetDirs
void SetDirs(QStringList dirs)
Definition: videoscan.cpp:101
VideoMetadata::SaveToDatabase
void SaveToDatabase()
Definition: videometadata.cpp:1952
VIDEO_COVERFILE_DEFAULT
const QString VIDEO_COVERFILE_DEFAULT
Definition: globals.cpp:25
VIDEO_PLOT_DEFAULT
const QString VIDEO_PLOT_DEFAULT
Definition: globals.cpp:32
VideoScannerThread::m_liveSGHosts
QStringList m_liveSGHosts
Definition: videoscan.h:106
MThread::qthread
QThread * qthread(void)
Returns the thread, this will always return the same pointer no matter how often you restart the thre...
Definition: mthread.cpp:236
MThread::RunEpilog
void RunEpilog(void)
Cleans up a thread's resources, call this if you reimplement run().
Definition: mthread.cpp:209
VIDEO_TRAILER_DEFAULT
const QString VIDEO_TRAILER_DEFAULT
Definition: globals.cpp:26
uint
unsigned int uint
Definition: compat.h:79
gCoreContext
MythCoreContext * gCoreContext
This global variable contains the MythCoreContext instance for the app.
Definition: mythcorecontext.cpp:59
VideoScannerThread::m_dbMetadata
VideoMetadataListManager * m_dbMetadata
Definition: videoscan.h:109
VideoScannerThread::m_removeAll
bool m_removeAll
Definition: videoscan.h:102
VIDEO_INETREF_DEFAULT
const QString VIDEO_INETREF_DEFAULT
Definition: globals.cpp:24
VIDEO_FANART_DEFAULT
const QString VIDEO_FANART_DEFAULT
Definition: globals.cpp:29
videometadatalistmanager.h
VideoScannerThread::m_delList
QList< int > m_delList
Definition: videoscan.h:114
MythDate::fromString
QDateTime fromString(const QString &dtstr)
Converts kFilename && kISODate formats to QDateTime.
Definition: mythdate.cpp:34
MythCoreContext::GetBoolSetting
bool GetBoolSetting(const QString &key, bool defaultval=false)
Definition: mythcorecontext.cpp:910
FileAssociations::getFileAssociation
static FileAssociations & getFileAssociation()
Definition: dbaccess.cpp:831
VideoMetadataListManager::purgeByID
bool purgeByID(unsigned int db_id)
Definition: videometadatalistmanager.cpp:187
VideoScannerThread::m_dbDataChanged
bool m_dbDataChanged
Definition: videoscan.h:115
VideoScannerThread::SetProgressDialog
void SetProgressDialog(MythUIProgressDialog *dialog)
Definition: videoscan.h:71
ScanVideoDirectory
bool ScanVideoDirectory(const QString &start_path, DirectoryHandler *handler, const FileAssociations::ext_ignore_list &ext_disposition, bool list_unknown_extensions)
Definition: dirscan.cpp:227
VideoMetadata::SetHost
void SetHost(const QString &host)
Definition: videometadata.cpp:1842
VideoScannerThread::run
void run() override
Runs the Qt event loop unless we have a QRunnable, in which case we run the runnable run instead.
Definition: videoscan.cpp:161
VideoScannerThread::~VideoScannerThread
~VideoScannerThread() override
Definition: videoscan.cpp:89
VIDEO_RATING_DEFAULT
const QString VIDEO_RATING_DEFAULT
Definition: globals.cpp:30
VideoScannerThread::m_parent
QObject * m_parent
Definition: videoscan.h:99
mythcontext.h
MThread
This is a wrapper around QThread that does several additional things.
Definition: mthread.h:48
VideoScannerThread::VideoScannerThread
VideoScannerThread(QObject *parent)
Definition: videoscan.cpp:80
GetMythMainWindow
MythMainWindow * GetMythMainWindow(void)
Definition: mythmainwindow.cpp:102
MThread::isRunning
bool isRunning(void) const
Definition: mthread.cpp:266
VideoMetadata::GetID
unsigned int GetID() const
Definition: videometadata.cpp:1737
VideoScannerThread::verifyFiles
void verifyFiles(FileCheckList &files, PurgeList &remove)
Definition: videoscan.cpp:247
VIDEO_YEAR_DEFAULT
@ VIDEO_YEAR_DEFAULT
Definition: videometadata.h:18
VideoScanChanges
Definition: videoscan.h:44
VideoScannerThread::removeOrphans
void removeOrphans(unsigned int id, const QString &filename)
Definition: videoscan.cpp:231
MythMainWindow::GetStack
MythScreenStack * GetStack(const QString &Stackname)
Definition: mythmainwindow.cpp:320
VideoMetadataListManager::metadata_list
std::list< VideoMetadataPtr > metadata_list
Definition: videometadatalistmanager.h:14
VideoScanner::~VideoScanner
~VideoScanner() override
Definition: videoscan.cpp:421
VideoScannerThread::updateDB
bool updateDB(const FileCheckList &add, const PurgeList &remove)
Definition: videoscan.cpp:307
VideoScannerThread::m_offlineSGHosts
QStringList m_offlineSGHosts
Definition: videoscan.h:107
VideoScannerThread::FileCheckList
std::map< QString, CheckStruct > FileCheckList
Definition: videoscan.h:86
VideoScannerThread::m_hasGUI
bool m_hasGUI
Definition: videoscan.h:104
MythCoreContext::HasGUI
bool HasGUI(void) const
Definition: mythcorecontext.cpp:1748
VIDEO_BANNER_DEFAULT
const QString VIDEO_BANNER_DEFAULT
Definition: globals.cpp:28
VideoScannerThread::SetHosts
void SetHosts(const QStringList &hosts)
Definition: videoscan.cpp:94
build_compdb.filename
filename
Definition: build_compdb.py:21
VideoMetadata::VideoFileHash
static QString VideoFileHash(const QString &file_name, const QString &host)
Definition: videometadata.cpp:1123
DirectoryHandler
Definition: dirscan.h:6
mythmainwindow.h
MythScreenStack::AddScreen
virtual void AddScreen(MythScreenType *screen, bool allowFade=true)
Definition: mythscreenstack.cpp:50
VideoScannerThread::m_directories
QStringList m_directories
Definition: videoscan.h:105
ShowOkPopup
MythConfirmationDialog * ShowOkPopup(const QString &message, bool showCancel)
Non-blocking version of MythPopupBox::showOkPopup()
Definition: mythdialogbox.cpp:563
VideoScannerThread::getDataChanged
bool getDataChanged() const
Definition: videoscan.h:73
VideoScanner::finishedScan
void finishedScan()
Definition: videoscan.cpp:472
videoutils.h
RemoteGetActiveBackends
bool RemoteGetActiveBackends(QStringList *list)
return list of backends currently connected to the master
Definition: remoteutil.cpp:570
dirhandler
Definition: videolist.cpp:1143
VideoScannerThread::PurgeList
std::vector< std::pair< int, QString > > PurgeList
Definition: videoscan.h:85
VIDEO_DIRECTOR_DEFAULT
const QString VIDEO_DIRECTOR_DEFAULT
Definition: globals.cpp:23
VIDEO_SCREENSHOT_DEFAULT
const QString VIDEO_SCREENSHOT_DEFAULT
Definition: globals.cpp:27
VideoScanner::doScanAll
void doScanAll(void)
Definition: videoscan.cpp:467
dirhandler::newDir
DirectoryHandler * newDir(const QString &dir_name, const QString &fq_dir_name) override
Definition: videolist.cpp:1157