summaryrefslogtreecommitdiff
path: root/rbutil/rbutilqt/base/voicefile.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'rbutil/rbutilqt/base/voicefile.cpp')
-rw-r--r--rbutil/rbutilqt/base/voicefile.cpp96
1 files changed, 89 insertions, 7 deletions
diff --git a/rbutil/rbutilqt/base/voicefile.cpp b/rbutil/rbutilqt/base/voicefile.cpp
index b7a5f8f760..70c0f7b653 100644
--- a/rbutil/rbutilqt/base/voicefile.cpp
+++ b/rbutil/rbutilqt/base/voicefile.cpp
@@ -16,11 +16,13 @@
16 * 16 *
17 ****************************************************************************/ 17 ****************************************************************************/
18 18
19#include <QtCore>
19#include "voicefile.h" 20#include "voicefile.h"
20#include "utils.h" 21#include "utils.h"
21#include "rockboxinfo.h" 22#include "rockboxinfo.h"
22#include "rbsettings.h" 23#include "rbsettings.h"
23#include "systeminfo.h" 24#include "systeminfo.h"
25#include "ziputil.h"
24 26
25VoiceFileCreator::VoiceFileCreator(QObject* parent) :QObject(parent) 27VoiceFileCreator::VoiceFileCreator(QObject* parent) :QObject(parent)
26{ 28{
@@ -54,7 +56,6 @@ bool VoiceFileCreator::createVoiceFile()
54 emit done(true); 56 emit done(true);
55 return false; 57 return false;
56 } 58 }
57
58 QString target = info.target(); 59 QString target = info.target();
59 QString features = info.features(); 60 QString features = info.features();
60 m_targetid = info.targetID().toInt(); 61 m_targetid = info.targetID().toInt();
@@ -62,14 +63,97 @@ bool VoiceFileCreator::createVoiceFile()
62 m_voiceformat = info.voicefmt(); 63 m_voiceformat = info.voicefmt();
63 QString version = m_versionstring.left(m_versionstring.indexOf("-")).remove("r"); 64 QString version = m_versionstring.left(m_versionstring.indexOf("-")).remove("r");
64 65
65 //prepare download url 66 // check if voicefile is present on target
67 QString fn = m_mountpoint + "/.rockbox/langs/voicestrings.zip";
68 qDebug() << "[VoiceFile] searching for zipped voicestrings at" << fn;
69 if(QFileInfo(fn).isFile()) {
70 // search for binary voice strings file in archive
71 ZipUtil z(this);
72 if(z.open(fn)) {
73 QStringList contents = z.files();
74 int index;
75 for(index = 0; index < contents.size(); ++index) {
76 // strip any path, we don't know the structure in the zip
77 if(QFileInfo(contents.at(index)).baseName() == m_lang) {
78 break;
79 }
80 }
81 if(index < contents.size()) {
82 qDebug() << "[VoiceFile] extracting strings file from zip";
83 // extract strings
84 QTemporaryFile stringsfile;
85 stringsfile.open();
86 QString sfn = stringsfile.fileName();
87 // ZipUtil::extractArchive() only compares the filename.
88 if(z.extractArchive(sfn, QFileInfo(contents.at(index)).fileName())) {
89 emit logItem(tr("Extracted voice strings from installation"), LOGINFO);
90
91 stringsfile.seek(0);
92 QByteArray data = stringsfile.readAll();
93 const char* buf = data.constData();
94 // check file header
95 // header (4 bytes): cookie = 9a, version = 06, targetid, options
96 // subheader for each user. Only "core" for now.
97 // subheader (6 bytes): count (2bytes), size (2bytes), offset (2bytes)
98 if(buf[0] != (char)0x9a || buf[1] != 0x06 || buf[2] != m_targetid) {
99 emit logItem(tr("Extracted voice strings incompatible"), LOGINFO);
100 }
101 else {
102 QMap<int, QString> voicestrings;
103
104 /* skip header */
105 int idx = 10;
106 do {
107 unsigned int id = ((unsigned char)buf[idx])<<8
108 | ((unsigned char)buf[idx+1]);
109 // need to use strlen here, since QString::size()
110 // returns number of characters, not bytes.
111 int len = strlen(&buf[idx + 2]);
112 voicestrings[id] = QString::fromUtf8(&buf[idx+2]);
113 idx += 2 + len + 1;
114
115 } while(idx < data.size());
116
117 stringsfile.close();
118
119 // create input file suitable for voicefont from strings.
120 QTemporaryFile voicefontlist;
121 voicefontlist.open();
122 m_filename = voicefontlist.fileName();
123 for(int i = 0; i < voicestrings.size(); ++i) {
124 QByteArray qba;
125 qba = QString("id: %1_%2\n")
126 .arg(voicestrings.keys().at(i) < 0x8000 ? "LANG" : "VOICE")
127 .arg(voicestrings.keys().at(i)).toUtf8();
128 voicefontlist.write(qba);
129 qba = QString("voice: \"%1\"\n").arg(
130 voicestrings[voicestrings.keys().at(i)]).toUtf8();
131 voicefontlist.write(qba);
132 }
133 voicefontlist.close();
134
135 // everything successful, now create the actual voice file.
136 create();
137 return true;
138 }
139
140 }
141 }
142 }
143 }
144 emit logItem(tr("Could not retrieve strings from installation, downloading"), LOGINFO);
145 // if either no zip with voice strings is found or something went wrong
146 // retrieving the necessary files we'll end up here, trying to get the
147 // genlang output as previously from the webserver.
148
149 // prepare download url
66 QString genlang = SystemInfo::value(SystemInfo::GenlangUrl).toString(); 150 QString genlang = SystemInfo::value(SystemInfo::GenlangUrl).toString();
67 genlang.replace("%LANG%", m_lang); 151 genlang.replace("%LANG%", m_lang);
68 genlang.replace("%TARGET%", target); 152 genlang.replace("%TARGET%", target);
69 genlang.replace("%REVISION%", version); 153 genlang.replace("%REVISION%", version);
70 genlang.replace("%FEATURES%", features); 154 genlang.replace("%FEATURES%", features);
71 QUrl genlangUrl(genlang); 155 QUrl genlangUrl(genlang);
72 qDebug() << "[VoiceFileCreator] downloading " << genlangUrl; 156 qDebug() << "[VoiceFileCreator] downloading" << genlangUrl;
73 157
74 //download the correct genlang output 158 //download the correct genlang output
75 QTemporaryFile *downloadFile = new QTemporaryFile(this); 159 QTemporaryFile *downloadFile = new QTemporaryFile(this);
@@ -129,8 +213,6 @@ void VoiceFileCreator::create(void)
129 return; 213 return;
130 } 214 }
131 215
132 QCoreApplication::processEvents();
133
134 //read in downloaded file 216 //read in downloaded file
135 emit logItem(tr("Reading strings..."),LOGINFO); 217 emit logItem(tr("Reading strings..."),LOGINFO);
136 QTextStream in(&genlang); 218 QTextStream in(&genlang);
@@ -200,7 +282,7 @@ void VoiceFileCreator::create(void)
200 connect(&generator,SIGNAL(logItem(QString,int)),this,SIGNAL(logItem(QString,int))); 282 connect(&generator,SIGNAL(logItem(QString,int)),this,SIGNAL(logItem(QString,int)));
201 connect(&generator,SIGNAL(logProgress(int,int)),this,SIGNAL(logProgress(int,int))); 283 connect(&generator,SIGNAL(logProgress(int,int)),this,SIGNAL(logProgress(int,int)));
202 connect(this,SIGNAL(aborted()),&generator,SLOT(abort())); 284 connect(this,SIGNAL(aborted()),&generator,SLOT(abort()));
203 285
204 if(generator.process(&m_talkList, m_wavtrimThreshold) == TalkGenerator::eERROR) 286 if(generator.process(&m_talkList, m_wavtrimThreshold) == TalkGenerator::eERROR)
205 { 287 {
206 cleanup(); 288 cleanup();
@@ -209,7 +291,7 @@ void VoiceFileCreator::create(void)
209 return; 291 return;
210 } 292 }
211 } 293 }
212 294
213 //make voicefile 295 //make voicefile
214 emit logItem(tr("Creating voicefiles..."),LOGINFO); 296 emit logItem(tr("Creating voicefiles..."),LOGINFO);
215 FILE* ids2 = fopen(m_filename.toLocal8Bit(), "r"); 297 FILE* ids2 = fopen(m_filename.toLocal8Bit(), "r");