Example #1
0
Doc Doc::CreateFromFile(const WCHAR *filePath)
{
    Doc doc;
    if (EpubDoc::IsSupportedFile(filePath))
        doc = Doc(EpubDoc::CreateFromFile(filePath));
    else if (Fb2Doc::IsSupportedFile(filePath))
        doc = Doc(Fb2Doc::CreateFromFile(filePath));
    else if (MobiDoc::IsSupportedFile(filePath)) {
        doc = Doc(MobiDoc::CreateFromFile(filePath));
        // MobiDoc is also used for loading PalmDoc - don't expose that to Doc users, though
        if (doc.mobiDoc && doc.mobiDoc->GetDocType() != Pdb_Mobipocket) {
            doc.Delete();
            // .prc files can be both MobiDoc or PalmDoc
            if (PalmDoc::IsSupportedFile(filePath))
                doc = Doc(PalmDoc::CreateFromFile(filePath));
        }
    }
    else if (PalmDoc::IsSupportedFile(filePath))
        doc = Doc(PalmDoc::CreateFromFile(filePath));

    // if failed to load and more specific error message hasn't been
    // set above, set a generic error message
    if (doc.IsNone()) {
        CrashIf(doc.error);
        doc.error = Error_Unknown;
        doc.filePath.Set(str::Dup(filePath));
    }
    else {
        CrashIf(!Doc::IsSupportedFile(filePath));
    }
    CrashIf(!doc.generic && !doc.IsNone());
    return doc;
}
Doc Doc::CreateFromFile(const WCHAR *filePath)
{
    Doc doc;
    if (EpubDoc::IsSupportedFile(filePath))
        doc = Doc(EpubDoc::CreateFromFile(filePath));
    else if (Fb2Doc::IsSupportedFile(filePath))
        doc = Doc(Fb2Doc::CreateFromFile(filePath));
    else if (MobiDoc::IsSupportedFile(filePath))
        doc = Doc(MobiDoc::CreateFromFile(filePath));

    // if failed to load and more specific error message hasn't been
    // set above, set a generic error message
    if (doc.IsNone()) {
        CrashIf(doc.error);
        doc.error = Error_Unknown;
        doc.filePath.Set(str::Dup(filePath));
    }
    CrashIf(!doc.generic && !doc.IsNone());
    return doc;
}
EbookFormattingThread::EbookFormattingThread(Doc doc, HtmlFormatterArgs *args, EbookController *ctrl) :
    doc(doc), formatterArgs(args), controller(ctrl), pageCount(0)
{
    AssertCrash(doc.IsEbook() || (doc.IsNone() && (NULL != args->htmlStr)));
}
Example #4
0
EbookFormattingThread::EbookFormattingThread(Doc doc, HtmlFormatterArgs *args, EbookController *ctrl, int reparseIdx, ControllerCallback *cb) :
    doc(doc), formatterArgs(args), cb(cb), controller(ctrl), pageCount(0), reparseIdx(reparseIdx), pagesAfterReparseIdx(0)
{
    CrashIf(reparseIdx < 0);
    AssertCrash(doc.IsDocLoaded() || (doc.IsNone() && (nullptr != args->htmlStr)));
}
Example #5
0
void OpenMobiInWindow(Doc doc, SumatraWindow& winToReplace)
{
    const WCHAR *fullPath = doc.GetFilePath();
    DisplayState *ds = gFileHistory.Find(fullPath);

    if (doc.IsNone()) {
        // TODO: a hack. In LoadDocumentOld(), if current window IsAboutWindow(),
        // we set loadedFilePath to prevent a crash if multiple ebook files are
        // dropped on about window. We need to undo that in case of failure
        // or else the window will be stuck in an invalid state (not about window
        // but not a document window either)
        WindowInfo *w = winToReplace.AsWindowInfo();
        if (str::Eq(w->loadedFilePath, doc.GetFilePath())) {
            free(w->loadedFilePath);
            w->loadedFilePath = NULL;
            // this is now about window. We don't want to show it if we're already
            // showing other windows (the scenario: dragging ebook file on a window
            // showing a document, we create invisible window for this document and
            // we don't want to show empty window if loading fails
            if (gEbookWindows.Count() > 0 || gWindows.Count() > 1) {
                CloseWindow(w, false);
                if (gFileHistory.MarkFileInexistent(fullPath))
                    prefs::Save();
                // TODO: notify the use that loading failed (e.g. show a notification)
                return;
            }
        }
        // TODO: notify the user that loading failed (e.g. show a notification)

        // TODO: this is not a great solution. In case of opening
        // file from cmd-line, we create a window but don't show it
        // if loading afils, we have to show the window. If window
        // is already visible, this is a no-op
        ShowWindow(winToReplace.HwndFrame(), SW_SHOW);
        if (gFileHistory.MarkFileInexistent(fullPath))
            prefs::Save();
        return;
    }

    if (gGlobalPrefs->rememberOpenedFiles) {
        ds = gFileHistory.MarkFileLoaded(fullPath);
        if (gGlobalPrefs->showStartPage) {
            // TODO: do it on a background thread?
            CreateThumbnailForDoc(doc, *ds);
        }
        prefs::Save();
    }

    int startReparseIdx = -1;
    if (ds && gGlobalPrefs->rememberStatePerDocument && !ds->useDefaultState)
        startReparseIdx = ds->reparseIdx;

    // Add the file also to Windows' recently used documents (this doesn't
    // happen automatically on drag&drop, reopening from history, etc.)
    if (HasPermission(Perm_DiskAccess) && !gPluginMode)
        SHAddToRecentDocs(SHARD_PATH, fullPath);

    ScopedMem<WCHAR> winTitle(str::Format(L"%s - %s", path::GetBaseName(fullPath), SUMATRA_WINDOW_TITLE));

    if (winToReplace.AsEbookWindow()) {
        EbookWindow *mw = winToReplace.AsEbookWindow();
        CrashIf(!mw);
        mw->ebookController->SetDoc(doc);
        win::SetText(mw->hwndFrame, winTitle);
        // TODO: if we have window position/last position for this file, restore it
        return;
    }

    RectI windowPos = gGlobalPrefs->windowPos;
    if (!windowPos.IsEmpty())
        EnsureAreaVisibility(windowPos);
    else
        windowPos = GetDefaultWindowPos();

    if (ds && !ds->windowPos.IsEmpty()) {
        // Make sure it doesn't have a position like outside of the screen etc.
        windowPos = ShiftRectToWorkArea(ds->windowPos);
    }

    WindowInfo *winInfo = winToReplace.AsWindowInfo();
    bool wasMaximized = false;
    if (winInfo && winInfo->hwndFrame) {
        wasMaximized = IsZoomed(winInfo->hwndFrame);
        // hide the window instead of destroying it so that
        // windows doesn't set a window from a different
        // process as foreground window instead of the once
        // created below
        ShowWindow(winInfo->hwndFrame, SW_HIDE);
    }

    HWND hwnd = CreateWindow(
            MOBI_FRAME_CLASS_NAME, SUMATRA_WINDOW_TITLE,
            WS_OVERLAPPEDWINDOW,
            windowPos.x, windowPos.y, windowPos.dx, windowPos.dy,
            NULL, NULL,
            ghinst, NULL);
    if (!hwnd) {
        CloseDocumentAndDeleteWindowInfo(winInfo);
        return;
    }
    if (HasPermission(Perm_DiskAccess) && !gPluginMode)
        DragAcceptFiles(hwnd, TRUE);
    if (Touch::SupportsGestures()) {
        GESTURECONFIG gc = { 0, GC_ALLGESTURES, 0 };
        Touch::SetGestureConfig(hwnd, 0, 1, &gc, sizeof(GESTURECONFIG));
    }

    EbookWindow *win = new EbookWindow();
    win->ebookControls = CreateEbookControls(hwnd);
    win->hwndWrapper = win->ebookControls->mainWnd;
    win->ebookController = new EbookController(win->ebookControls);
    win->hwndFrame = hwnd;

    gEbookWindows.Append(win);
    win::SetText(win->hwndFrame, winTitle);
    SetMenu(hwnd, BuildMenu(win));

    ShowWindow(hwnd, wasMaximized ? SW_SHOWMAXIMIZED : SW_SHOW);
    win->ebookController->SetDoc(doc, startReparseIdx);

    CloseDocumentAndDeleteWindowInfo(winInfo);
}