1
0
Fork 0
mirror of https://github.com/geometer/FBReaderJ.git synced 2025-10-05 02:39:23 +02:00

<video> ePub3 support (in progress)

This commit is contained in:
Nikolay Pultsin 2014-03-08 17:50:20 +00:00
parent cf2683079d
commit e14011b7bb
18 changed files with 363 additions and 33 deletions

View file

@ -83,6 +83,7 @@ LOCAL_SRC_FILES := \
NativeFormats/zlibrary/text/src/model/ZLCachedMemoryAllocator.cpp \ NativeFormats/zlibrary/text/src/model/ZLCachedMemoryAllocator.cpp \
NativeFormats/zlibrary/text/src/model/ZLTextModel.cpp \ NativeFormats/zlibrary/text/src/model/ZLTextModel.cpp \
NativeFormats/zlibrary/text/src/model/ZLTextParagraph.cpp \ NativeFormats/zlibrary/text/src/model/ZLTextParagraph.cpp \
NativeFormats/zlibrary/text/src/model/ZLVideoEntry.cpp \
NativeFormats/zlibrary/ui/src/android/filesystem/JavaFSDir.cpp \ NativeFormats/zlibrary/ui/src/android/filesystem/JavaFSDir.cpp \
NativeFormats/zlibrary/ui/src/android/filesystem/JavaInputStream.cpp \ NativeFormats/zlibrary/ui/src/android/filesystem/JavaInputStream.cpp \
NativeFormats/zlibrary/ui/src/android/filesystem/ZLAndroidFSManager.cpp \ NativeFormats/zlibrary/ui/src/android/filesystem/ZLAndroidFSManager.cpp \

View file

@ -25,6 +25,7 @@
#include <ZLLogger.h> #include <ZLLogger.h>
#include <ZLCachedMemoryAllocator.h> #include <ZLCachedMemoryAllocator.h>
#include <ZLTextStyleEntry.h> #include <ZLTextStyleEntry.h>
#include <ZLVideoEntry.h>
#include "BookReader.h" #include "BookReader.h"
#include "BookModel.h" #include "BookModel.h"
@ -230,6 +231,16 @@ void BookReader::addImage(const std::string &id, shared_ptr<const ZLImage> image
env->DeleteLocalRef(javaImage); env->DeleteLocalRef(javaImage);
} }
void BookReader::addVideoEntry(const ZLVideoEntry &entry) {
if (myCurrentTextModel != 0) {
mySectionContainsRegularContents = true;
endParagraph();
beginParagraph();
myCurrentTextModel->addVideoEntry(entry);
endParagraph();
}
}
void BookReader::insertEndParagraph(ZLTextParagraph::Kind kind) { void BookReader::insertEndParagraph(ZLTextParagraph::Kind kind) {
if (myCurrentTextModel != 0 && mySectionContainsRegularContents) { if (myCurrentTextModel != 0 && mySectionContainsRegularContents) {
std::size_t size = myCurrentTextModel->paragraphsNumber(); std::size_t size = myCurrentTextModel->paragraphsNumber();

View file

@ -36,6 +36,7 @@ class ZLTextModel;
class ZLInputStream; class ZLInputStream;
class ZLCachedMemoryAllocator; class ZLCachedMemoryAllocator;
class ZLTextStyleEntry; class ZLTextStyleEntry;
class ZLVideoEntry;
class BookReader { class BookReader {
@ -68,6 +69,8 @@ public:
void addImageReference(const std::string &id, short vOffset, bool isCover); void addImageReference(const std::string &id, short vOffset, bool isCover);
void addImage(const std::string &id, shared_ptr<const ZLImage> image); void addImage(const std::string &id, shared_ptr<const ZLImage> image);
void addVideoEntry(const ZLVideoEntry &entry);
void beginContentsParagraph(int referenceNumber = -1); void beginContentsParagraph(int referenceNumber = -1);
void endContentsParagraph(); void endContentsParagraph();
bool contentsParagraphIsOpen() const; bool contentsParagraphIsOpen() const;

View file

@ -60,42 +60,82 @@ void XHTMLTagAction::endParagraph(XHTMLReader &reader) {
reader.endParagraph(); reader.endParagraph();
} }
class XHTMLTagStyleAction : public XHTMLTagAction { class XHTMLGlobalTagAction : public XHTMLTagAction {
private:
bool isEnabled(XHTMLReadingState state);
};
class XHTMLTextModeTagAction : public XHTMLTagAction {
private:
bool isEnabled(XHTMLReadingState state);
};
bool XHTMLGlobalTagAction::isEnabled(XHTMLReadingState state) {
return true;
}
bool XHTMLTextModeTagAction::isEnabled(XHTMLReadingState state) {
return state == XHTML_READ_BODY;
}
class XHTMLTagStyleAction : public XHTMLGlobalTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagLinkAction : public XHTMLTagAction { class XHTMLTagLinkAction : public XHTMLGlobalTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagParagraphAction : public XHTMLTagAction { class XHTMLTagParagraphAction : public XHTMLTextModeTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagBodyAction : public XHTMLTagAction { class XHTMLTagBodyAction : public XHTMLGlobalTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagRestartParagraphAction : public XHTMLTagAction { class XHTMLTagRestartParagraphAction : public XHTMLTextModeTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagImageAction : public XHTMLTagAction { class XHTMLTagVideoAction : public XHTMLTagAction {
private:
bool isEnabled(XHTMLReadingState state);
public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader);
};
class XHTMLTagSourceAction : public XHTMLTagAction {
private:
bool isEnabled(XHTMLReadingState state);
public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader);
};
class XHTMLTagImageAction : public XHTMLTextModeTagAction {
public: public:
XHTMLTagImageAction(shared_ptr<ZLXMLReader::NamePredicate> predicate); XHTMLTagImageAction(shared_ptr<ZLXMLReader::NamePredicate> predicate);
@ -120,7 +160,7 @@ private:
friend class XHTMLTagSvgAction; friend class XHTMLTagSvgAction;
}; };
class XHTMLTagSvgAction : public XHTMLTagAction { class XHTMLTagSvgAction : public XHTMLTextModeTagAction {
public: public:
XHTMLTagSvgAction(XHTMLSvgImageNamePredicate &predicate); XHTMLTagSvgAction(XHTMLSvgImageNamePredicate &predicate);
@ -131,14 +171,14 @@ private:
XHTMLSvgImageNamePredicate &myPredicate; XHTMLSvgImageNamePredicate &myPredicate;
}; };
class XHTMLTagItemAction : public XHTMLTagAction { class XHTMLTagItemAction : public XHTMLTextModeTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
void doAtEnd(XHTMLReader &reader); void doAtEnd(XHTMLReader &reader);
}; };
class XHTMLTagHyperlinkAction : public XHTMLTagAction { class XHTMLTagHyperlinkAction : public XHTMLTextModeTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
@ -148,7 +188,7 @@ private:
std::stack<FBTextKind> myHyperlinkStack; std::stack<FBTextKind> myHyperlinkStack;
}; };
class XHTMLTagControlAction : public XHTMLTagAction { class XHTMLTagControlAction : public XHTMLTextModeTagAction {
public: public:
XHTMLTagControlAction(FBTextKind control); XHTMLTagControlAction(FBTextKind control);
@ -160,7 +200,7 @@ private:
FBTextKind myControl; FBTextKind myControl;
}; };
class XHTMLTagParagraphWithControlAction : public XHTMLTagAction { class XHTMLTagParagraphWithControlAction : public XHTMLTextModeTagAction {
public: public:
XHTMLTagParagraphWithControlAction(FBTextKind control); XHTMLTagParagraphWithControlAction(FBTextKind control);
@ -172,7 +212,7 @@ private:
FBTextKind myControl; FBTextKind myControl;
}; };
class XHTMLTagPreAction : public XHTMLTagAction { class XHTMLTagPreAction : public XHTMLTextModeTagAction {
public: public:
void doAtStart(XHTMLReader &reader, const char **xmlattributes); void doAtStart(XHTMLReader &reader, const char **xmlattributes);
@ -187,16 +227,16 @@ void XHTMLTagStyleAction::doAtStart(XHTMLReader &reader, const char **xmlattribu
return; return;
} }
if (reader.myReadState == XHTMLReader::READ_NOTHING) { if (reader.myReadState == XHTML_READ_NOTHING) {
reader.myReadState = XHTMLReader::READ_STYLE; reader.myReadState = XHTML_READ_STYLE;
reader.myTableParser = new StyleSheetTableParser(reader.myStyleSheetTable); reader.myTableParser = new StyleSheetTableParser(reader.myStyleSheetTable);
ZLLogger::Instance().println("CSS", "parsing style tag content"); ZLLogger::Instance().println("CSS", "parsing style tag content");
} }
} }
void XHTMLTagStyleAction::doAtEnd(XHTMLReader &reader) { void XHTMLTagStyleAction::doAtEnd(XHTMLReader &reader) {
if (reader.myReadState == XHTMLReader::READ_STYLE) { if (reader.myReadState == XHTML_READ_STYLE) {
reader.myReadState = XHTMLReader::READ_NOTHING; reader.myReadState = XHTML_READ_NOTHING;
reader.myTableParser.reset(); reader.myTableParser.reset();
} }
} }
@ -248,7 +288,7 @@ void XHTMLTagParagraphAction::doAtEnd(XHTMLReader &reader) {
void XHTMLTagBodyAction::doAtStart(XHTMLReader &reader, const char**) { void XHTMLTagBodyAction::doAtStart(XHTMLReader &reader, const char**) {
++reader.myBodyCounter; ++reader.myBodyCounter;
if (reader.myBodyCounter > 0) { if (reader.myBodyCounter > 0) {
reader.myReadState = XHTMLReader::READ_BODY; reader.myReadState = XHTML_READ_BODY;
} }
} }
@ -256,7 +296,7 @@ void XHTMLTagBodyAction::doAtEnd(XHTMLReader &reader) {
endParagraph(reader); endParagraph(reader);
--reader.myBodyCounter; --reader.myBodyCounter;
if (reader.myBodyCounter <= 0) { if (reader.myBodyCounter <= 0) {
reader.myReadState = XHTMLReader::READ_NOTHING; reader.myReadState = XHTML_READ_NOTHING;
} }
} }
@ -284,6 +324,43 @@ void XHTMLTagItemAction::doAtEnd(XHTMLReader &reader) {
endParagraph(reader); endParagraph(reader);
} }
bool XHTMLTagVideoAction::isEnabled(XHTMLReadingState state) {
return state == XHTML_READ_BODY || state == XHTML_READ_VIDEO;
}
void XHTMLTagVideoAction::doAtStart(XHTMLReader &reader, const char**) {
if (reader.myReadState == XHTML_READ_BODY) {
reader.myReadState = XHTML_READ_VIDEO;
reader.myVideoEntry = new ZLVideoEntry();
}
}
void XHTMLTagVideoAction::doAtEnd(XHTMLReader &reader) {
if (reader.myReadState == XHTML_READ_VIDEO) {
bookReader(reader).addVideoEntry(*reader.myVideoEntry);
reader.myVideoEntry.reset();
reader.myReadState = XHTML_READ_BODY;
}
}
bool XHTMLTagSourceAction::isEnabled(XHTMLReadingState state) {
return state == XHTML_READ_VIDEO;
}
void XHTMLTagSourceAction::doAtStart(XHTMLReader &reader, const char **xmlattributes) {
const char *mime = reader.attributeValue(xmlattributes, "type");
const char *href = reader.attributeValue(xmlattributes, "src");
if (mime != 0 && href != 0) {
reader.myVideoEntry->addSource(
mime,
ZLFile(pathPrefix(reader) + MiscUtil::decodeHtmlURL(href)).path()
);
}
}
void XHTMLTagSourceAction::doAtEnd(XHTMLReader &reader) {
}
XHTMLTagImageAction::XHTMLTagImageAction(shared_ptr<ZLXMLReader::NamePredicate> predicate) { XHTMLTagImageAction::XHTMLTagImageAction(shared_ptr<ZLXMLReader::NamePredicate> predicate) {
myPredicate = predicate; myPredicate = predicate;
} }
@ -520,6 +597,9 @@ void XHTMLReader::fillTagTable() {
//addAction("tr", new XHTMLTagAction()); //addAction("tr", new XHTMLTagAction());
//addAction("caption", new XHTMLTagAction()); //addAction("caption", new XHTMLTagAction());
//addAction("span", new XHTMLTagAction()); //addAction("span", new XHTMLTagAction());
addAction("video", new XHTMLTagVideoAction());
addAction("source", new XHTMLTagSourceAction());
} }
} }
@ -543,7 +623,7 @@ bool XHTMLReader::readFile(const ZLFile &file, const std::string &referenceName)
myPreformatted = false; myPreformatted = false;
myNewParagraphInProgress = false; myNewParagraphInProgress = false;
myReadState = READ_NOTHING; myReadState = XHTML_READ_NOTHING;
myBodyCounter = 0; myBodyCounter = 0;
myCurrentParagraphIsEmpty = true; myCurrentParagraphIsEmpty = true;
@ -587,7 +667,7 @@ void XHTMLReader::startElementHandler(const char *tag, const char **attributes)
myDoPageBreakAfterStack.push_back(myStyleSheetTable.doBreakAfter(sTag, sClass)); myDoPageBreakAfterStack.push_back(myStyleSheetTable.doBreakAfter(sTag, sClass));
XHTMLTagAction *action = getAction(sTag); XHTMLTagAction *action = getAction(sTag);
if (action != 0) { if (action != 0 && action->isEnabled(myReadState)) {
action->doAtStart(*this, attributes); action->doAtStart(*this, attributes);
} }
@ -613,7 +693,7 @@ void XHTMLReader::endElementHandler(const char *tag) {
myCSSStack.pop_back(); myCSSStack.pop_back();
XHTMLTagAction *action = getAction(tag); XHTMLTagAction *action = getAction(tag);
if (action != 0) { if (action != 0 && action->isEnabled(myReadState)) {
action->doAtEnd(*this); action->doAtEnd(*this);
myNewParagraphInProgress = false; myNewParagraphInProgress = false;
} }
@ -675,14 +755,15 @@ void XHTMLReader::endParagraph() {
void XHTMLReader::characterDataHandler(const char *text, std::size_t len) { void XHTMLReader::characterDataHandler(const char *text, std::size_t len) {
switch (myReadState) { switch (myReadState) {
case READ_NOTHING: case XHTML_READ_NOTHING:
case XHTML_READ_VIDEO:
break; break;
case READ_STYLE: case XHTML_READ_STYLE:
if (!myTableParser.isNull()) { if (!myTableParser.isNull()) {
myTableParser->parse(text, len); myTableParser->parse(text, len);
} }
break; break;
case READ_BODY: case XHTML_READ_BODY:
if (myPreformatted) { if (myPreformatted) {
if (*text == '\r' || *text == '\n') { if (*text == '\r' || *text == '\n') {
endParagraph(); endParagraph();

View file

@ -25,6 +25,7 @@
#include <vector> #include <vector>
#include <ZLXMLReader.h> #include <ZLXMLReader.h>
#include <ZLVideoEntry.h>
#include "../css/StyleSheetTable.h" #include "../css/StyleSheetTable.h"
#include "../css/StyleSheetParser.h" #include "../css/StyleSheetParser.h"
@ -36,6 +37,13 @@ class XHTMLReader;
class EncryptionMap; class EncryptionMap;
enum XHTMLReadingState {
XHTML_READ_NOTHING,
XHTML_READ_STYLE,
XHTML_READ_BODY,
XHTML_READ_VIDEO
};
class XHTMLTagAction { class XHTMLTagAction {
public: public:
@ -43,6 +51,7 @@ public:
virtual void doAtStart(XHTMLReader &reader, const char **xmlattributes) = 0; virtual void doAtStart(XHTMLReader &reader, const char **xmlattributes) = 0;
virtual void doAtEnd(XHTMLReader &reader) = 0; virtual void doAtEnd(XHTMLReader &reader) = 0;
virtual bool isEnabled(XHTMLReadingState state) = 0;
protected: protected:
static BookReader &bookReader(XHTMLReader &reader); static BookReader &bookReader(XHTMLReader &reader);
@ -103,13 +112,10 @@ private:
bool myCurrentParagraphIsEmpty; bool myCurrentParagraphIsEmpty;
shared_ptr<StyleSheetSingleStyleParser> myStyleParser; shared_ptr<StyleSheetSingleStyleParser> myStyleParser;
shared_ptr<StyleSheetTableParser> myTableParser; shared_ptr<StyleSheetTableParser> myTableParser;
enum { XHTMLReadingState myReadState;
READ_NOTHING,
READ_STYLE,
READ_BODY
} myReadState;
int myBodyCounter; int myBodyCounter;
bool myMarkNextImageAsCover; bool myMarkNextImageAsCover;
shared_ptr<ZLVideoEntry> myVideoEntry;
friend class XHTMLTagAction; friend class XHTMLTagAction;
friend class XHTMLTagStyleAction; friend class XHTMLTagStyleAction;
@ -120,6 +126,8 @@ private:
friend class XHTMLTagBodyAction; friend class XHTMLTagBodyAction;
friend class XHTMLTagRestartParagraphAction; friend class XHTMLTagRestartParagraphAction;
friend class XHTMLTagImageAction; friend class XHTMLTagImageAction;
friend class XHTMLTagVideoAction;
friend class XHTMLTagSourceAction;
}; };
#endif /* __XHTMLREADER_H__ */ #endif /* __XHTMLREADER_H__ */

View file

@ -26,11 +26,12 @@
//#include <ZLLanguageUtil.h> //#include <ZLLanguageUtil.h>
#include <ZLUnicodeUtil.h> #include <ZLUnicodeUtil.h>
//#include <ZLStringUtil.h> //#include <ZLStringUtil.h>
//#include <ZLLogger.h> #include <ZLLogger.h>
#include "ZLTextModel.h" #include "ZLTextModel.h"
#include "ZLTextParagraph.h" #include "ZLTextParagraph.h"
#include "ZLTextStyleEntry.h" #include "ZLTextStyleEntry.h"
#include "ZLVideoEntry.h"
ZLTextModel::ZLTextModel(const std::string &id, const std::string &language, const std::size_t rowSize, ZLTextModel::ZLTextModel(const std::string &id, const std::string &language, const std::size_t rowSize,
const std::string &directoryName, const std::string &fileExtension) : const std::string &directoryName, const std::string &fileExtension) :
@ -352,6 +353,31 @@ void ZLTextModel::addBidiReset() {
++myParagraphLengths.back(); ++myParagraphLengths.back();
} }
void ZLTextModel::addVideoEntry(const ZLVideoEntry &entry) {
const std::map<std::string,std::string> &sources = entry.sources();
std::size_t len = 4;
for (std::map<std::string,std::string>::const_iterator it = sources.begin(); it != sources.end(); ++it) {
len += 2 * (ZLUnicodeUtil::utf8Length(it->first) + ZLUnicodeUtil::utf8Length(it->second)) + 4;
}
myLastEntryStart = myAllocator->allocate(len);
*myLastEntryStart = ZLTextParagraphEntry::VIDEO_ENTRY;
*(myLastEntryStart + 1) = 0;
char *p = ZLCachedMemoryAllocator::writeUInt16(myLastEntryStart + 2, sources.size());
for (std::map<std::string,std::string>::const_iterator it = sources.begin(); it != sources.end(); ++it) {
ZLUnicodeUtil::Ucs2String first;
ZLUnicodeUtil::utf8ToUcs2(first, it->first);
p = ZLCachedMemoryAllocator::writeString(p, first);
ZLUnicodeUtil::Ucs2String second;
ZLUnicodeUtil::utf8ToUcs2(second, it->second);
p = ZLCachedMemoryAllocator::writeString(p, second);
}
myParagraphs.back()->addEntry(myLastEntryStart);
++myParagraphLengths.back();
}
void ZLTextModel::flush() { void ZLTextModel::flush() {
myAllocator->flush(); myAllocator->flush();
} }

View file

@ -33,6 +33,7 @@
#include <ZLCachedMemoryAllocator.h> #include <ZLCachedMemoryAllocator.h>
class ZLTextStyleEntry; class ZLTextStyleEntry;
class ZLVideoEntry;
class ZLTextModel { class ZLTextModel {
@ -73,6 +74,7 @@ public:
void addImage(const std::string &id, short vOffset, bool isCover); void addImage(const std::string &id, short vOffset, bool isCover);
void addFixedHSpace(unsigned char length); void addFixedHSpace(unsigned char length);
void addBidiReset(); void addBidiReset();
void addVideoEntry(const ZLVideoEntry &entry);
void flush(); void flush();

View file

@ -46,6 +46,8 @@ public:
STYLE_CLOSE_ENTRY = 7, STYLE_CLOSE_ENTRY = 7,
FIXED_HSPACE_ENTRY = 8, FIXED_HSPACE_ENTRY = 8,
RESET_BIDI_ENTRY = 9, RESET_BIDI_ENTRY = 9,
AUDIO_ENTRY = 10,
VIDEO_ENTRY = 11,
}; };
protected: protected:

View file

@ -0,0 +1,28 @@
/*
* Copyright (C) 2004-2014 Geometer Plus <contact@geometerplus.com>
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
#include "ZLVideoEntry.h"
void ZLVideoEntry::addSource(const std::string &type, const std::string &path) {
mySources.insert(std::make_pair(type, path));
}
const std::map<std::string,std::string> &ZLVideoEntry::sources() const {
return mySources;
}

View file

@ -0,0 +1,38 @@
/*
* Copyright (C) 2004-2014 Geometer Plus <contact@geometerplus.com>
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
#ifndef __ZLVIDEOENTRY_H__
#define __ZLVIDEOENTRY_H__
#include <map>
#include <string>
#include <ZLTextParagraph.h>
class ZLVideoEntry : public ZLTextParagraphEntry {
public:
void addSource(const std::string &type, const std::string &path);
const std::map<std::string,std::string> &sources() const;
private:
std::map<std::string,std::string> mySources;
};
#endif /* __ZLVIDEOENTRY_H__ */

View file

@ -134,6 +134,11 @@ public final class MimeType {
// ??? // ???
public static final MimeType IMAGE_XDJVU = get("image/x-djvu"); public static final MimeType IMAGE_XDJVU = get("image/x-djvu");
// video
public static final MimeType VIDEO_MP4 = get("video/mp4");
public static final MimeType VIDEO_WEBM = get("video/webm");
public static final MimeType VIDEO_OGG = get("video/ogg");
public static final MimeType UNKNOWN = get("*/*"); public static final MimeType UNKNOWN = get("*/*");
public static final MimeType NULL = new MimeType(null, null); public static final MimeType NULL = new MimeType(null, null);

View file

@ -30,6 +30,8 @@ public interface ZLTextParagraph {
byte STYLE_CLOSE = 7; byte STYLE_CLOSE = 7;
byte FIXED_HSPACE = 8; byte FIXED_HSPACE = 8;
byte RESET_BIDI = 9; byte RESET_BIDI = 9;
byte AUDIO = 10;
byte VIDEO = 11;
} }
interface EntryIterator { interface EntryIterator {
@ -46,6 +48,7 @@ public interface ZLTextParagraph {
String getHyperlinkId(); String getHyperlinkId();
ZLImageEntry getImageEntry(); ZLImageEntry getImageEntry();
ZLVideoEntry getVideoEntry();
ZLTextStyleEntry getStyleEntry(); ZLTextStyleEntry getStyleEntry();
short getFixedHSpaceLength(); short getFixedHSpaceLength();

View file

@ -64,6 +64,9 @@ public class ZLTextPlainModel implements ZLTextModel, ZLTextStyleEntry.Feature {
// ImageEntry // ImageEntry
private ZLImageEntry myImageEntry; private ZLImageEntry myImageEntry;
// VideoEntry
private ZLVideoEntry myVideoEntry;
// StyleEntry // StyleEntry
private ZLTextStyleEntry myStyleEntry; private ZLTextStyleEntry myStyleEntry;
@ -114,6 +117,10 @@ public class ZLTextPlainModel implements ZLTextModel, ZLTextStyleEntry.Feature {
return myImageEntry; return myImageEntry;
} }
public ZLVideoEntry getVideoEntry() {
return myVideoEntry;
}
public ZLTextStyleEntry getStyleEntry() { public ZLTextStyleEntry getStyleEntry() {
return myStyleEntry; return myStyleEntry;
} }
@ -163,11 +170,11 @@ public class ZLTextPlainModel implements ZLTextModel, ZLTextStyleEntry.Feature {
} }
case ZLTextParagraph.Entry.HYPERLINK_CONTROL: case ZLTextParagraph.Entry.HYPERLINK_CONTROL:
{ {
short kind = (short)data[dataOffset++]; final short kind = (short)data[dataOffset++];
myControlKind = (byte)kind; myControlKind = (byte)kind;
myControlIsStart = true; myControlIsStart = true;
myHyperlinkType = (byte)(kind >> 8); myHyperlinkType = (byte)(kind >> 8);
short labelLength = (short)data[dataOffset++]; final short labelLength = (short)data[dataOffset++];
myHyperlinkId = new String(data, dataOffset, labelLength); myHyperlinkId = new String(data, dataOffset, labelLength);
dataOffset += labelLength; dataOffset += labelLength;
break; break;
@ -223,6 +230,24 @@ public class ZLTextPlainModel implements ZLTextModel, ZLTextStyleEntry.Feature {
case ZLTextParagraph.Entry.RESET_BIDI: case ZLTextParagraph.Entry.RESET_BIDI:
// No data // No data
break; break;
case ZLTextParagraph.Entry.AUDIO:
// No data
break;
case ZLTextParagraph.Entry.VIDEO:
{
myVideoEntry = new ZLVideoEntry();
final short mapSize = (short)data[dataOffset++];
for (short i = 0; i < mapSize; ++i) {
short len = (short)data[dataOffset++];
final String mime = new String(data, dataOffset, len);
dataOffset += len;
len = (short)data[dataOffset++];
final String src = new String(data, dataOffset, len);
dataOffset += len;
myVideoEntry.addSource(mime, src);
}
break;
}
} }
++myCounter; ++myCounter;
myDataOffset = dataOffset; myDataOffset = dataOffset;

View file

@ -0,0 +1,35 @@
/*
* Copyright (C) 2007-2014 Geometer Plus <contact@geometerplus.com>
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
package org.geometerplus.zlibrary.text.model;
import java.util.Map;
import java.util.HashMap;
public class ZLVideoEntry {
private final Map<String,String> mySources = new HashMap<String,String>();
public void addSource(String mime, String path) {
mySources.put(mime, path);
}
public Map<String,String> sources() {
return mySources;
}
}

View file

@ -100,6 +100,16 @@ public final class ZLTextParagraphCursor {
} }
} }
break; break;
case ZLTextParagraph.Entry.AUDIO:
break;
case ZLTextParagraph.Entry.VIDEO:
final ZLVideoEntry videoEntry = it.getVideoEntry();
elements.add(new ZLTextVideoElement(videoEntry.sources()));
System.err.println("VIDEO === VIDEO");
for (Map.Entry<String,String> entry : videoEntry.sources().entrySet()) {
System.err.println(entry.getKey() + " ===> " + entry.getValue());
}
break;
case ZLTextParagraph.Entry.STYLE_CSS: case ZLTextParagraph.Entry.STYLE_CSS:
case ZLTextParagraph.Entry.STYLE_OTHER: case ZLTextParagraph.Entry.STYLE_OTHER:
elements.add(new ZLTextStyleElement(it.getStyleEntry())); elements.add(new ZLTextStyleElement(it.getStyleEntry()));

View file

@ -0,0 +1,30 @@
/*
* Copyright (C) 2007-2014 Geometer Plus <contact@geometerplus.com>
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
package org.geometerplus.zlibrary.text.view;
import java.util.Map;
public final class ZLTextVideoElement extends ZLTextElement {
public final Map<String,String> Sources;
ZLTextVideoElement(Map<String,String> sources) {
Sources = sources;
}
}

View file

@ -908,6 +908,21 @@ public abstract class ZLTextView extends ZLTextViewBase {
getScalingType(imageElement), getScalingType(imageElement),
getAdjustingModeForImages() getAdjustingModeForImages()
); );
} else if (element instanceof ZLTextVideoElement) {
// TODO: draw
context.setLineColor(getTextColor(ZLTextHyperlink.NO_LINK));
context.drawLine(area.XStart, area.YStart, area.XStart, area.YEnd);
context.drawLine(area.XStart, area.YEnd, area.XEnd, area.YEnd);
context.drawLine(area.XEnd, area.YEnd, area.XEnd, area.YStart);
context.drawLine(area.XEnd, area.YStart, area.XStart, area.YStart);
final int l = area.XStart + (area.XEnd - area.XStart) * 7 / 16;
final int r = area.XStart + (area.XEnd - area.XStart) * 10 / 16;
final int t = area.YStart + (area.YEnd - area.YStart) * 2 / 6;
final int b = area.YStart + (area.YEnd - area.YStart) * 4 / 6;
final int c = area.YStart + (area.YEnd - area.YStart) / 2;
context.drawLine(l, t, l, b);
context.drawLine(l, t, r, c);
context.drawLine(l, b, r, c);
} else if (element == ZLTextElement.HSpace) { } else if (element == ZLTextElement.HSpace) {
final int cw = context.getSpaceWidth(); final int cw = context.getSpaceWidth();
/* /*
@ -1075,6 +1090,9 @@ public abstract class ZLTextView extends ZLTextViewBase {
} else if (element instanceof ZLTextImageElement) { } else if (element instanceof ZLTextImageElement) {
wordOccurred = true; wordOccurred = true;
isVisible = true; isVisible = true;
} else if (element instanceof ZLTextVideoElement) {
wordOccurred = true;
isVisible = true;
} else if (isStyleChangeElement(element)) { } else if (isStyleChangeElement(element)) {
applyStyleChangeElement(element); applyStyleChangeElement(element);
} }
@ -1251,7 +1269,7 @@ public abstract class ZLTextView extends ZLTextViewBase {
wordOccurred = false; wordOccurred = false;
--spaceCounter; --spaceCounter;
} }
} else if (element instanceof ZLTextWord || element instanceof ZLTextImageElement) { } else if (element instanceof ZLTextWord || element instanceof ZLTextImageElement || element instanceof ZLTextVideoElement) {
final int height = getElementHeight(element); final int height = getElementHeight(element);
final int descent = getElementDescent(element); final int descent = getElementDescent(element);
final int length = element instanceof ZLTextWord ? ((ZLTextWord)element).Length : 0; final int length = element instanceof ZLTextWord ? ((ZLTextWord)element).Length : 0;

View file

@ -197,6 +197,8 @@ abstract class ZLTextViewBase extends ZLView {
getScalingType(imageElement) getScalingType(imageElement)
); );
return size != null ? size.Width : 0; return size != null ? size.Width : 0;
} else if (element instanceof ZLTextVideoElement) {
return 300;
} else if (element == ZLTextElement.Indent) { } else if (element == ZLTextElement.Indent) {
return myTextStyle.getFirstLineIndentDelta(); return myTextStyle.getFirstLineIndentDelta();
} else if (element instanceof ZLTextFixedHSpaceElement) { } else if (element instanceof ZLTextFixedHSpaceElement) {
@ -217,6 +219,8 @@ abstract class ZLTextViewBase extends ZLView {
); );
return (size != null ? size.Height : 0) + return (size != null ? size.Height : 0) +
Math.max(getContext().getStringHeight() * (myTextStyle.getLineSpacePercent() - 100) / 100, 3); Math.max(getContext().getStringHeight() * (myTextStyle.getLineSpacePercent() - 100) / 100, 3);
} else if (element instanceof ZLTextVideoElement) {
return 200;
} }
return 0; return 0;
} }