Ejemplo n.º 1
0
bool MythWebPage::extension(Extension extension, const ExtensionOption *option,
                            ExtensionReturn *output)
{
    if (extension == QWebPage::ErrorPageExtension)
    {
        if (!option || !output)
            return false;

        const ErrorPageExtensionOption *erroroption
                        = static_cast<const ErrorPageExtensionOption *>(option);
        ErrorPageExtensionReturn *erroroutput = NULL;
        erroroutput = static_cast<ErrorPageExtensionReturn *>(output);

        QString filename = "htmls/notfound.html";

        if (!GetMythUI()->FindThemeFile(filename))
            return false;

        QFile file(QLatin1String(qPrintable(filename)));
        bool isOpened = file.open(QIODevice::ReadOnly);

        if (!isOpened)
            return false;

        QString title = tr("Error loading page: %1").arg(erroroption->url.toString());
        QString html = QString(QLatin1String(file.readAll()))
                       .arg(title)
                       .arg(erroroption->errorString)
                       .arg(erroroption->url.toString());

        QBuffer imageBuffer;
        imageBuffer.open(QBuffer::ReadWrite);
        QIcon icon = qApp->style()->standardIcon(QStyle::SP_MessageBoxWarning,
                                                 0, 0);
        QPixmap pixmap = icon.pixmap(QSize(32, 32));

        if (pixmap.save(&imageBuffer, "PNG"))
        {
            html.replace(QLatin1String("IMAGE_BINARY_DATA_HERE"),
                         QString(QLatin1String(imageBuffer.buffer().toBase64())));
        }

        erroroutput->content = html.toUtf8();

        return true;
    }

    return false;
}
Ejemplo n.º 2
0
static int runMenu(QString which_menu)
{
    QString themedir = GetMythUI()->GetThemeDir();

    // find the 'mainmenu' MythThemedMenu so we can use the callback from it
    MythThemedMenu *mainMenu = NULL;
    QObject *parentObject = GetMythMainWindow()->GetMainStack()->GetTopScreen();

    while (parentObject)
    {
        MythThemedMenu *menu = dynamic_cast<MythThemedMenu *>(parentObject);

        if (menu && menu->objectName() == "mainmenu")
        {
            mainMenu = menu;
            break;
        }

        parentObject = parentObject->parent();
    }

    MythThemedMenu *diag = new MythThemedMenu(
        themedir, which_menu, GetMythMainWindow()->GetMainStack(),
        "music menu");

    // save the callback from the main menu
    if (mainMenu)
        mainMenu->getCallback(&m_callback, &m_callbackdata);

    diag->setCallback(MusicCallback, NULL);
    diag->setKillable();

    if (diag->foundTheme())
    {
        if (LCD *lcd = LCD::Get())
        {
            lcd->switchToTime();
        }
        GetMythMainWindow()->GetMainStack()->AddScreen(diag);
        return 0;
    }
    else
    {
        LOG(VB_GENERAL, LOG_ERR, QString("Couldn't find menu %1 or theme %2")
                              .arg(which_menu).arg(themedir));
        delete diag;
        return -1;
    }
}
Ejemplo n.º 3
0
/** \fn     GalleryViewHelper::DeleteCurrentNode()
 *  \brief  Deletes the current node from the generic tree
 *  \return void
 */
void GalleryViewHelper::DeleteCurrentNode()
{
    ImageMetadata *im = GetImageMetadataFromSelectedNode();

    // TODO: Remove directories as well
    if (im && im->m_type >= kImageFile)

        // Delete the file and remove the database entry
        if (m_fileHelper->RemoveFile(im))
        {
            // Remove the entry from the node list
            m_currentNode->deleteNode(m_currentNode->getSelectedChild());

            // Clean up thumbnail cache
            GetMythUI()->RemoveFromCacheByFile(im->m_thumbFileNameList->at(0));
        }
}
Ejemplo n.º 4
0
ZMLivePlayer::ZMLivePlayer(MythScreenStack *parent)
             :MythScreenType(parent, "zmliveview")
{
    m_paused = false;

    m_players = NULL;
    m_monitors = NULL;
    m_monitorLayout = 1;

    GetMythUI()->DoDisableScreensaver();

    m_frameTimer = new QTimer(this);
    connect(m_frameTimer, SIGNAL(timeout()), this,
            SLOT(updateFrame()));

    getMonitorList();
}
Ejemplo n.º 5
0
bool XMLParseBase::LoadBaseTheme(const QString &baseTheme)
{
    VERBOSE(VB_GUI, LOC +
            QString("Asked to load base file from '%1'").arg(baseTheme));

    if (loadedBaseFiles.contains(baseTheme))
    {
        VERBOSE(VB_GUI, LOC +
                QString("Base file already loaded '%1'").arg(baseTheme));
        return true;
    }

    bool ok = false;
    bool loadOnlyWindows = false;
    bool showWarnings = true;

    const QStringList searchpath = GetMythUI()->GetThemeSearchPath();

    QStringList::const_iterator it = searchpath.begin();
    for (; it != searchpath.end(); ++it)
    {
        QString themefile = *it + baseTheme;
        if (doLoad(QString(), GetGlobalObjectStore(), themefile,
                   loadOnlyWindows, showWarnings))
        {
            VERBOSE(VB_GUI, LOC +
                    QString("Loaded base theme from '%1'").arg(themefile));
            // Don't complain about duplicate definitions after first
            // successful load (set showWarnings to false).
            showWarnings = false;
            ok = true;
        }
        else
        {
            VERBOSE(VB_GUI|VB_FILE, LOC_WARN +
                    QString("No theme file '%1'").arg(themefile));
        }
    }

    if (ok)
        loadedBaseFiles.append(baseTheme);

    return ok;
}
Ejemplo n.º 6
0
void ImageView::GetScreenShot(QImage& image, const ThumbItem *item)
{
    QFileInfo fi(item->GetPath());
    QString screenshot = QString("%1%2-screenshot.jpg")
                                .arg(ThumbGenerator::getThumbcacheDir(fi.path()))
                                .arg(item->GetName());

    if (QFile::exists(screenshot))
    {
        QImage img(screenshot);
        image = img;
    }
    else
    {
        QString movie("gallery-moviethumb.png");
        if (GetMythUI()->FindThemeFile(movie))
            image.load(movie);
    }
}
Ejemplo n.º 7
0
/** \fn     GalleryViewHelper::DeleteSelectedNodes()
 *  \brief  Deletes multiple selected nodes from the generic tree
 *  \return void
 */
void GalleryViewHelper::DeleteSelectedNodes()
{
    QList<MythGenericTree *> *nodeTree = m_currentNode->getAllChildren();
    for (int i = 0; i < nodeTree->size(); i++)
    {
        ImageMetadata *im = nodeTree->at(i)->GetData().value<ImageMetadata *>();

        // TODO: Remove directories as well
        if (im && im->m_selected && im->m_type >= kImageFile)
        {
            // Delete the file and remove the database entry
            if (m_fileHelper->RemoveFile(im))
            {
                // Clean up thumbnail cache
                GetMythUI()->RemoveFromCacheByFile(im->m_thumbFileNameList->at(0));

                // Remove the entry from the node list
                m_currentNode->deleteNode(nodeTree->at(i));
            }
        }
    }
}
Ejemplo n.º 8
0
bool MythXDisplay::Open(void)
{
    MythXLocker locker(this);

    QString dispStr = GetMythUI()->GetX11Display();
    const char *dispCStr = NULL;
    if (!dispStr.isEmpty())
        dispCStr = dispStr.toAscii().constData();

    m_disp = XOpenDisplay(dispCStr);
    if (!m_disp)
        return false;

    xdisplays[m_disp] = this;
    m_screen_num = DefaultScreen(m_disp);
    m_screen     = DefaultScreenOfDisplay(m_disp);
    m_black      = XBlackPixel(m_disp, m_screen_num);
    m_depth      = DefaultDepthOfScreen(m_screen);
    m_root       = DefaultRootWindow(m_disp);

    return true;
}
Ejemplo n.º 9
0
void MythUIImage::FindRandomImage(void)
{
    QDir imageDir(m_imageDirectory);

    if (!imageDir.exists())
    {
        QString themeDir = GetMythUI()->GetThemeDir() + '/';
        imageDir = themeDir + m_imageDirectory;
    }

    QStringList imageTypes;

    QList< QByteArray > exts = QImageReader::supportedImageFormats();
    QList< QByteArray >::Iterator it = exts.begin();

    for (; it != exts.end(); ++it)
    {
        imageTypes.append(QString("*.").append(*it));
    }

    imageDir.setNameFilters(imageTypes);

    QStringList imageList = imageDir.entryList();
    QString randFile;

    if (imageList.size())
    {
        // try to find a different image
        do
        {
            randFile = QString("%1%2").arg(m_imageDirectory)
                                      .arg(imageList.takeAt(random() % imageList.size()));

        } while (imageList.size() > 1 && randFile == m_OrigFilename);
    }

    m_OrigFilename = m_imageProperties.filename = randFile;
}
Ejemplo n.º 10
0
QPixmap *EditMetadataDialog::createScaledPixmap(QString filename,
                                         int width, int height, Qt::AspectRatioMode mode)
{
    QPixmap *pixmap = NULL;

    if (!filename.isEmpty())
    {
        QImage *img = GetMythUI()->LoadScaleImage(filename);
        if (!img)
        {
            VERBOSE(VB_IMPORTANT, QString("EditMetadataDialog: Failed to load image %1").arg(filename));
            return NULL;
        }
        else
        {
            pixmap = new QPixmap(img->scaled(width, height,
                                    mode, Qt::SmoothTransformation));
            delete img;
        }
    }

    return pixmap;
}
Ejemplo n.º 11
0
DialogCode ProfileGroupEditor::exec(void)
{
    DialogCode ret = kDialogCodeAccepted;
    redraw = true;

    while ((QDialog::Accepted == ret) || redraw)
    {
        redraw = false;

        Load();

        dialog = new ConfigurationDialogWidget(GetMythMainWindow(),
                                               "ProfileGroupEditor");

        connect(dialog, SIGNAL(menuButtonPressed()), this, SLOT(callDelete()));

        int   width = 0,    height = 0;
        float wmult = 0.0f, hmult  = 0.0f;
        GetMythUI()->GetScreenSettings(width, wmult, height, hmult);

        QVBoxLayout *layout = new QVBoxLayout(dialog);
        layout->setMargin((int)(20 * hmult));
        layout->addWidget(listbox->configWidget(NULL, dialog));

        dialog->Show();

        ret = dialog->exec();

        dialog->deleteLater();
        dialog = NULL;

        if (ret == QDialog::Accepted)
            open(listbox->getValue().toInt());
    }

    return kDialogCodeRejected;
}
Ejemplo n.º 12
0
static void runMusicSelection(void)
{
    GetMythUI()->AddCurrentLocation("musicplaylists");
    startDatabaseTree();
    GetMythUI()->RemoveCurrentLocation();
}
Ejemplo n.º 13
0
static void runMusicPlayback(void)
{
    GetMythUI()->AddCurrentLocation("playmusic");
    startPlayback();
    GetMythUI()->RemoveCurrentLocation();
}
Ejemplo n.º 14
0
int main(int argc, char **argv)
{
    bool bShowSettings = false;

    MythWelcomeCommandLineParser cmdline;
    if (!cmdline.Parse(argc, argv))
    {
        cmdline.PrintHelp();
        return GENERIC_EXIT_INVALID_CMDLINE;
    }

    if (cmdline.toBool("showhelp"))
    {
        cmdline.PrintHelp();
        return GENERIC_EXIT_OK;
    }

    if (cmdline.toBool("showversion"))
    {
        cmdline.PrintVersion();
        return GENERIC_EXIT_OK;
    }
    
    QApplication a(argc, argv);
    QCoreApplication::setApplicationName(MYTH_APPNAME_MYTHWELCOME);

    int retval;
    if ((retval = cmdline.ConfigureLogging()) != GENERIC_EXIT_OK)
        return retval;

    if (cmdline.toBool("setup"))
        bShowSettings = true;

#ifndef _WIN32
    QList<int> signallist;
    signallist << SIGINT << SIGTERM << SIGSEGV << SIGABRT << SIGBUS << SIGFPE
               << SIGILL;
    SignalHandler handler(signallist);
    signal(SIGHUP, SIG_IGN);
#endif

    gContext = new MythContext(MYTH_BINARY_VERSION);
    if (!gContext->Init())
    {
        LOG(VB_GENERAL, LOG_ERR,
            "mythwelcome: Could not initialize MythContext. Exiting.");
        return GENERIC_EXIT_NO_MYTHCONTEXT;
    }

    if (!MSqlQuery::testDBConnection())
    {
        LOG(VB_GENERAL, LOG_ERR,
            "mythwelcome: Could not open the database. Exiting.");
        return -1;
    }

    LCD::SetupLCD();

    if (LCD *lcd = LCD::Get())
        lcd->switchToTime();

    MythTranslation::load("mythfrontend");

    GetMythUI()->LoadQtConfig();

    MythMainWindow *mainWindow = GetMythMainWindow();
    mainWindow->Init();

    initKeys();

    if (bShowSettings)
    {
        MythShutdownSettings settings;
        settings.exec();
    }
    else
    {
        MythScreenStack *mainStack = GetMythMainWindow()->GetMainStack();

        WelcomeDialog *welcome = new WelcomeDialog(mainStack, "mythwelcome");

        if (welcome->Create())
            mainStack->AddScreen(welcome, false);
        else
            return -1;

        do
        {
            qApp->processEvents();
            usleep(5000);
        } while (mainStack->TotalScreens() > 0);
    }

    DestroyMythMainWindow();

    delete gContext;

    return 0;
}
Ejemplo n.º 15
0
bool MythUIText::ParseElement(
    const QString &filename, QDomElement &element, bool showWarnings)
{
    if (element.tagName() == "area")
    {
        SetArea(parseRect(element));
        m_OrigDisplayRect = m_Area;
    }
//    else if (element.tagName() == "altarea") // Unused, but maybe in future?
//        m_AltDisplayRect = parseRect(element);
    else if (element.tagName() == "font")
    {
        QString fontname = getFirstText(element);
        MythFontProperties *fp = GetFont(fontname);
        if (!fp)
            fp = GetGlobalFontMap()->GetFont(fontname);
        if (fp)
        {
            MythFontProperties font = *fp;
            int screenHeight = GetMythMainWindow()->GetUIScreenRect().height();
            font.Rescale(screenHeight);
            int fontStretch = GetMythUI()->GetFontStretch();
            font.AdjustStretch(fontStretch);
            QString state = element.attribute("state","");
            if (!state.isEmpty())
            {
                m_FontStates.insert(state, font);
            }
            else
            {
                m_FontStates.insert("default", font);
                *m_Font = m_FontStates["default"];
            }
        }
    }
    else if (element.tagName() == "value")
    {
        if (element.attribute("lang","").isEmpty())
        {
            m_Message = qApp->translate("ThemeUI",
                                        parseText(element).toUtf8(), NULL,
                                        QCoreApplication::UnicodeUTF8);
        }
		#if 0
        else if (element.attribute("lang","").toLower() ==
                 gCoreContext->GetLanguageAndVariant())
        #else
		else if (element.attribute("lang","").toLower() ==
                 "en_us")
	 #endif
        {
            m_Message = parseText(element);
        }
	 #if 0
        else if (element.attribute("lang","").toLower() ==
                 gCoreContext->GetLanguage())
	#else
		else if (element.attribute("lang","").toLower() ==
                 "en")
	#endif
        {
            m_Message = parseText(element);
        }

        m_DefaultMessage = m_Message;
        SetText(m_Message);
    }
    else if (element.tagName() == "template")
Ejemplo n.º 16
0
MythImage *MythUIHelper::CacheImage(const QString &url, MythImage *im,
                                    bool nodisk)
{
    if (!im)
        return NULL;

    if (!nodisk)
    {
        QString dstfile = GetMythUI()->GetThemeCacheDir() + '/' + url;

        LOG(VB_GUI | VB_FILE, LOG_INFO, LOC +
            QString("Saved to Cache (%1)").arg(dstfile));

        // This would probably be better off somewhere else before any
        // Load() calls at all.
        QDir themedir(GetMythUI()->GetThemeCacheDir());

        if (!themedir.exists())
            themedir.mkdir(GetMythUI()->GetThemeCacheDir());

        // Save to disk cache
        im->save(dstfile, "PNG");
    }

    // delete the oldest cached images until we fall below threshold.
    QMutexLocker locker(d->m_cacheLock);

    while (d->m_cacheSize.fetchAndAddOrdered(0) + im->byteCount() >=
           d->m_maxCacheSize.fetchAndAddOrdered(0) &&
           d->imageCache.size())
    {
        QMap<QString, MythImage *>::iterator it = d->imageCache.begin();
        uint oldestTime = MythDate::current().toTime_t();
        QString oldestKey = it.key();

        int count = 0;

        for (; it != d->imageCache.end(); ++it)
        {
            if (d->CacheTrack[it.key()] < oldestTime)
            {
                if ((2 == it.value()->IncrRef()) && (it.value() != im))
                {
                    oldestTime = d->CacheTrack[it.key()];
                    oldestKey = it.key();
                    count++;
                }
                it.value()->DecrRef();
            }
        }

        LOG(VB_GUI | VB_FILE, LOG_INFO, LOC +
            QString("%1 images are eligible for expiry").arg(count));

        if (count > 0)
        {
            LOG(VB_GUI | VB_FILE, LOG_INFO, LOC +
                QString("Cache too big (%1), removing :%2:")
                .arg(d->m_cacheSize.fetchAndAddOrdered(0) + im->byteCount())
                .arg(oldestKey));

            d->imageCache[oldestKey]->SetIsInCache(false);
            d->imageCache[oldestKey]->DecrRef();
            d->imageCache.remove(oldestKey);
            d->CacheTrack.remove(oldestKey);
        }
        else
        {
            break;
        }
    }

    QMap<QString, MythImage *>::iterator it = d->imageCache.find(url);

    if (it == d->imageCache.end())
    {
        im->IncrRef();
        d->imageCache[url] = im;
        d->CacheTrack[url] = MythDate::current().toTime_t();

        im->SetIsInCache(true);
        LOG(VB_GUI | VB_FILE, LOG_INFO, LOC +
            QString("NOT IN RAM CACHE, Adding, and adding to size :%1: :%2:")
            .arg(url).arg(im->byteCount()));
    }

    LOG(VB_GUI | VB_FILE, LOG_INFO, LOC +
        QString("MythUIHelper::CacheImage : Cache Count = :%1: size :%2:")
        .arg(d->imageCache.count())
        .arg(d->m_cacheSize.fetchAndAddRelaxed(0)));

    return d->imageCache[url];
}
Ejemplo n.º 17
0
void MetadataImageDownload::run()
{
    // Always handle thumbnails first, they're higher priority.
    ThumbnailData *thumb;
    while ((thumb = moreThumbs()) != NULL)
    {
        QString sFilename = getDownloadFilename(thumb->title, thumb->url);

        bool exists = QFile::exists(sFilename);
        if (!exists && !thumb->url.isEmpty())
            GetMythDownloadManager()->download(thumb->url, sFilename);

        // inform parent we have thumbnail ready for it
        if (QFile::exists(sFilename) && m_parent)
        {
            VERBOSE(VB_GENERAL|VB_EXTRA,
                    QString("Threaded Image Thumbnail Download: %1")
                    .arg(sFilename));
            thumb->url = sFilename;
            QCoreApplication::postEvent(m_parent,
                           new ThumbnailDLEvent(thumb));
        }
        else
            delete thumb;
    }

    MetadataLookup *lookup;
    while ((lookup = moreDownloads()) != NULL)
    {
        DownloadMap downloads = lookup->GetDownloads();
        DownloadMap downloaded;

        for (DownloadMap::iterator i = downloads.begin();
                i != downloads.end(); ++i)
        {
            ArtworkType type = i.key();
            ArtworkInfo info = i.value();
            QString filename = getDownloadFilename( type, lookup,
                                   info.url );
            if (lookup->GetHost().isEmpty())
            {
                QString path = getLocalWritePath(lookup->GetType(), type);
                QDir dirPath(path);
                if (!dirPath.exists())
                    if (!dirPath.mkpath(path))
                    {
                        VERBOSE(VB_GENERAL,
                             QString("Metadata Image Download: Unable to create "
                                     "path %1, aborting download.").arg(path));
                        continue;
                    }
                QString finalfile = path + "/" + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                if (!QFile::exists(finalfile) || lookup->GetAllowOverwrites())
                {
                    QFile dest_file(finalfile);
                    if (dest_file.exists())
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        dest_file.remove();
                    }

                    VERBOSE(VB_GENERAL,
                         QString("Metadata Image Download: %1 ->%2")
                         .arg(oldurl).arg(finalfile));
                    QByteArray *download = new QByteArray();
                    GetMythDownloadManager()->download(oldurl, download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(*download);
                    if (!didLoad)
                    {
                        VERBOSE(VB_IMPORTANT,QString("Tried to write %1, "
                                "but it appears to be an HTML redirect "
                                "(filesize %2).")
                                .arg(oldurl).arg(download->size()));
                        delete download;
                        download = NULL;
                        continue;
                    }

                    if (dest_file.open(QIODevice::WriteOnly))
                    {
                        off_t size = dest_file.write(*download, download->size());
                        if (size != download->size())
                        {
                            VERBOSE(VB_IMPORTANT,
                            QString("Image Download: Error Writing Image "
                                    "to file: %1").arg(finalfile));
                        }
                        else
                            downloaded.insert(type, info);
                    }

                    delete download;
                }
                else
                    downloaded.insert(type, info);
            }
            else
            {
                QString path = getStorageGroupURL(type, lookup->GetHost());
                QString finalfile = path + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                if (!RemoteFile::Exists(finalfile) || lookup->GetAllowOverwrites())
                {

                    if (RemoteFile::Exists(finalfile))
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        RemoteFile::DeleteFile(finalfile);
                    }

                    VERBOSE(VB_GENERAL,
                        QString("Metadata Image Download: %1 -> %2")
                        .arg(oldurl).arg(finalfile));
                    QByteArray *download = new QByteArray();
                    GetMythDownloadManager()->download(oldurl, download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(*download);
                    if (!didLoad)
                    {
                        VERBOSE(VB_IMPORTANT,QString("Tried to write %1, "
                                "but it appears to be an HTML redirect "
                                "or corrupt file (filesize %2).")
                                .arg(oldurl).arg(download->size()));
                        delete download;
                        download = NULL;
                        continue;
                    }

                    RemoteFile *outFile = new RemoteFile(finalfile, true);
                    if (!outFile->isOpen())
                    {
                        VERBOSE(VB_IMPORTANT,
                            QString("Image Download: Failed to open "
                                    "remote file (%1) for write.  Does "
                                    "Storage Group Exist?")
                                    .arg(finalfile));
                        delete outFile;
                        outFile = NULL;
                    }
                    else
                    {
                        off_t written = outFile->Write(*download,
                                                       download->size());
                        if (written != download->size())
                        {
                            VERBOSE(VB_IMPORTANT,
                            QString("Image Download: Error Writing Image "
                                    "to file: %1").arg(finalfile));
                        }
                        else
                            downloaded.insert(type, info);
                        delete outFile;
                        outFile = NULL;
                    }

                    delete download;
                }
                else
                    downloaded.insert(type, info);
            }
        }
        lookup->SetDownloads(downloaded);
        QCoreApplication::postEvent(m_parent, new ImageDLEvent(lookup));
    }
}
Ejemplo n.º 18
0
void EditAlbumartDialog::customEvent(QEvent *event)
{
    if (event->type() == DialogCompletionEvent::kEventType)
    {
        DialogCompletionEvent *dce = (DialogCompletionEvent*)(event);

        // make sure the user didn't ESCAPE out of the menu
        if (dce->GetResult() < 0)
            return;

        QString resultid   = dce->GetId();
        QString resulttext = dce->GetResultText();

        if (resultid == "changetypemenu")
        {
            int type = dce->GetData().toInt();

            if ((type >= IT_UNKNOWN) && (type < IT_LAST))
            {
                // get selected image in list
                MythUIButtonListItem *item = m_coverartList->GetItemCurrent();
                if (item)
                {
                    item->SetText(m_albumArt->getTypeName((ImageType) type));
                    AlbumArtImage *image = qVariantValue<AlbumArtImage*> (item->GetData());
                    if (image)
                    {
                        AlbumArtImage oldImage = *image;

                        image->imageType = (ImageType) type;

                        if (image->imageType == oldImage.imageType)
                            return;

                        // rename any cached image to match the new type
                        if (image->embedded)
                        {
                            // update the new cached image filename
                            image->filename = QString(GetConfDir() + "/MythMusic/AlbumArt/%1-%2.jpg")
                                                .arg(m_metadata->ID())
                                                .arg(AlbumArtImages::getTypeFilename(image->imageType));

                            if (image->filename != oldImage.filename && QFile::exists(oldImage.filename))
                            {
                                // remove any old cached file with the same name as the new one
                                QFile::remove(image->filename);
                                // rename the old cached file to the new one
                                QFile::rename(oldImage.filename, image->filename);

                                // force the theme image cache to refresh the image
                                GetMythUI()->RemoveFromCacheByFile(image->filename);
                            }

                            // change the image type in the tag if it supports it
                            MetaIO *tagger = m_metadata->getTagger();

                            if (tagger && tagger->supportsEmbeddedImages())
                            {
                                if (!tagger->changeImageType(m_metadata->Filename(), &oldImage, image->imageType))
                                    LOG(VB_GENERAL, LOG_INFO, "EditAlbumartDialog: failed to change image type");
                            }
                        }
                        else
                        {
                            QFileInfo fi(oldImage.filename);

                            // get the new images filename
                            image->filename = QString(fi.absolutePath() + "/%1.jpg")
                                    .arg(AlbumArtImages::getTypeFilename(image->imageType));

                            if (image->filename != oldImage.filename && QFile::exists(oldImage.filename))
                            {
                                // remove any old cached file with the same name as the new one
                                QFile::remove(image->filename);
                                // rename the old cached file to the new one
                                QFile::rename(oldImage.filename, image->filename);

                                // force the theme image cache to refresh the image
                                GetMythUI()->RemoveFromCacheByFile(image->filename);
                            }
                        }

                        m_albumArtChanged = true;

                        gridItemChanged(item);
                    }
                }
            }
        }
        else if (resultid == "asktypemenu")
        {
            int type = dce->GetData().toInt();

            if ((type >= IT_UNKNOWN) && (type < IT_LAST))
                copyImageToTag((ImageType) type);
        }
        else if (resultid == "optionsmenu")
        {
            if (resulttext == tr("Edit Metadata"))
                switchToMetadata();
            else if (resulttext == tr("Rescan For Images"))
                rescanForImages();
            else if (resulttext == tr("Search Internet For Images"))
                searchForAlbumImages();
            else if (resulttext == tr("Change Image Type"))
                showTypeMenu();
            else if (resulttext == tr("Copy Selected Image To Tag"))
                copySelectedImageToTag();
            else if (resulttext == tr("Remove Selected Image From Tag"))
                removeSelectedImageFromTag();
            else if (resulttext == tr("Copy Image To Tag"))
                startCopyImageToTag();
        }
        else if (resultid == "imagelocation")
        {
            m_imageFilename = resulttext;

            // save directory location for next time
            QFileInfo fi(m_imageFilename);
            gCoreContext->SaveSetting("MusicLastImageLocation", fi.canonicalPath());

            showTypeMenu(false);
        }
    }
    else if (event->type() == MythEvent::MythEventMessage)
    {
        MythEvent *me = (MythEvent *)event;
        QStringList tokens = me->Message().split(" ", QString::SkipEmptyParts);

        if (!tokens.isEmpty())
        {
            if (tokens[0] == "BROWSER_DOWNLOAD_FINISHED")
                rescanForImages();
        }
    }
}
Ejemplo n.º 19
0
void MetadataImageDownload::run()
{
    RunProlog();

    // Always handle thumbnails first, they're higher priority.
    ThumbnailData *thumb;
    while ((thumb = moreThumbs()) != NULL)
    {
        QString sFilename = getDownloadFilename(thumb->title, thumb->url);

        bool exists = QFile::exists(sFilename);
        if (!exists && !thumb->url.isEmpty())
        {
            if (!GetMythDownloadManager()->download(thumb->url, sFilename))
            {
                LOG(VB_GENERAL, LOG_ERR,
                    QString("MetadataImageDownload: failed to download thumbnail from: %1")
                    .arg(thumb->url));

                delete thumb;
                continue;
            }
        }

        // inform parent we have thumbnail ready for it
        if (QFile::exists(sFilename) && m_parent)
        {
            LOG(VB_GENERAL, LOG_DEBUG,
                QString("Threaded Image Thumbnail Download: %1")
                .arg(sFilename));
            thumb->url = sFilename;
            QCoreApplication::postEvent(m_parent,
                                        new ThumbnailDLEvent(thumb));
        }
        else
            delete thumb;
    }

    while (true)
    {
        m_mutex.lock();
        if (m_downloadList.isEmpty())
        {
            // no more to process, we're done
            m_mutex.unlock();
            break;
        }
        // Ref owns the MetadataLookup object for the duration of the loop
        // and it will be deleted automatically when the loop completes
        RefCountHandler<MetadataLookup> ref = m_downloadList.takeFirstAndDecr();
        m_mutex.unlock();
        MetadataLookup *lookup = ref;
        DownloadMap downloads = lookup->GetDownloads();
        DownloadMap downloaded;

        bool errored = false;
        for (DownloadMap::iterator i = downloads.begin();
                i != downloads.end(); ++i)
        {
            VideoArtworkType type = i.key();
            ArtworkInfo info = i.value();
            QString filename = getDownloadFilename( type, lookup,
                                                    info.url );
            if (lookup->GetHost().isEmpty())
            {
                QString path = getLocalWritePath(lookup->GetType(), type);
                QDir dirPath(path);
                if (!dirPath.exists())
                {
                    if (!dirPath.mkpath(path))
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Metadata Image Download: Unable to create "
                                    "path %1, aborting download.").arg(path));
                        errored = true;
                        break;
                    }
                }
                QString finalfile = path + "/" + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                if (!QFile::exists(finalfile) || lookup->GetAllowOverwrites())
                {
                    QFile dest_file(finalfile);
                    if (dest_file.exists())
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        dest_file.remove();
                    }

                    LOG(VB_GENERAL, LOG_INFO,
                        QString("Metadata Image Download: %1 ->%2")
                        .arg(oldurl).arg(finalfile));
                    QByteArray download;
                    GetMythDownloadManager()->download(oldurl, &download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(download);
                    if (!didLoad)
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Tried to write %1, but it appears to be "
                                    "an HTML redirect (filesize %2).")
                            .arg(oldurl).arg(download.size()));
                        errored = true;
                        break;
                    }

                    if (dest_file.open(QIODevice::WriteOnly))
                    {
                        off_t size = dest_file.write(download,
                                                     download.size());
                        dest_file.close();
                        if (size != download.size())
                        {
                            // File creation failed for some reason, delete it
                            RemoteFile::DeleteFile(finalfile);
                            LOG(VB_GENERAL, LOG_ERR,
                                QString("Image Download: Error Writing Image "
                                        "to file: %1").arg(finalfile));
                            errored = true;
                            break;
                        }
                    }
                }
            }
            else
            {
                QString path = getStorageGroupURL(type, lookup->GetHost());
                QString finalfile = path + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                bool exists = false;
                bool onMaster = false;
                QString resolvedFN;
                if (gCoreContext->IsMasterBackend() &&
                        gCoreContext->IsThisHost(lookup->GetHost()))
                {
                    StorageGroup sg(getStorageGroupName(type), lookup->GetHost());
                    resolvedFN = sg.FindFile(filename);
                    exists = !resolvedFN.isEmpty() && QFile::exists(resolvedFN);
                    if (!exists)
                    {
                        resolvedFN = getLocalStorageGroupPath(type,
                                                              lookup->GetHost()) + "/" + filename;
                    }
                    onMaster = true;
                }
                else
                    exists = RemoteFile::Exists(finalfile);

                if (!exists || lookup->GetAllowOverwrites())
                {
                    if (exists && !onMaster)
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        RemoteFile::DeleteFile(finalfile);
                    }
                    else if (exists)
                        QFile::remove(resolvedFN);

                    LOG(VB_GENERAL, LOG_INFO,
                        QString("Metadata Image Download: %1 -> %2")
                        .arg(oldurl).arg(finalfile));
                    QByteArray download;
                    GetMythDownloadManager()->download(oldurl, &download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(download);
                    if (!didLoad)
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Tried to write %1, but it appears to be "
                                    "an HTML redirect or corrupt file "
                                    "(filesize %2).")
                            .arg(oldurl).arg(download.size()));
                        errored = true;
                        break;
                    }

                    if (!onMaster)
                    {
                        RemoteFile outFile(finalfile, true);

                        if (!outFile.isOpen())
                        {
                            LOG(VB_GENERAL, LOG_ERR,
                                QString("Image Download: Failed to open "
                                        "remote file (%1) for write.  Does "
                                        "Storage Group Exist?")
                                .arg(finalfile));
                            errored = true;
                            break;
                        }
                        off_t written = outFile.Write(download,
                                                      download.size());
                        if (written != download.size())
                        {
                            // File creation failed for some reason, delete it
                            RemoteFile::DeleteFile(finalfile);

                            LOG(VB_GENERAL, LOG_ERR,
                                QString("Image Download: Error Writing Image "
                                        "to file: %1").arg(finalfile));
                            errored = true;
                            break;
                        }
                    }
                    else
                    {
                        QFile dest_file(resolvedFN);
                        if (dest_file.open(QIODevice::WriteOnly))
                        {
                            off_t size = dest_file.write(download,
                                                         download.size());
                            dest_file.close();
                            if (size != download.size())
                            {
                                // File creation failed for some reason, delete it
                                RemoteFile::DeleteFile(resolvedFN);
                                LOG(VB_GENERAL, LOG_ERR,
                                    QString("Image Download: Error Writing Image "
                                            "to file: %1").arg(finalfile));
                                errored = true;
                                break;
                            }
                        }
                    }
                }
            }
            if (!errored)
            {
                // update future Artwork Map with what we've successfully
                // retrieved (either downloaded or already existing
                downloaded.insert(type, info);
            }
        }
        if (errored)
        {
            QCoreApplication::postEvent(m_parent,
                                        new ImageDLFailureEvent(lookup));
            errored = false;
        }
        lookup->SetDownloads(downloaded);
        QCoreApplication::postEvent(m_parent, new ImageDLEvent(lookup));
    }

    RunEpilog();
}
Ejemplo n.º 20
0
bool MythUIVirtualKeyboard::Create()
{
    if (!LoadWindowFromXML("keyboard/keyboard.xml", "keyboard", this))
        return false;

    BuildFocusList();

    loadKeyDefinitions(gCoreContext->GetLanguageAndVariant());
    updateKeys(true);

    int screenWidth, screenHeight;
    float xmult, ymult;
    GetMythUI()->GetScreenSettings(screenWidth, xmult, screenHeight, ymult);
    MythRect editArea = m_parentEdit->GetArea();
    MythRect area = GetArea();
    MythPoint newPos;

    //FIXME this assumes the edit is a direct child of the parent screen
    MythUIType *parentScreen = NULL;
    parentScreen = dynamic_cast<MythUIType *>(m_parentEdit->parent());
    if (parentScreen)
    {
        editArea.moveTopLeft(QPoint(editArea.x() + parentScreen->GetArea().x(),
                                    editArea.y() + parentScreen->GetArea().y()));
    }

    switch (m_preferredPos)
    {
        case VK_POSABOVEEDIT:
            if (editArea.y() - area.height() - 5 > 0)
            {
                newPos = QPoint(editArea.x() + editArea.width() / 2 - area.width() / 2,
                                editArea.y() - area.height() - 5);
            }
            else
            {
                newPos = QPoint(editArea.x() + editArea.width() / 2 - area.width() / 2,
                                editArea.y() + editArea.height() + 5);
            }
            break;

        case VK_POSTOPDIALOG:
            newPos = QPoint(screenWidth / 2 - area.width() / 2, 5);
            break;

        case VK_POSBOTTOMDIALOG:
            newPos = QPoint(screenWidth / 2 - area.width() / 2, screenHeight - 5 - area.height());
            break;

        case VK_POSCENTERDIALOG:
            newPos = QPoint(screenWidth / 2 - area.width() / 2, screenHeight / 2 - area.height() / 2);
            break;

        default:
            // VK_POSBELOWEDIT
            if (editArea.y() + editArea.height() + area.height() + 5 < screenHeight)
            {
                newPos = QPoint(editArea.x() + editArea.width() / 2 - area.width() / 2,
                                editArea.y() + editArea.height() + 5);
            }
            else
            {
                newPos = QPoint(editArea.x() + editArea.width() / 2 - area.width() / 2,
                                editArea.y() - area.height() - 5);
            }
            break;
    }

    // make sure the popup doesn't go off screen
    if (newPos.x() < 5)
        newPos.setX(5);
    if (newPos.x() + area.width() + 5 > screenWidth)
        newPos.setX(screenWidth - area.width() - 5);
    if (newPos.y() < 5)
        newPos.setY(5);
    if (newPos.y() + area.height() + 5 > screenHeight)
        newPos.setY(screenHeight - area.height() - 5);

    SetPosition(newPos);

    return true;
}
Ejemplo n.º 21
0
/**
 *  \copydoc MythUIType::ParseElement()
 */
bool MythUIImage::ParseElement(
    const QString &filename, QDomElement &element, bool showWarnings)
{
    QWriteLocker updateLocker(&d->m_UpdateLock);

    if (element.tagName() == "filename")
    {
        m_imageProperties.isThemeImage = true; // This is an image distributed with the them
        m_OrigFilename = m_imageProperties.filename = getFirstText(element);

        if (m_imageProperties.filename.endsWith('/'))
        {
            m_showingRandomImage = true;
            m_imageDirectory = m_imageProperties.filename;

            FindRandomImage();
        }
    }
    else if (element.tagName() == "filepattern")
    {
        m_imageProperties.isThemeImage = true; // This is an image distributed with the theme
        m_OrigFilename = m_imageProperties.filename = getFirstText(element);
        QString tmp = element.attribute("low");

        if (!tmp.isEmpty())
            m_LowNum = tmp.toInt();

        tmp = element.attribute("high");

        if (!tmp.isEmpty())
            m_HighNum = tmp.toInt();

        tmp = element.attribute("cycle", "start");

        if (tmp == "reverse")
            m_animationCycle = kCycleReverse;
    }
    else if (element.tagName() == "area")
    {
        SetArea(parseRect(element));
        m_imageProperties.forceSize = m_Area.size();
    }
    else if (element.tagName() == "preserveaspect")
        m_imageProperties.preserveAspect = parseBool(element);
    else if (element.tagName() == "crop")
        m_imageProperties.cropRect = parseRect(element);
    else if (element.tagName() == "delay")
    {
        QString value = getFirstText(element);

        if (value.contains(","))
        {
            QVector<int> delays;
            QStringList tokens = value.split(",");
            QStringList::iterator it = tokens.begin();

            for (; it != tokens.end(); ++it)
            {
                if ((*it).isEmpty())
                {
                    if (delays.size())
                        delays.append(delays[delays.size()-1]);
                    else
                        delays.append(0); // Default 0ms delay before first image
                }
                else
                {
                    delays.append((*it).toInt());
                }
            }

            if (delays.size())
            {
                m_Delay = delays[0];
                SetDelays(delays);
            }
        }
        else
        {
            m_Delay = value.toInt();
        }
    }
    else if (element.tagName() == "reflection")
    {
        m_imageProperties.isReflected = true;
        QString tmp = element.attribute("axis");

        if (!tmp.isEmpty())
        {
            if (tmp.toLower() == "horizontal")
                m_imageProperties.reflectAxis = ReflectHorizontal;
            else
                m_imageProperties.reflectAxis = ReflectVertical;
        }

        tmp = element.attribute("shear");

        if (!tmp.isEmpty())
            m_imageProperties.reflectShear = tmp.toInt();

        tmp = element.attribute("scale");

        if (!tmp.isEmpty())
            m_imageProperties.reflectScale = tmp.toInt();

        tmp = element.attribute("length");

        if (!tmp.isEmpty())
            m_imageProperties.reflectLength = tmp.toInt();

        tmp = element.attribute("spacing");

        if (!tmp.isEmpty())
            m_imageProperties.reflectSpacing = tmp.toInt();
    }
    else if (element.tagName() == "mask")
    {
        QString maskfile = getFirstText(element);

        MythImage *newMaskImage = GetPainter()->GetFormatImage();
        if (newMaskImage->Load(maskfile))
        {
            float wmult; // Width multipler
            float hmult; // Height multipler
            GetMythUI()->GetScreenSettings(wmult, hmult);
            if (wmult != 1.0f || hmult != 1.0f)
            {
                int width = newMaskImage->size().width() * wmult;
                int height = newMaskImage->size().height() * hmult;
                newMaskImage->Resize(QSize(width, height));
            }

            m_imageProperties.SetMaskImage(newMaskImage);
        }
        else
            m_imageProperties.SetMaskImage(NULL);
        newMaskImage->DecrRef();
    }
    else if (element.tagName() == "grayscale" ||
             element.tagName() == "greyscale")
    {
        m_imageProperties.isGreyscale = parseBool(element);
    }
    else
    {
        return MythUIType::ParseElement(filename, element, showWarnings);
    }

    m_NeedLoad = true;

    if (m_Parent && m_Parent->IsDeferredLoading(true))
        m_NeedLoad = false;

    return true;
}
Ejemplo n.º 22
0
/**
 *  \brief Load the image(s), wraps ImageLoader::LoadImage()
 */
bool MythUIImage::Load(bool allowLoadInBackground, bool forceStat)
{
    d->m_UpdateLock.lockForRead();

    m_Initiator = m_EnableInitiator;

    QString bFilename = m_imageProperties.filename;
    bFilename.detach();

    d->m_UpdateLock.unlock();

    QString filename = bFilename;

    if (bFilename.isEmpty())
    {
        Clear();
        SetMinArea(MythRect());
        SetRedraw();

        return false;
    }

    if (getenv("DISABLETHREADEDMYTHUIIMAGE"))
        allowLoadInBackground = false;

    // Don't clear the widget before we need to, otherwise it causes
    // unsightly flashing. We exclude animations for now since that requires a
    // deeper fix
    bool isAnimation = (m_HighNum != m_LowNum) || m_animatedImage;

    if (isAnimation)
        Clear();

    QString imagelabel;

    int j = 0;

    for (int i = m_LowNum; i <= m_HighNum && !m_animatedImage; i++)
    {
        if (!m_animatedImage && m_HighNum != m_LowNum &&
            bFilename.contains("%1"))
            filename = bFilename.arg(i);

        ImageProperties imProps = m_imageProperties;
        imProps.filename = filename;
        imagelabel = ImageLoader::GenImageLabel(imProps);

        // Only load in the background if allowed and the image is
        // not already in our mem cache
        int cacheMode = kCacheIgnoreDisk;

        if (forceStat)
            cacheMode |= (int)kCacheForceStat;

        int cacheMode2 = kCacheNormal;

        if (forceStat)
            cacheMode2 |= (int)kCacheForceStat;

        bool do_background_load = false;
        if (allowLoadInBackground)
        {
            MythImage *img = GetMythUI()->LoadCacheImage(
                filename, imagelabel, GetPainter(),
                static_cast<ImageCacheMode>(cacheMode));
            if (img)
                img->DecrRef();
            else
                do_background_load = true;
        }

        if (do_background_load)
        {
            SetMinArea(MythRect());
            LOG(VB_GUI | VB_FILE, LOG_DEBUG, LOC +
                QString("Load(), spawning thread to load '%1'").arg(filename));

            m_runningThreads++;
            ImageLoadThread *bImgThread;
            bImgThread = new ImageLoadThread(this, GetPainter(),
                                             imProps,
                                             bFilename, i,
                                             static_cast<ImageCacheMode>(cacheMode2));
            GetMythUI()->GetImageThreadPool()->start(bImgThread, "ImageLoad");
        }
        else
        {
            if (!isAnimation && !GetMythUI()->IsImageInCache(imagelabel))
                Clear();

            // Perform a blocking load
            LOG(VB_GUI | VB_FILE, LOG_DEBUG, LOC +
                QString("Load(), loading '%1' in foreground").arg(filename));
            bool aborted = false;

            if (ImageLoader::SupportsAnimation(filename))
            {
                AnimationFrames *myFrames;

                myFrames = ImageLoader::LoadAnimatedImage(GetPainter(), imProps,
                                        static_cast<ImageCacheMode>(cacheMode2),
                                        this, aborted);

                // TODO We might want to handle an abort here more gracefully
                if (aborted)
                    LOG(VB_GUI, LOG_DEBUG, QString("Aborted loading animated"
                                                   "image %1 in foreground")
                                                                .arg(filename));

                SetAnimationFrames(*myFrames);

                delete myFrames;
            }
            else
            {
                MythImage *image = NULL;

                image = ImageLoader::LoadImage(GetPainter(),
                                               imProps,
                                               static_cast<ImageCacheMode>(cacheMode2),
                                               this, aborted);

                // TODO We might want to handle an abort here more gracefully
                if (aborted)
                    LOG(VB_GUI, LOG_DEBUG, QString("Aborted loading animated"
                                                   "image %1 in foreground")
                                                                .arg(filename));

                if (image)
                {
                    if (m_imageProperties.forceSize.isNull())
                        SetSize(image->size());

                    MythRect rect(GetFullArea());
                    rect.setSize(image->size());
                    SetMinArea(rect);

                    m_ImagesLock.lock();
                    m_Images[j] = image;
                    m_ImagesLock.unlock();

                    SetRedraw();
                    d->m_UpdateLock.lockForWrite();
                    m_LastDisplay = QTime::currentTime();
                    d->m_UpdateLock.unlock();
                }
                else
                {
                    Reset();

                    m_ImagesLock.lock();
                    m_Images[j] = NULL;
                    m_ImagesLock.unlock();
                }
            }
        }

        ++j;
    }

    return true;
}
Ejemplo n.º 23
0
/** \brief Handle a MythTV action for the Menus.
 *
 *  \param action single action to be handled
 *  \return true if the action is not to EXEC another program
 */
bool MythThemedMenu::handleAction(const QString &action, const QString &password)
{
    MythUIMenuCallbacks *cbs = GetMythUI()->GetMenuCBs();

    if (((password == "SetupPinCode") &&
         GetMythDB()->GetNumSetting("SetupPinCodeRequired", 0)) ||
         (!password.isEmpty() && password != "SetupPinCode"))
    {
        if (!checkPinCode(password))
            return true;
    }

    if (action.left(5) == "EXEC ")
    {
        QString rest = action.right(action.length() - 5);
        if (cbs && cbs->exec_program)
            cbs->exec_program(rest);

        return false;
    }
    else if (action.left(7) == "EXECTV ")
    {
        QString rest = action.right(action.length() - 7).trimmed();
        if (cbs && cbs->exec_program_tv)
            cbs->exec_program_tv(rest);
    }
    else if (action.left(5) == "MENU ")
    {
        QString menu = action.right(action.length() - 5);

        MythScreenStack *stack = GetScreenStack();

        MythThemedMenu *newmenu = new MythThemedMenu("", menu, stack, menu,
                                                     false, m_state);
        if (newmenu->foundTheme())
            stack->AddScreen(newmenu);
        else
            delete newmenu;
    }
    else if (action.left(6) == "UPMENU")
    {
        m_wantpop = true;
    }
    else if (action.left(12) == "CONFIGPLUGIN")
    {
        QString rest = action.right(action.length() - 13);
        if (cbs && cbs->configplugin)
            cbs->configplugin(rest);
    }
    else if (action.left(6) == "PLUGIN")
    {
        QString rest = action.right(action.length() - 7);
        if (cbs && cbs->plugin)
            cbs->plugin(rest);
    }
    else if (action.left(8) == "SHUTDOWN")
    {
        if (m_allocedstate)
        {
            m_wantpop = true;
        }
    }
    else if (action.left(5) == "EJECT")
    {
        if (cbs && cbs->eject)
            cbs->eject();
    }
    else if (action.left(5) == "JUMP ")
    {
        QString rest = action.right(action.length() - 5);
        GetMythMainWindow()->JumpTo(rest, false);
    }
    else if (action.left(6) == "MEDIA ")
    {
        // the format is MEDIA HANDLER URL
        // TODO: allow spaces in the url
        QStringList list = action.simplified().split(' ');
        if (list.size() >= 3)
            GetMythMainWindow()->HandleMedia(list[1], list[2]);
    }
    else
    {
        m_selection = action;
        if (m_state->m_callback)
            m_state->m_callback(m_state->m_callbackdata, m_selection);
        else
            LOG(VB_GENERAL, LOG_ERR, "Unknown menu action: " + action);
    }

    return true;
}
Ejemplo n.º 24
0
void ThumbGenerator::loadFile(QImage& image, const QFileInfo& fi)
{
    static int sequence = 0;

    if (GalleryUtil::IsMovie(fi.filePath()))
    {
        bool thumbnailCreated = false;
        QDir tmpDir("/tmp/mythgallery");
        if (!tmpDir.exists())
        {
            if (!tmpDir.mkdir(tmpDir.absolutePath()))
            {
                LOG(VB_GENERAL, LOG_ERR,
                    "Unable to create temp dir for movie thumbnail creation: " +
                    tmpDir.absolutePath());
            }
        }

        if (tmpDir.exists())
        {
            QString thumbFile = QString("%1.png")
                .arg(++sequence,8,10,QChar('0'));

            QString cmd = "mythpreviewgen";
            QStringList args;
            args << logPropagateArgs.split(" ", QString::SkipEmptyParts);
            args << "--infile" << '"' + fi.absoluteFilePath() + '"';
            args << "--outfile" << '"' + tmpDir.filePath(thumbFile) + '"';

            MythSystemLegacy ms(cmd, args, kMSRunShell);
            ms.SetDirectory(tmpDir.absolutePath());
            ms.Run();
            if (ms.Wait() == GENERIC_EXIT_OK)
            {
                QFileInfo thumb(tmpDir.filePath(thumbFile));
                if (thumb.exists())
                {
                    QImage img(thumb.absoluteFilePath());
                    image = img;
                    thumbnailCreated = true;
                }
            }
        }

        if (!thumbnailCreated)
        {
            QImage *img = GetMythUI()->LoadScaleImage("gallery-moviethumb.png");
            if (img)
            {
                image = *img;
            }
        }
    }
    else
    {
#ifdef EXIF_SUPPORT
        // Try to get thumbnail from exif data
        ExifData *ed = exif_data_new_from_file(fi.absoluteFilePath()
                                               .toLocal8Bit().constData());
        if (ed && ed->data)
        {
            image.loadFromData(ed->data, ed->size);
        }

        if (ed)
            exif_data_free(ed);

        if (image.width() > m_width && image.height() > m_height)
            return;
#endif

#ifdef DCRAW_SUPPORT
        QString extension = fi.suffix();
        QSet<QString> dcrawFormats = DcrawFormats::getFormats();
        int rotateAngle;

        if (dcrawFormats.contains(extension) &&
            (rotateAngle = DcrawHandler::loadThumbnail(&image,
                                               fi.absoluteFilePath())) != -1 &&
            image.width() > m_width && image.height() > m_height)
        {
            if (rotateAngle != 0)
            {
                QMatrix matrix;
                matrix.rotate(rotateAngle);
                image = image.transformed(matrix);
            }

            return;
        }
#endif

        image.load(fi.absoluteFilePath());
    }
}
Ejemplo n.º 25
0
void ThemeUpdateChecker::checkForUpdate(void)
{
    if (GetMythUI()->GetCurrentLocation(false, true) != "mainmenu")
        return;

    if (RemoteFile::Exists(m_infoPackage))
    {
        QString remoteThemeDir =
            gCoreContext->GenMythURL(gCoreContext->GetSetting("MasterServerIP"),
                                     0,
                                     QString("%1/%2").arg(m_mythVersion).arg(GetMythUI()->GetThemeName()),
                                     "Temp");

        QString infoXML = remoteThemeDir;
        infoXML.append("/themeinfo.xml");

        if (RemoteFile::Exists(infoXML))
        {
            ThemeInfo *remoteTheme = new ThemeInfo(remoteThemeDir);
            if (!remoteTheme)
            {
                LOG(VB_GENERAL, LOG_ERR,
                    QString("ThemeUpdateChecker::checkForUpdate(): "
                            "Unable to create ThemeInfo for %1")
                        .arg(infoXML));
                return;
            }
                
            ThemeInfo *localTheme = new ThemeInfo(GetMythUI()->GetThemeDir());
            if (!localTheme)
            {
                LOG(VB_GENERAL, LOG_ERR,
                    "ThemeUpdateChecker::checkForUpdate(): " 
                    "Unable to create ThemeInfo for current theme");
                return;
            }

            int rmtMaj = remoteTheme->GetMajorVersion();
            int rmtMin = remoteTheme->GetMinorVersion();
            int locMaj = localTheme->GetMajorVersion();
            int locMin = localTheme->GetMinorVersion();

            if ((rmtMaj > locMaj) ||
                ((rmtMaj == locMaj) &&
                 (rmtMin > locMin)))
            {
                m_lastKnownThemeVersion =
                    QString("%1-%2.%3").arg(GetMythUI()->GetThemeName())
                                       .arg(rmtMaj).arg(rmtMin);

                QString status = gCoreContext->GetSetting("ThemeUpdateStatus");
                QString currentLocation = GetMythUI()->GetCurrentLocation(false, true);

                if ((!status.startsWith(m_lastKnownThemeVersion)) &&
                    (currentLocation == "mainmenu"))
                {
                    m_currentVersion = QString("%1.%2").arg(locMaj).arg(locMin);
                    m_newVersion = QString("%1.%2").arg(rmtMaj).arg(rmtMin);

                    gCoreContext->SaveSetting("ThemeUpdateStatus",
                                         m_lastKnownThemeVersion + " notified");

                    QString message = tr("Version %1 of the %2 theme is now "
                                         "available in the Theme Chooser.  The "
                                         "currently installed version is %3.")
                                         .arg(m_newVersion)
                                         .arg(GetMythUI()->GetThemeName())
                                         .arg(m_currentVersion);

                    ShowOkPopup(message);
                }
            }
                
            delete remoteTheme;
            delete localTheme;
        }
    }
}
Ejemplo n.º 26
0
static void runMusicStreamPlayback(void)
{
    GetMythUI()->AddCurrentLocation("streammusic");
    startStreamPlayback();
    GetMythUI()->RemoveCurrentLocation();
}
void MetadataImageDownload::run()
{
    RunProlog();

    // Always handle thumbnails first, they're higher priority.
    ThumbnailData *thumb;
    while ((thumb = moreThumbs()) != NULL)
    {
        QString sFilename = getDownloadFilename(thumb->title, thumb->url);

        bool exists = QFile::exists(sFilename);
        if (!exists && !thumb->url.isEmpty())
        {
            if (!GetMythDownloadManager()->download(thumb->url, sFilename))
            {
                LOG(VB_GENERAL, LOG_ERR,
                    QString("MetadataImageDownload: failed to download thumbnail from: %1")
                    .arg(thumb->url));

                delete thumb;
                continue;
            }
        }

        // inform parent we have thumbnail ready for it
        if (QFile::exists(sFilename) && m_parent)
        {
            LOG(VB_GENERAL, LOG_DEBUG,
                    QString("Threaded Image Thumbnail Download: %1")
                    .arg(sFilename));
            thumb->url = sFilename;
            QCoreApplication::postEvent(m_parent,
                           new ThumbnailDLEvent(thumb));
        }
        else
            delete thumb;
    }

    MetadataLookup *lookup;
    while ((lookup = moreDownloads()) != NULL)
    {
        DownloadMap downloads = lookup->GetDownloads();
        DownloadMap downloaded;

        for (DownloadMap::iterator i = downloads.begin();
                i != downloads.end(); ++i)
        {
            VideoArtworkType type = i.key();
            ArtworkInfo info = i.value();
            QString filename = getDownloadFilename( type, lookup,
                                   info.url );
            if (lookup->GetHost().isEmpty())
            {
                QString path = getLocalWritePath(lookup->GetType(), type);
                QDir dirPath(path);
                if (!dirPath.exists())
                    if (!dirPath.mkpath(path))
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Metadata Image Download: Unable to create "
                                    "path %1, aborting download.").arg(path));
                        QCoreApplication::postEvent(m_parent,
                                    new ImageDLFailureEvent(lookup));
                        continue;
                    }
                QString finalfile = path + "/" + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                if (!QFile::exists(finalfile) || lookup->GetAllowOverwrites())
                {
                    QFile dest_file(finalfile);
                    if (dest_file.exists())
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        dest_file.remove();
                    }

                    LOG(VB_GENERAL, LOG_INFO,
                        QString("Metadata Image Download: %1 ->%2")
                         .arg(oldurl).arg(finalfile));
                    QByteArray *download = new QByteArray();
                    GetMythDownloadManager()->download(oldurl, download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(*download);
                    if (!didLoad)
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Tried to write %1, but it appears to be "
                                    "an HTML redirect (filesize %2).")
                                .arg(oldurl).arg(download->size()));
                        delete download;
                        download = NULL;
                        QCoreApplication::postEvent(m_parent,
                                    new ImageDLFailureEvent(lookup));
                        continue;
                    }

                    if (dest_file.open(QIODevice::WriteOnly))
                    {
                        off_t size = dest_file.write(*download,
                                                     download->size());
                        if (size != download->size())
                        {
                            LOG(VB_GENERAL, LOG_ERR,
                                QString("Image Download: Error Writing Image "
                                        "to file: %1").arg(finalfile));
                            QCoreApplication::postEvent(m_parent,
                                        new ImageDLFailureEvent(lookup));
                        }
                        else
                            downloaded.insert(type, info);
                    }

                    delete download;
                }
                else
                    downloaded.insert(type, info);
            }
            else
            {
                QString path = getStorageGroupURL(type, lookup->GetHost());
                QString finalfile = path + filename;
                QString oldurl = info.url;
                info.url = finalfile;
                bool exists = false;
                bool onMaster = false;
                QString resolvedFN;
                if ((lookup->GetHost().toLower() == gCoreContext->GetHostName().toLower()) ||
                    (gCoreContext->IsThisHost(lookup->GetHost())))
                {
                    StorageGroup sg;
                    resolvedFN = sg.FindFile(filename);
                    exists = QFile::exists(resolvedFN);
                    if (!exists)
                    {
                        resolvedFN = getLocalStorageGroupPath(type,
                                                 lookup->GetHost()) + "/" + filename;
                    }
                    onMaster = true;
                }
                else
                    exists = RemoteFile::Exists(finalfile);

                if (!exists || lookup->GetAllowOverwrites())
                {

                    if (exists && !onMaster)
                    {
                        QFileInfo fi(finalfile);
                        GetMythUI()->RemoveFromCacheByFile(fi.fileName());
                        RemoteFile::DeleteFile(finalfile);
                    }
                    else if (exists)
                        QFile::remove(resolvedFN);

                    LOG(VB_GENERAL, LOG_INFO,
                        QString("Metadata Image Download: %1 -> %2")
                            .arg(oldurl).arg(finalfile));
                    QByteArray *download = new QByteArray();
                    GetMythDownloadManager()->download(oldurl, download);

                    QImage testImage;
                    bool didLoad = testImage.loadFromData(*download);
                    if (!didLoad)
                    {
                        LOG(VB_GENERAL, LOG_ERR,
                            QString("Tried to write %1, but it appears to be "
                                    "an HTML redirect or corrupt file "
                                    "(filesize %2).")
                                .arg(oldurl).arg(download->size()));
                        delete download;
                        download = NULL;
                        QCoreApplication::postEvent(m_parent,
                                    new ImageDLFailureEvent(lookup));
                        continue;
                    }

                    if (!onMaster)
                    {
                        RemoteFile *outFile = new RemoteFile(finalfile, true);
                        if (!outFile->isOpen())
                        {
                            LOG(VB_GENERAL, LOG_ERR,
                                QString("Image Download: Failed to open "
                                        "remote file (%1) for write.  Does "
                                        "Storage Group Exist?")
                                        .arg(finalfile));
                            delete outFile;
                            outFile = NULL;
                            QCoreApplication::postEvent(m_parent,
                                        new ImageDLFailureEvent(lookup));
                        }
                        else
                        {
                            off_t written = outFile->Write(*download,
                                                           download->size());
                            if (written != download->size())
                            {
                                LOG(VB_GENERAL, LOG_ERR,
                                    QString("Image Download: Error Writing Image "
                                            "to file: %1").arg(finalfile));
                                QCoreApplication::postEvent(m_parent,
                                        new ImageDLFailureEvent(lookup));
                            }
                            else
                                downloaded.insert(type, info);
                            delete outFile;
                            outFile = NULL;
                        }
                    }
                    else
                    {
                        QFile dest_file(resolvedFN);
                        if (dest_file.open(QIODevice::WriteOnly))
                        {
                            off_t size = dest_file.write(*download,
                                                         download->size());
                            if (size != download->size())
                            {
                                LOG(VB_GENERAL, LOG_ERR,
                                    QString("Image Download: Error Writing Image "
                                            "to file: %1").arg(finalfile));
                                QCoreApplication::postEvent(m_parent,
                                            new ImageDLFailureEvent(lookup));
                            }
                            else
                                downloaded.insert(type, info);
                        }
                    }

                    delete download;
                }
                else
                    downloaded.insert(type, info);
            }
        }
        lookup->SetDownloads(downloaded);
        QCoreApplication::postEvent(m_parent, new ImageDLEvent(lookup));
    }

    RunEpilog();
}
Ejemplo n.º 28
0
    static MythImage *LoadImage(MythPainter *painter,
                                 // Must be a copy for thread safety
                                ImageProperties imProps,
                                ImageCacheMode cacheMode,
                                 // Included only to check address, could be
                                 // replaced by generating a unique value for
                                 // each MythUIImage object?
                                const MythUIImage *parent,
                                bool &aborted,
                                MythImageReader *imageReader = NULL)
    {
        QString cacheKey = GenImageLabel(imProps);
        if (!PreLoad(cacheKey, parent))
        {
            aborted = true;
            return NULL;
        }

        QString filename = imProps.filename;
        MythImage *image = NULL;

        bool bResize = false;
        bool bFoundInCache = false;

        int w = -1;
        int h = -1;

        if (!imProps.forceSize.isNull())
        {
            if (imProps.forceSize.width() != -1)
                w = imProps.forceSize.width();

            if (imProps.forceSize.height() != -1)
                h = imProps.forceSize.height();

            bResize = true;
        }

        if (!imageReader)
        {
            image = GetMythUI()->LoadCacheImage(filename, cacheKey,
                                                painter, cacheMode);
        }

        if (image)
        {
            if (VERBOSE_LEVEL_CHECK(VB_GUI | VB_FILE, LOG_INFO))
            {
                image->IncrRef();
                int cnt = image->DecrRef();
                LOG(VB_GUI | VB_FILE, LOG_INFO,
                    QString("ImageLoader::LoadImage(%1) Found in cache, "
                            "RefCount = %2")
                    .arg(cacheKey).arg(cnt));
            }

            if (imProps.isReflected)
                image->setIsReflected(true);

            if (imProps.isOriented)
                image->setIsOriented(true);

            bFoundInCache = true;
        }
        else
        {
            LOG(VB_GUI | VB_FILE, LOG_INFO,
                QString("ImageLoader::LoadImage(%1) NOT Found in cache. "
                        "Loading Directly").arg(cacheKey));

            image = painter->GetFormatImage();
            bool ok = false;

            if (imageReader)
                ok = image->Load(imageReader);
            else
                ok = image->Load(filename);

            if (!ok)
            {
                image->DecrRef();
                image = NULL;
            }
        }

        if (image && image->isNull())
        {
            LOG(VB_GUI | VB_FILE, LOG_INFO,
                QString("ImageLoader::LoadImage(%1) Image is NULL")
                                                    .arg(filename));

            image->DecrRef();
            image = NULL;
        }

        if (image && !bFoundInCache)
        {
            if (imProps.isReflected)
                image->Reflect(imProps.reflectAxis, imProps.reflectShear,
                               imProps.reflectScale, imProps.reflectLength,
                               imProps.reflectSpacing);

            if (imProps.isGreyscale)
                image->ToGreyscale();

            if (imProps.isOriented)
                image->Orientation(imProps.orientation);

            // Even if an explicit size wasn't defined this image may still need
            // to be scaled because of a difference between the theme resolution
            // and the screen resolution. We want to avoid scaling twice.
            if (!bResize && imProps.isThemeImage)
            {
                float wmult; // Width multipler
                float hmult; // Height multipler
                GetMythUI()->GetScreenSettings(wmult, hmult);
                if (wmult != 1.0f || hmult != 1.0f)
                {
                    w = image->size().width() * wmult;
                    h = image->size().height() * hmult;
                    bResize = true;
                }
            }

            if (bResize)
                image->Resize(QSize(w, h), imProps.preserveAspect);

            if (imProps.isMasked)
            {
                QRect imageArea = image->rect();
                QRect maskArea = imProps.GetMaskImageRect();

                // Crop the mask to the image
                int x = 0;
                int y = 0;

                if (maskArea.width() > imageArea.width())
                    x = (maskArea.width() - imageArea.width()) / 2;

                if (maskArea.height() > imageArea.height())
                    y = (maskArea.height() - imageArea.height()) / 2;

                if (x > 0 || y > 0)
                    imageArea.translate(x, y);

                QImage mask = imProps.GetMaskImageSubset(imageArea);
                image->setAlphaChannel(mask.alphaChannel());
            }

            if (!imageReader)
                GetMythUI()->CacheImage(cacheKey, image);
        }

        if (image)
            image->SetChanged();

        PostLoad(cacheKey);

        return image;
    }
Ejemplo n.º 29
0
void GameHandler::Launchgame(RomInfo *romdata, QString systemname)
{
    GameHandler *handler;

    if (!systemname.isEmpty() && !systemname.isNull())
    {
        handler = GetHandlerByName(systemname);
    }
    else if (!(handler = GetHandler(romdata)))
    {
        // Couldn't get handler so abort.
        return;
    }
    QString exec = handler->SystemCmdLine();

    if (exec.isEmpty())
        return;

    if (handler->GameType() != "PC")
    {
        QString arg = "\"" + romdata->Rompath() +
                      "/" + romdata->Romname() + "\"";

        // If they specified a %s in the commandline place the romname
        // in that location, otherwise tack it on to the end of
        // the command.
        if (exec.contains("%s") || handler->SpanDisks())
        {
            exec = exec.replace(QRegExp("%s"),arg);

            if (handler->SpanDisks())
            {
                QRegExp rxp = QRegExp( "%d[0-4]", Qt::CaseSensitive, QRegExp::RegExp);

                if (exec.contains(rxp))
                {
                    if (romdata->DiskCount() > 1)
                    {
                        // Chop off the extension, .  and last character of the name which we are assuming is the disk #
                        QString basename = romdata->Romname().left(romdata->Romname().length() - (romdata->getExtension().length() + 2));
                        QString extension = romdata->getExtension();
                        QString rom;
                        QString diskid[] = { "%d0", "%d1", "%d2", "%d3", "%d4", "%d5", "%d6" };

                        for (int disk = 1; disk <= romdata->DiskCount(); disk++)
                        {
                            rom = QString("\"%1/%2%3.%4\"")
                                          .arg(romdata->Rompath())
                                          .arg(basename)
                                          .arg(disk)
                                          .arg(extension);
                            exec = exec.replace(QRegExp(diskid[disk]),rom);
                        }
                    } else
                    {   // If there is only one disk make sure we replace %d1 just like %s
                        exec = exec.replace(QRegExp("%d1"),arg);
                    }
                }
            }
        }
        else
        {
            exec = exec + " \"" +
                   romdata->Rompath() + "/" +
                   romdata->Romname() + "\"";
        }
    }

    QString savedir = QDir::current().path();
    QDir d;
    if (!handler->SystemWorkingPath().isEmpty())
    {
        if (!d.cd(handler->SystemWorkingPath()))
        {
            LOG(VB_GENERAL, LOG_ERR, LOC +
                QString("Failed to change to specified Working Directory: %1")
                    .arg(handler->SystemWorkingPath()));
        }
    }
    LOG(VB_GENERAL, LOG_INFO, LOC + QString("Launching Game : %1 : %2")
           .arg(handler->SystemName())
           .arg(exec));

    GetMythUI()->AddCurrentLocation(QString("MythGame %1 ( %2 )").arg(handler->SystemName()).arg(exec));

    QStringList cmdlist = exec.split(";");
    if (cmdlist.count() > 0)
    {
        for (QStringList::Iterator cmd = cmdlist.begin(); cmd != cmdlist.end();
             ++cmd )
        {
            LOG(VB_GENERAL, LOG_INFO, LOC +
                QString("Executing : %1").arg(*cmd));
            myth_system(*cmd, kMSProcessEvents);
        }
    }
    else
    {
        LOG(VB_GENERAL, LOG_INFO, LOC + QString("Executing : %1").arg(exec));
        myth_system(exec, kMSProcessEvents);
    }

    GetMythUI()->RemoveCurrentLocation();

    (void)d.cd(savedir);
}
Ejemplo n.º 30
0
void MythFontProperties::SetPixelSize(float size)
{
    QSize baseSize = GetMythUI()->GetBaseSize();
    m_relativeSize = size / (float)(baseSize.height());
    m_face.setPixelSize(GetMythMainWindow()->NormY((int)(size + 0.5f)));
}