1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
|
<?php
/**
* This is the way MOBI files should be created if you want all features (TOC, images).
*
* File modified by Dawson for use in eBook Creator
* Added pagebreaks and a setting to remove table of contents.
*/
class MOBIFile extends ContentProvider {
const PARAGRAPH = 0;
const H2 = 1;
const H3 = 2;
const IMAGE = 3;
const PAGEBREAK = 4;
private $settings = array("title" => "Unknown Title", "toc" => true);
private $parts = array();
private $images = array();
/**
* Get the text data (the "html" code)
*/
public function getTextData(){
$prefix = "<html><head><guide><reference title='CONTENT' type='toc' filepos=0000000000 /></guide></head><body>";
$title = "<h1>".$this->settings["title"]."</h1>";
list($text, $entries) = $this->generateText();
if($this->settings["toc"]) {
$toc = $this->generateTOC($entries); //Generate TOC to get the right length
$toc = $this->generateTOC($entries, strlen($prefix)+strlen($toc)+strlen($title)); //Generate the real TOC
}
$suffix = "</body></html>";
return $prefix.$toc.$title.$text.$suffix;
}
/**
* Generate the body's text and the chapter entries
* @return array($string, $entries) $string is the html data, $entries
* contains the level, the title and the position of the titles.
*/
public function generateText(){
$str = "";
$entries = array();
for($i = 0; $i < sizeof($this->parts); $i++){
list($type, $data) = $this->parts[$i];
$id = "title_".$i;
switch($type){
case self::PARAGRAPH:
$str .= "<p>".$data."</p>";
break;
case self::PAGEBREAK:
$str .= '<mbp:pagebreak/>';
break;
case self::H2:
$entries[] = array("level" => 2, "position" => strlen($str), "title" => $data, "id" => $id);
$str .= "<h2 id='" . $id . "'>".$data."</h2>";
break;
case self::H3:
$entries[] = array("level" => 3, "position" => strlen($str), "title" => $data, "id" => $id);
$str .= "<h3 id='" . $id . "'>".$data."</h3>";
break;
case self::IMAGE:
$str .= "<img recindex=".str_pad($data+1, 10, "0", STR_PAD_LEFT)." />";
break;
}
}
return array($str, $entries);
}
/**
* Generate a TOC
* @param $entries The entries array generated by generateText
* @param $base The zero position
*/
public function generateTOC($entries, $base = 0){
$toc = "<h2>Contents</h2>";
$toc .= "<blockquote><table summary='Table of Contents'><col/><tbody>";
for($i = 0, $len = sizeof($entries); $i < $len; $i++){
$entry = $entries[$i];
$pos = str_pad($entry["position"]+$base, 10, "0", STR_PAD_LEFT);
$toc .= "<tr><td><a href='#".$entry["id"]."' filepos='".$pos."'>".$entry["title"]."</a></td></tr>";
}
return $toc."</tbody></b></table></blockquote><mbp:pagebreak/>";
}
/**
* Get the file records of the images
*/
public function getImages(){
return $this->images;
}
/**
* Get the metadata
*/
public function getMetaData(){
return $this->settings;
}
/**
* Change the file's settings. For example set("author", "John Doe") or set("title", "The adventures of John Doe").
* @param $key Key of the setting to insert.
*/
public function set($key, $value){
$this->settings[$key] = $value;
}
/**
* Get the file's settings.
*/
public function get($key){
return $this->settings[$key];
}
/**
* Append a paragraph of text to the file.
* @param string $text The text to insert.
*/
public function appendParagraph($text){
$this->parts[] = array(self::PARAGRAPH, $text);
}
/**
* Append a chapter title (H2)
* @param string $title The title to insert.
*/
public function appendChapterTitle($title){
$this->parts[] = array(self::H2, $title);
}
/**
* Append a section title (H3)
* @param string $title The title to insert.
*/
public function appendSectionTitle($title){
$this->parts[] = array(self::H3, $title);
}
public function appendPageBreak() {
$this->parts[] = array(self::PAGEBREAK, null);
}
/**
* Append an image.
* @param resource $img An image file (for example, created by `imagecreate`)
*/
public function appendImage($img){
$imgIndex = sizeof($this->images);
$this->images[] = new FileRecord(new Record(ImageHandler::CreateImage($img)));
$this->parts[] = array(self::IMAGE, $imgIndex);
}
}
|