Information about this format and testfiles can be found at http://en.wikipedia.org/wiki/CDisplay_RAR_Archived_Comic_Book_File svn path=/trunk/playground/graphics/okular/; revision=624702remotes/origin/KDE/4.0
parent
169b752433
commit
deabbae3bf
12 changed files with 547 additions and 0 deletions
@ -0,0 +1,26 @@ |
|||||||
|
include_directories( |
||||||
|
${CMAKE_SOURCE_DIR}/okular |
||||||
|
) |
||||||
|
|
||||||
|
|
||||||
|
########### next target ############### |
||||||
|
|
||||||
|
set( okularGenerator_comicbook_PART_SRCS |
||||||
|
document.cpp |
||||||
|
generator_comicbook.cpp |
||||||
|
unrar.cpp |
||||||
|
) |
||||||
|
|
||||||
|
kde4_automoc(${okularGenerator_comicbook_PART_SRCS}) |
||||||
|
|
||||||
|
kde4_add_plugin(okularGenerator_comicbook WITH_PREFIX ${okularGenerator_comicbook_PART_SRCS}) |
||||||
|
|
||||||
|
target_link_libraries(okularGenerator_comicbook okularcore ${KDE4_KDEUI_LIBS} ) |
||||||
|
|
||||||
|
install(TARGETS okularGenerator_comicbook DESTINATION ${PLUGIN_INSTALL_DIR}) |
||||||
|
|
||||||
|
|
||||||
|
########### install files ############### |
||||||
|
|
||||||
|
install( FILES libokularGenerator_comicbook.desktop okularComicbook.desktop DESTINATION ${SERVICES_INSTALL_DIR} ) |
||||||
|
install( FILES x-cbz.desktop x-cbr.desktop DESTINATION ${MIME_INSTALL_DIR}/application ) |
||||||
@ -0,0 +1,127 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#include <QtGui/QImage> |
||||||
|
|
||||||
|
#include <kzip.h> |
||||||
|
|
||||||
|
#include "document.h" |
||||||
|
#include "unrar.h" |
||||||
|
|
||||||
|
using namespace ComicBook; |
||||||
|
|
||||||
|
Document::Document() |
||||||
|
: mUnrar( 0 ), mZip( 0 ) |
||||||
|
{ |
||||||
|
} |
||||||
|
|
||||||
|
Document::~Document() |
||||||
|
{ |
||||||
|
delete mUnrar; |
||||||
|
delete mZip; |
||||||
|
} |
||||||
|
|
||||||
|
bool Document::open( const QString &fileName ) |
||||||
|
{ |
||||||
|
delete mZip; |
||||||
|
delete mUnrar; |
||||||
|
|
||||||
|
/**
|
||||||
|
* We have a zip archive |
||||||
|
*/ |
||||||
|
if ( fileName.toLower().endsWith( ".cbz" ) ) { |
||||||
|
mZip = new KZip( fileName ); |
||||||
|
|
||||||
|
if ( !mZip->open( QIODevice::ReadOnly ) ) { |
||||||
|
delete mZip; |
||||||
|
mZip = 0; |
||||||
|
|
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
const KArchiveDirectory *directory = mZip->directory(); |
||||||
|
if ( !directory ) { |
||||||
|
delete mZip; |
||||||
|
mZip = 0; |
||||||
|
|
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
mZipDir = const_cast<KArchiveDirectory*>( directory ); |
||||||
|
QStringList entries = directory->entries(); |
||||||
|
if ( entries.count() == 1 ) { |
||||||
|
// seems to be a nested directory
|
||||||
|
const KArchiveEntry *entry = directory->entry( entries[ 0 ] ); |
||||||
|
if ( entry->isDirectory() ) { |
||||||
|
entries = static_cast<const KArchiveDirectory*>( entry )->entries(); |
||||||
|
mZipDir = const_cast<KArchiveDirectory*>( static_cast<const KArchiveDirectory*>( entry ) ); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
extractImageFiles( entries ); |
||||||
|
|
||||||
|
} else { |
||||||
|
/**
|
||||||
|
* We have a rar archive |
||||||
|
*/ |
||||||
|
mUnrar = new Unrar(); |
||||||
|
|
||||||
|
if ( !mUnrar->open( fileName ) ) { |
||||||
|
delete mUnrar; |
||||||
|
mUnrar = 0; |
||||||
|
|
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
extractImageFiles( mUnrar->list() ); |
||||||
|
} |
||||||
|
|
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
void Document::extractImageFiles( const QStringList &list ) |
||||||
|
{ |
||||||
|
QStringList files( list ); |
||||||
|
|
||||||
|
qSort( files ); |
||||||
|
|
||||||
|
for ( int i = 0; i < files.count(); ++i ) { |
||||||
|
const QString lowerFile = files[ i ].toLower(); |
||||||
|
|
||||||
|
if ( lowerFile.endsWith( ".gif" ) || |
||||||
|
lowerFile.endsWith( ".jpg" ) || |
||||||
|
lowerFile.endsWith( ".jpeg" ) || |
||||||
|
lowerFile.endsWith( ".png" ) ) |
||||||
|
mPageMap.append( files[ i ] ); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
int Document::pages() const |
||||||
|
{ |
||||||
|
return mPageMap.count(); |
||||||
|
} |
||||||
|
|
||||||
|
QStringList Document::pageTitles() const |
||||||
|
{ |
||||||
|
return QStringList(); |
||||||
|
} |
||||||
|
|
||||||
|
QImage Document::pageImage( int page ) const |
||||||
|
{ |
||||||
|
if ( mZip ) { |
||||||
|
const KArchiveFile *entry = static_cast<const KArchiveFile*>( mZipDir->entry( mPageMap[ page ] ) ); |
||||||
|
if ( entry ) |
||||||
|
return QImage::fromData( entry->data() ); |
||||||
|
|
||||||
|
} else { |
||||||
|
return QImage::fromData( mUnrar->contentOf( mPageMap[ page ] ) ); |
||||||
|
} |
||||||
|
|
||||||
|
return QImage(); |
||||||
|
} |
||||||
@ -0,0 +1,46 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#ifndef COMICBOOK_DOCUMENT_H |
||||||
|
#define COMICBOOK_DOCUMENT_H |
||||||
|
|
||||||
|
#include <QtCore/QStringList> |
||||||
|
|
||||||
|
class KArchiveDirectory; |
||||||
|
class KZip; |
||||||
|
class QImage; |
||||||
|
class Unrar; |
||||||
|
|
||||||
|
namespace ComicBook { |
||||||
|
|
||||||
|
class Document |
||||||
|
{ |
||||||
|
public: |
||||||
|
Document(); |
||||||
|
~Document(); |
||||||
|
|
||||||
|
bool open( const QString &fileName ); |
||||||
|
|
||||||
|
int pages() const; |
||||||
|
QStringList pageTitles() const; |
||||||
|
|
||||||
|
QImage pageImage( int page ) const; |
||||||
|
|
||||||
|
private: |
||||||
|
void extractImageFiles( const QStringList& ); |
||||||
|
|
||||||
|
QStringList mPageMap; |
||||||
|
Unrar *mUnrar; |
||||||
|
KZip *mZip; |
||||||
|
KArchiveDirectory *mZipDir; |
||||||
|
}; |
||||||
|
|
||||||
|
} |
||||||
|
|
||||||
|
#endif |
||||||
@ -0,0 +1,89 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#include <qpainter.h> |
||||||
|
#include <kprinter.h> |
||||||
|
|
||||||
|
#include <okular/core/page.h> |
||||||
|
|
||||||
|
#include "generator_comicbook.h" |
||||||
|
|
||||||
|
OKULAR_EXPORT_PLUGIN(ComicBookGenerator) |
||||||
|
|
||||||
|
ComicBookGenerator::ComicBookGenerator() |
||||||
|
: Generator() |
||||||
|
{ |
||||||
|
} |
||||||
|
|
||||||
|
ComicBookGenerator::~ComicBookGenerator() |
||||||
|
{ |
||||||
|
} |
||||||
|
|
||||||
|
bool ComicBookGenerator::loadDocument( const QString & fileName, QVector<Okular::Page*> & pagesVector ) |
||||||
|
{ |
||||||
|
if ( !mDocument.open( fileName ) ) |
||||||
|
return false; |
||||||
|
|
||||||
|
int pages = mDocument.pages(); |
||||||
|
pagesVector.resize( pages ); |
||||||
|
|
||||||
|
for ( int i = 0; i < pages; ++i ) { |
||||||
|
Okular::Page * page = new Okular::Page( i, 800, 600, Okular::Rotation0 ); |
||||||
|
pagesVector[i] = page; |
||||||
|
} |
||||||
|
|
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
bool ComicBookGenerator::closeDocument() |
||||||
|
{ |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
bool ComicBookGenerator::canGeneratePixmap( bool ) const |
||||||
|
{ |
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
void ComicBookGenerator::generatePixmap( Okular::PixmapRequest * request ) |
||||||
|
{ |
||||||
|
int width = request->width(); |
||||||
|
int height = request->height(); |
||||||
|
|
||||||
|
QImage image = mDocument.pageImage( request->pageNumber() ); |
||||||
|
image = image.scaled( width, height, Qt::IgnoreAspectRatio, Qt::SmoothTransformation ); |
||||||
|
request->page()->setPixmap( request->id(), new QPixmap( QPixmap::fromImage( image ) ) ); |
||||||
|
|
||||||
|
// signal that the request has been accomplished
|
||||||
|
signalRequestDone(request); |
||||||
|
} |
||||||
|
|
||||||
|
bool ComicBookGenerator::print( KPrinter& printer ) |
||||||
|
{ |
||||||
|
QPainter p( &printer ); |
||||||
|
|
||||||
|
for ( int i = 0; i < mDocument.pages(); ++i ) { |
||||||
|
const QImage image = mDocument.pageImage( i ); |
||||||
|
|
||||||
|
if ( i != 0 ) |
||||||
|
printer.newPage(); |
||||||
|
|
||||||
|
p.drawImage( 0, 0, image ); |
||||||
|
} |
||||||
|
|
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
bool ComicBookGenerator::hasFeature( GeneratorFeature ) const |
||||||
|
{ |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
#include "generator_comicbook.moc" |
||||||
|
|
||||||
@ -0,0 +1,42 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#ifndef GENERATOR_COMICBOOK_H |
||||||
|
#define GENERATOR_COMICBOOK_H |
||||||
|
|
||||||
|
#include <okular/core/generator.h> |
||||||
|
|
||||||
|
#include "document.h" |
||||||
|
|
||||||
|
class ComicBookGenerator : public Okular::Generator |
||||||
|
{ |
||||||
|
Q_OBJECT |
||||||
|
|
||||||
|
public: |
||||||
|
ComicBookGenerator(); |
||||||
|
virtual ~ComicBookGenerator(); |
||||||
|
|
||||||
|
// [INHERITED] load a document and fill up the pagesVector
|
||||||
|
bool loadDocument( const QString & fileName, QVector<Okular::Page*> & pagesVector ); |
||||||
|
bool closeDocument(); |
||||||
|
|
||||||
|
// [INHERITED] perform actions on document / pages
|
||||||
|
bool canGeneratePixmap( bool async ) const; |
||||||
|
void generatePixmap( Okular::PixmapRequest * request ); |
||||||
|
|
||||||
|
// [INHERITED] print document using already configured kprinter
|
||||||
|
bool print( KPrinter& printer ); |
||||||
|
|
||||||
|
bool hasFeature( GeneratorFeature feature ) const; |
||||||
|
|
||||||
|
private: |
||||||
|
ComicBook::Document mDocument; |
||||||
|
}; |
||||||
|
|
||||||
|
#endif |
||||||
@ -0,0 +1,11 @@ |
|||||||
|
[Desktop Entry] |
||||||
|
Encoding=UTF-8 |
||||||
|
Type=Service |
||||||
|
Name=Comic Book |
||||||
|
Comment=Comic book backend for okular |
||||||
|
ServiceTypes=okular/Generator |
||||||
|
MimeType=application/x-cbz;application/x-cbr; |
||||||
|
X-KDE-Library=libokularGenerator_comicbook |
||||||
|
X-KDE-Priority=1 |
||||||
|
X-KDE-okularAPIVersion=1 |
||||||
|
X-KDE-okularHasInternalSettings=false |
||||||
@ -0,0 +1,8 @@ |
|||||||
|
[Desktop Entry] |
||||||
|
Encoding=UTF-8 |
||||||
|
Icon=okular |
||||||
|
Name=okular |
||||||
|
ServiceTypes=KParts/ReadOnlyPart |
||||||
|
X-KDE-Library=libokularpart |
||||||
|
Type=Service |
||||||
|
MimeType=application/x-cbz;application/x-cbr; |
||||||
@ -0,0 +1,113 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#include <QtCore/QFile> |
||||||
|
#include <QtCore/QProcess> |
||||||
|
|
||||||
|
#include <ktempdir.h> |
||||||
|
|
||||||
|
#include "unrar.h" |
||||||
|
|
||||||
|
Unrar::Unrar() |
||||||
|
: QObject( 0 ), mTempDir( 0 ), mErrorOccured( false ) |
||||||
|
{ |
||||||
|
} |
||||||
|
|
||||||
|
Unrar::~Unrar() |
||||||
|
{ |
||||||
|
delete mTempDir; |
||||||
|
} |
||||||
|
|
||||||
|
bool Unrar::open( const QString &fileName ) |
||||||
|
{ |
||||||
|
delete mTempDir; |
||||||
|
mTempDir = new KTempDir(); |
||||||
|
|
||||||
|
mFileName = fileName; |
||||||
|
|
||||||
|
/**
|
||||||
|
* Extract the archive to a temporary directory |
||||||
|
*/ |
||||||
|
mStdOutData.clear(); |
||||||
|
mStdErrData.clear(); |
||||||
|
|
||||||
|
mProcess = new QProcess( this ); |
||||||
|
|
||||||
|
connect( mProcess, SIGNAL( readyReadStandardOutput() ), SLOT( readFromStdout() ) ); |
||||||
|
connect( mProcess, SIGNAL( readyReadStandardError() ), SLOT( readFromStderr() ) ); |
||||||
|
connect( mProcess, SIGNAL( finished( int, QProcess::ExitStatus ) ), SLOT( processExited() ) ); |
||||||
|
connect( mProcess, SIGNAL( error( QProcess::ProcessError ) ), SLOT( processExited() ) ); |
||||||
|
|
||||||
|
mProcess->start( "unrar", QStringList() << "e" << mFileName << mTempDir->name(), QIODevice::ReadOnly ); |
||||||
|
|
||||||
|
mEventLoop.exec(); |
||||||
|
|
||||||
|
delete mProcess; |
||||||
|
mProcess = 0; |
||||||
|
|
||||||
|
if ( mErrorOccured ) { |
||||||
|
mErrorOccured = false; |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
QStringList Unrar::list() |
||||||
|
{ |
||||||
|
mStdOutData.clear(); |
||||||
|
mStdErrData.clear(); |
||||||
|
|
||||||
|
mProcess = new QProcess( this ); |
||||||
|
|
||||||
|
connect( mProcess, SIGNAL( readyReadStandardOutput() ), SLOT( readFromStdout() ) ); |
||||||
|
connect( mProcess, SIGNAL( readyReadStandardError() ), SLOT( readFromStderr() ) ); |
||||||
|
connect( mProcess, SIGNAL( finished( int, QProcess::ExitStatus ) ), SLOT( processExited() ) ); |
||||||
|
connect( mProcess, SIGNAL( error( QProcess::ProcessError ) ), SLOT( processError() ) ); |
||||||
|
|
||||||
|
mProcess->start( "unrar", QStringList() << "lb" << mFileName, QIODevice::ReadOnly ); |
||||||
|
|
||||||
|
mEventLoop.exec(); |
||||||
|
|
||||||
|
delete mProcess; |
||||||
|
mProcess = 0; |
||||||
|
|
||||||
|
return QString::fromLocal8Bit( mStdOutData ).split( "\n", QString::SkipEmptyParts ); |
||||||
|
} |
||||||
|
|
||||||
|
QByteArray Unrar::contentOf( const QString &fileName ) const |
||||||
|
{ |
||||||
|
QFile file( mTempDir->name() + fileName ); |
||||||
|
if ( !file.open( QIODevice::ReadOnly ) ) |
||||||
|
return QByteArray(); |
||||||
|
|
||||||
|
return file.readAll(); |
||||||
|
} |
||||||
|
|
||||||
|
void Unrar::readFromStdout() |
||||||
|
{ |
||||||
|
mStdOutData += mProcess->readAllStandardOutput(); |
||||||
|
} |
||||||
|
|
||||||
|
void Unrar::readFromStderr() |
||||||
|
{ |
||||||
|
mStdErrData += mProcess->readAllStandardError(); |
||||||
|
} |
||||||
|
|
||||||
|
void Unrar::processExited() |
||||||
|
{ |
||||||
|
mEventLoop.exit(); |
||||||
|
} |
||||||
|
|
||||||
|
void Unrar::processError() |
||||||
|
{ |
||||||
|
mErrorOccured = true; |
||||||
|
} |
||||||
|
|
||||||
|
#include "unrar.moc" |
||||||
@ -0,0 +1,67 @@ |
|||||||
|
/***************************************************************************
|
||||||
|
* Copyright (C) 2007 by Tobias Koenig <tokoe@kde.org> * |
||||||
|
* * |
||||||
|
* This program is free software; you can redistribute it and/or modify * |
||||||
|
* it under the terms of the GNU General Public License as published by * |
||||||
|
* the Free Software Foundation; either version 2 of the License, or * |
||||||
|
* (at your option) any later version. * |
||||||
|
***************************************************************************/ |
||||||
|
|
||||||
|
#ifndef UNRAR_H |
||||||
|
#define UNRAR_H |
||||||
|
|
||||||
|
#include <QtCore/QEventLoop> |
||||||
|
#include <QtCore/QObject> |
||||||
|
#include <QtCore/QStringList> |
||||||
|
|
||||||
|
class QProcess; |
||||||
|
class KTempDir; |
||||||
|
|
||||||
|
class Unrar : public QObject |
||||||
|
{ |
||||||
|
Q_OBJECT |
||||||
|
|
||||||
|
public: |
||||||
|
/**
|
||||||
|
* Creates a new unrar object. |
||||||
|
*/ |
||||||
|
Unrar(); |
||||||
|
|
||||||
|
/**
|
||||||
|
* Destroys the unrar object. |
||||||
|
*/ |
||||||
|
~Unrar(); |
||||||
|
|
||||||
|
/**
|
||||||
|
* Opens given rar archive. |
||||||
|
*/ |
||||||
|
bool open( const QString &fileName ); |
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the list of files from the archive. |
||||||
|
*/ |
||||||
|
QStringList list(); |
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the content of the file with the given name. |
||||||
|
*/ |
||||||
|
QByteArray contentOf( const QString &fileName ) const; |
||||||
|
|
||||||
|
private Q_SLOTS: |
||||||
|
void processExited(); |
||||||
|
void processError(); |
||||||
|
void readFromStdout(); |
||||||
|
void readFromStderr(); |
||||||
|
|
||||||
|
private: |
||||||
|
QProcess *mProcess; |
||||||
|
QEventLoop mEventLoop; |
||||||
|
QString mFileName; |
||||||
|
QByteArray mStdOutData; |
||||||
|
QByteArray mStdErrData; |
||||||
|
KTempDir *mTempDir; |
||||||
|
bool mErrorOccured; |
||||||
|
}; |
||||||
|
|
||||||
|
#endif |
||||||
|
|
||||||
@ -0,0 +1,8 @@ |
|||||||
|
[Desktop Entry] |
||||||
|
Type=MimeType |
||||||
|
Encoding=UTF-8 |
||||||
|
MimeType=application/x-cbr |
||||||
|
Icon=package_toys |
||||||
|
Patterns=*.cbr;*.CBR; |
||||||
|
Comment=Comic Book |
||||||
|
Comment[x-test]=xxComic Bookxx |
||||||
@ -0,0 +1,8 @@ |
|||||||
|
[Desktop Entry] |
||||||
|
Type=MimeType |
||||||
|
Encoding=UTF-8 |
||||||
|
MimeType=application/x-cbz |
||||||
|
Icon=package_toys |
||||||
|
Patterns=*.cbz;*.CBZ; |
||||||
|
Comment=Comic Book |
||||||
|
Comment[x-test]=xxComic Bookxx |
||||||
Loading…
Reference in new issue