Subversion Repositories Scribus

Rev

Rev 21563 | Rev 22165 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
4430 cbradney 1
/*
2
For general Scribus (>=1.3.2) copyright and licensing information please refer
3
to the COPYING file provided with the program. Following this notice may exist
4
a copyright and/or license notice that predates the release of Scribus 1.3.2
5
for which a new license (GPL+exception) is in place.
6
*/
3 paul 7
/***************************************************************************
8
                          hyphenator.cpp  -  description
9
                             -------------------
10
    begin                : Sat Nov 02 08:00:00 CEST 2002
11
    copyright            : (C) 2002 by Franz Schmid
12
    email                : Franz.Schmid@altmuehlnet.de
13
 ***************************************************************************/
14
 
15
/***************************************************************************
16
 *                                                                         *
17
 *   This program is free software; you can redistribute it and/or modify  *
18
 *   it under the terms of the GNU General Public License as published by  *
19
 *   the Free Software Foundation; either version 2 of the License, or     *
20
 *   (at your option) any later version.                                   *
21
 *                                                                         *
22
 ***************************************************************************/
23
#include "hyphenator.h"
13650 cbradney 24
#include "ui/hyask.h"
128 Franz 25
 
2688 craig 26
#include "scconfig.h"
128 Franz 27
 
16546 jghali 28
#include <QApplication>
10223 cbradney 29
#include <QCursor>
10242 subik 30
#include <QCheckBox>
9535 fschmid 31
#include <QByteArray>
21563 jghali 32
 
12787 pierre 33
#include "langmgr.h"
1693 craig 34
#include "scpaths.h"
5781 cbradney 35
#include "scribuscore.h"
13805 jghali 36
#include "scribusdoc.h"
1866 fschmid 37
#include "prefsfile.h"
2834 cbradney 38
#include "prefsmanager.h"
3 paul 39
 
10511 fschmid 40
Hyphenator::Hyphenator(QWidget* parent, ScribusDoc *dok) : QObject( parent ),
18330 jghali 41
        m_doc(dok),
21563 jghali 42
        m_hdict(NULL),
43
        m_codec(NULL),
44
        m_automatic(m_doc->hyphAutomatic()),
18330 jghali 45
        AutoCheck(m_doc->hyphAutoCheck())
3 paul 46
{
10170 fschmid 47
        rememberedWords.clear();
48
/* Add reading these special lists from prefs or doc here */
49
        ignoredWords.clear();
50
        specialWords.clear();
3 paul 51
}
52
 
53
Hyphenator::~Hyphenator()
54
{
18330 jghali 55
        if (m_hdict)
56
                hnj_hyphen_free(m_hdict);
3 paul 57
}
58
 
21563 jghali 59
bool Hyphenator::loadDict(const QString& name)
3 paul 60
{
22164 jghali 61
        if (LanguageManager::instance()->getHyphFilename(name).isEmpty())
21563 jghali 62
                return false;
12787 pierre 63
 
21563 jghali 64
        if (m_language != name)
164 Franz 65
        {
21563 jghali 66
                m_language = name;
6931 avox 67
 
21563 jghali 68
                QFile file(LanguageManager::instance()->getHyphFilename(m_language));
6931 avox 69
 
18330 jghali 70
                if (m_hdict != NULL)
71
                        hnj_hyphen_free(m_hdict);
6931 avox 72
 
21563 jghali 73
                if (file.open(QIODevice::ReadOnly))
6931 avox 74
                {
21563 jghali 75
                        m_codec = QTextCodec::codecForName(file.readLine());
76
                        m_hdict = hnj_hyphen_load(file.fileName().toLocal8Bit().data());
77
                        file.close();
78
                        return true;
6931 avox 79
                }
80
                else
81
                {
18330 jghali 82
                        m_hdict = NULL;
21563 jghali 83
                        return false;
6931 avox 84
                }
164 Franz 85
        }
21563 jghali 86
 
22164 jghali 87
        return (m_codec != 0 && m_hdict != 0);
3 paul 88
}
89
 
21563 jghali 90
void Hyphenator::slotNewSettings(bool Autom, bool ACheck)
3 paul 91
{
92
        AutoCheck = ACheck;
18330 jghali 93
        m_doc->setHyphAutomatic(Autom);
94
        m_doc->setHyphAutoCheck(AutoCheck);
3 paul 95
}
96
 
6931 avox 97
void Hyphenator::slotHyphenateWord(PageItem* it, const QString& text, int firstC)
3 paul 98
{
21563 jghali 99
        if (text.contains(SpecialChars::SHYPHEN))
164 Franz 100
                return;
22164 jghali 101
 
21563 jghali 102
        const CharStyle& style = it->itemText.charStyle(firstC);
103
        if (text.length() >= style.hyphenWordMin())
104
        {
105
                bool ok = loadDict(style.language());
106
                if (!ok)
107
                        return;
164 Franz 108
 
21563 jghali 109
                QByteArray te = m_codec->fromUnicode(text);
110
                char *buffer = static_cast<char*>(malloc(te.length() + 5));
3 paul 111
                if (buffer == NULL)
112
                        return;
21563 jghali 113
                char **rep = NULL;
114
                int *pos = NULL;
115
                int *cut = NULL;
116
                // TODO: support non-standard hyphenation, see hnj_hyphen_hyphenate2 docs
117
                if (!hnj_hyphen_hyphenate2(m_hdict, te.data(), te.length(), buffer, NULL, &rep, &pos, &cut))
164 Franz 118
                {
21563 jghali 119
                        buffer[te.length()] = '\0';
120
                        it->itemText.hyphenateWord(firstC, text.length(), buffer);
164 Franz 121
                }
3 paul 122
                free(buffer);
18144 jghali 123
                if (rep)
124
                {
21563 jghali 125
                        for (int i = 0; i < te.length() - 1; ++i)
126
                                free(rep[i]);
18144 jghali 127
                }
21563 jghali 128
                free(rep);
129
                free(pos);
130
                free(cut);
164 Franz 131
        }
3 paul 132
}
133
 
134
void Hyphenator::slotHyphenate(PageItem* it)
135
{
21563 jghali 136
        if (!(it->asTextFrame()) || (it->itemText.length() == 0))
164 Franz 137
                return;
18330 jghali 138
        m_doc->DoDrawing = false;
5559 avox 139
 
3 paul 140
        QString text = "";
5559 avox 141
 
6931 avox 142
        int startC = 0;
15522 jghali 143
        if (it->itemText.lengthOfSelection() > 0)
164 Franz 144
        {
6931 avox 145
                startC = it->itemText.startOfSelection();
146
                text = it->itemText.text(startC, it->itemText.lengthOfSelection());
164 Franz 147
        }
5559 avox 148
        else {
149
                text = it->itemText.text(0, it->itemText.length());
150
        }
21563 jghali 151
 
9769 fschmid 152
        rememberedWords.clear();
18181 fschmid 153
        qApp->setOverrideCursor(QCursor(Qt::WaitCursor));
21563 jghali 154
 
155
        BreakIterator* bi = StoryText::getWordIterator();
156
        bi->setText((const UChar*) text.utf16());
157
        int pos = bi->first();
158
        while (pos != BreakIterator::DONE)
164 Franz 159
        {
21563 jghali 160
                int firstC = pos;
161
                pos = bi->next();
162
                int lastC = pos;
163
                int countC = lastC - firstC;
164
 
165
                const CharStyle& style = it->itemText.charStyle(firstC);
166
                if (countC > 0 && countC > style.hyphenWordMin() - 1)
7029 avox 167
                {
21563 jghali 168
                        QString word = text.mid(firstC, countC);
169
                        QString wordLower = QLocale(style.language()).toLower(word);
170
                        if (wordLower.contains(SpecialChars::SHYPHEN))
6931 avox 171
                                break;
172
 
21563 jghali 173
                        bool ok = loadDict(style.language());
174
                        if (!ok)
175
                                continue;
6931 avox 176
 
21563 jghali 177
                        QByteArray te = m_codec->fromUnicode(wordLower);
178
                        char *buffer = static_cast<char*>(malloc(te.length() + 5));
3 paul 179
                        if (buffer == NULL)
180
                                break;
21563 jghali 181
 
182
                        char **rep = NULL;
183
                        int *pos = NULL;
184
                        int *cut = NULL;
185
                        // TODO: support non-standard hyphenation, see hnj_hyphen_hyphenate2 docs
186
                        if (!hnj_hyphen_hyphenate2(m_hdict, te.data(), te.length(), buffer, NULL, &rep, &pos, &cut))
164 Franz 187
                        {
8547 cbradney 188
                                int i = 0;
21563 jghali 189
                                buffer[te.length()] = '\0';
3 paul 190
                                bool hasHyphen = false;
21563 jghali 191
                                for (i = 1; i < wordLower.length()-1; ++i)
164 Franz 192
                                {
193
                                        if(buffer[i] & 1)
3 paul 194
                                        {
195
                                                hasHyphen = true;
196
                                                break;
197
                                        }
164 Franz 198
                                }
10170 fschmid 199
                                QString outs = "";
200
                                QString input = "";
21563 jghali 201
                                outs += word[0];
202
                                for (i = 1; i < wordLower.length()-1; ++i)
6931 avox 203
                                {
21563 jghali 204
                                        outs += word[i];
10170 fschmid 205
                                        if(buffer[i] & 1)
206
                                                outs += "-";
6931 avox 207
                                }
21563 jghali 208
                                outs += word.right(1);
10170 fschmid 209
                                input = outs;
21563 jghali 210
                                if (!ignoredWords.contains(word))
10170 fschmid 211
                                {
212
                                        if (!hasHyphen)
21563 jghali 213
                                                it->itemText.hyphenateWord(startC + firstC, wordLower.length(), NULL);
214
                                        else if (m_automatic)
13112 fschmid 215
                                        {
21563 jghali 216
                                                if (specialWords.contains(word))
13112 fschmid 217
                                                {
21563 jghali 218
                                                        outs = specialWords.value(word);
13112 fschmid 219
                                                        uint ii = 1;
220
                                                        for (i = 1; i < outs.length()-1; ++i)
221
                                                        {
222
                                                                QChar cht = outs[i];
223
                                                                if (cht == '-')
224
                                                                        buffer[ii-1] = 1;
225
                                                                else
226
                                                                {
227
                                                                        buffer[ii] = 0;
228
                                                                        ++ii;
229
                                                                }
230
                                                        }
231
                                                }
21563 jghali 232
                                                it->itemText.hyphenateWord(startC + firstC, wordLower.length(), buffer);
13112 fschmid 233
                                        }
10170 fschmid 234
                                        else
3 paul 235
                                        {
21563 jghali 236
                                                if (specialWords.contains(word))
164 Franz 237
                                                {
21563 jghali 238
                                                        outs = specialWords.value(word);
12094 jghali 239
                                                        uint ii = 1;
10170 fschmid 240
                                                        for (i = 1; i < outs.length()-1; ++i)
241
                                                        {
242
                                                                QChar cht = outs[i];
243
                                                                if (cht == '-')
12094 jghali 244
                                                                        buffer[ii-1] = 1;
10170 fschmid 245
                                                                else
12094 jghali 246
                                                                {
10170 fschmid 247
                                                                        buffer[ii] = 0;
12094 jghali 248
                                                                        ++ii;
249
                                                                }
10170 fschmid 250
                                                        }
164 Franz 251
                                                }
10179 fschmid 252
                                                if (rememberedWords.contains(input))
9769 fschmid 253
                                                {
10170 fschmid 254
                                                        outs = rememberedWords.value(input);
12094 jghali 255
                                                        uint ii = 1;
9769 fschmid 256
                                                        for (i = 1; i < outs.length()-1; ++i)
257
                                                        {
258
                                                                QChar cht = outs[i];
259
                                                                if (cht == '-')
12094 jghali 260
                                                                        buffer[ii-1] = 1;
9769 fschmid 261
                                                                else
12094 jghali 262
                                                                {
10170 fschmid 263
                                                                        buffer[ii] = 0;
12094 jghali 264
                                                                        ++ii;
265
                                                                }
9769 fschmid 266
                                                        }
21563 jghali 267
                                                        it->itemText.hyphenateWord(firstC, wordLower.length(), buffer);
9769 fschmid 268
                                                }
269
                                                else
270
                                                {
10170 fschmid 271
                                                        qApp->changeOverrideCursor(QCursor(Qt::ArrowCursor));
272
                                                        PrefsContext* prefs = PrefsManager::instance()->prefsFile->getContext("hyhpen_options");
273
                                                        int xpos = prefs->getInt("Xposition", -9999);
274
                                                        int ypos = prefs->getInt("Yposition", -9999);
275
                                                        HyAsk *dia = new HyAsk((QWidget*)parent(), outs);
276
                                                        if ((xpos != -9999) && (ypos != -9999))
277
                                                                dia->move(xpos, ypos);
278
                                                        qApp->processEvents();
279
                                                        if (dia->exec())
280
                                                        {
281
                                                                outs = dia->Wort->text();
12094 jghali 282
                                                                uint ii = 1;
10170 fschmid 283
                                                                for (i = 1; i < outs.length()-1; ++i)
284
                                                                {
285
                                                                        QChar cht = outs[i];
286
                                                                        if (cht == '-')
12094 jghali 287
                                                                                buffer[ii-1] = 1;
10170 fschmid 288
                                                                        else
12094 jghali 289
                                                                        {
10170 fschmid 290
                                                                                buffer[ii] = 0;
12094 jghali 291
                                                                                ++ii;
292
                                                                        }
10170 fschmid 293
                                                                }
294
                                                                if (!rememberedWords.contains(input))
295
                                                                        rememberedWords.insert(input, outs);
296
                                                                if (dia->addToIgnoreList->isChecked())
297
                                                                {
21563 jghali 298
                                                                        if (!ignoredWords.contains(word))
299
                                                                                ignoredWords.insert(word);
10170 fschmid 300
                                                                }
301
                                                                if (dia->addToExceptionList->isChecked())
302
                                                                {
21563 jghali 303
                                                                        if (!specialWords.contains(word))
304
                                                                                specialWords.insert(word, outs);
10170 fschmid 305
                                                                }
21563 jghali 306
                                                                it->itemText.hyphenateWord(firstC, wordLower.length(), buffer);
10170 fschmid 307
                                                        }
308
                                                        else
309
                                                        {
310
                                                                free(buffer);
311
                                                                buffer = NULL;
312
                                                                prefs->set("Xposition", dia->xpos);
313
                                                                prefs->set("Yposition", dia->ypos);
314
                                                                delete dia;
315
                                                                break;
316
                                                        }
9769 fschmid 317
                                                        prefs->set("Xposition", dia->xpos);
318
                                                        prefs->set("Yposition", dia->ypos);
319
                                                        delete dia;
10170 fschmid 320
                                                        qApp->changeOverrideCursor(QCursor(Qt::WaitCursor));
9769 fschmid 321
                                                }
164 Franz 322
                                        }
3 paul 323
                                }
164 Franz 324
                        }
3 paul 325
                        free(buffer);
18144 jghali 326
                        if (rep)
327
                        {
21563 jghali 328
                                for (int i = 0; i < te.length() - 1; ++i)
329
                                        free(rep[i]);
18144 jghali 330
                        }
21563 jghali 331
                        free(rep);
332
                        free(pos);
333
                        free(cut);
164 Franz 334
                }
335
        }
18181 fschmid 336
        qApp->restoreOverrideCursor();
18330 jghali 337
        m_doc->DoDrawing = true;
9769 fschmid 338
        rememberedWords.clear();
3 paul 339
}
2621 fschmid 340
 
341
void Hyphenator::slotDeHyphenate(PageItem* it)
342
{
5721 avox 343
        if (!(it->asTextFrame()) || (it ->itemText.length() == 0))
2621 fschmid 344
                return;
5559 avox 345
 
15522 jghali 346
        if (it->itemText.lengthOfSelection() > 0)
13054 pierre 347
        {
348
                it->itemText.hyphenateWord(it->itemText.startOfSelection(), it->itemText.lengthOfSelection(), NULL);
349
        }
350
        else {
351
                uint a = it->itemText.length();
352
                it->itemText.hyphenateWord(0, a, NULL);
353
        }
18330 jghali 354
        m_doc->DoDrawing = true;
2621 fschmid 355
}