Rev 23782 | Details | Compare with Previous | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
4507 | 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 | */ |
||
7 | /*************************************************************************** |
||
8 | gsutil.cpp - description |
||
9 | ------------------- |
||
10 | begin : Fri Sep 14 2001 |
||
11 | copyright : (C) 2001 by Franz Schmid |
||
12 | copyright : (C) 2006- Scribus Team (code moved from util.cpp) |
||
13 | email : Franz.Schmid@altmuehlnet.de |
||
14 | ***************************************************************************/ |
||
15 | |||
16 | /*************************************************************************** |
||
17 | * * |
||
18 | * This program is free software; you can redistribute it and/or modify * |
||
19 | * it under the terms of the GNU General Public License as published by * |
||
20 | * the Free Software Foundation; either version 2 of the License, or * |
||
21 | * (at your option) any later version. * |
||
22 | * * |
||
23 | ***************************************************************************/ |
||
24 | |||
10212 | cbradney | 25 | #include "util_ghostscript.h" |
4507 | cbradney | 26 | |
10223 | cbradney | 27 | #include <QDebug> |
28 | #include <QDir> |
||
29 | #include <QFile> |
||
30 | #include <QFileInfo> |
||
31 | #include <QPainter> |
||
32 | #include <QPixmap> |
||
10006 | cbradney | 33 | #include <QProcess> |
4507 | cbradney | 34 | |
35 | #include "scconfig.h" |
||
36 | |||
37 | #ifdef HAVE_UNISTD_H |
||
38 | #include <unistd.h> |
||
39 | #endif |
||
10223 | cbradney | 40 | |
15706 | jghali | 41 | #if defined(_WIN32) |
42 | #include <windows.h> |
||
17762 | jghali | 43 | #ifndef KEY_WOW64_32KEY |
44 | #define KEY_WOW64_32KEY (0x0200) |
||
15706 | jghali | 45 | #endif |
17762 | jghali | 46 | #ifndef KEY_WOW64_64KEY |
47 | #define KEY_WOW64_64KEY (0x0100) |
||
48 | #endif |
||
49 | #endif |
||
15706 | jghali | 50 | |
4507 | cbradney | 51 | #include "prefsfile.h" |
52 | #include "prefsmanager.h" |
||
53 | #include "scpaths.h" |
||
5243 | cbradney | 54 | #include "scribuscore.h" |
4507 | cbradney | 55 | #include "scribus.h" |
56 | #include "util.h" |
||
57 | |||
58 | using namespace std; |
||
59 | |||
60 | |||
61 | int callGS(const QStringList& args_in, const QString device) |
||
62 | { |
||
63 | QString cmd; |
||
10006 | cbradney | 64 | QStringList args; |
4507 | cbradney | 65 | PrefsManager* prefsManager = PrefsManager::instance(); |
66 | args.append( "-q" ); |
||
67 | args.append( "-dNOPAUSE" ); |
||
68 | args.append( "-dQUIET" ); |
||
69 | args.append( "-dPARANOIDSAFER" ); |
||
70 | args.append( "-dBATCH" ); |
||
71 | // Choose rendering device |
||
72 | if (!device.isEmpty()) |
||
73 | args.append( QString("-sDEVICE=%1").arg(device) ); // user specified device |
||
10866 | fschmid | 74 | else if (!ScCore->havePNGAlpha()) |
4507 | cbradney | 75 | args.append( "-sDEVICE=png16m" ); |
76 | else |
||
77 | args.append( "-sDEVICE=pngalpha" ); |
||
78 | // and antialiasing |
||
79 | if (prefsManager->appPrefs.gs_AntiAliasText) |
||
80 | args.append( "-dTextAlphaBits=4" ); |
||
81 | if (prefsManager->appPrefs.gs_AntiAliasGraphics) |
||
82 | args.append( "-dGraphicsAlphaBits=4" ); |
||
83 | |||
84 | // Add any extra font paths being used by Scribus to gs's font search path |
||
85 | PrefsContext *pc = PrefsManager::instance()->prefsFile->getContext("Fonts"); |
||
86 | PrefsTable *extraFonts = pc->getTable("ExtraFontDirs"); |
||
87 | const char sep = ScPaths::envPathSeparator; |
||
88 | if (extraFonts->getRowCount() >= 1) |
||
16576 | craig | 89 | cmd = QString("-sFONTPATH=%1").arg(QDir::toNativeSeparators(extraFonts->get(0,0))); |
4507 | cbradney | 90 | for (int i = 1; i < extraFonts->getRowCount(); ++i) |
16576 | craig | 91 | cmd += QString("%1%2").arg(sep).arg(QDir::toNativeSeparators(extraFonts->get(i,0))); |
4507 | cbradney | 92 | if( !cmd.isEmpty() ) |
93 | args.append( cmd ); |
||
94 | |||
95 | args += args_in; |
||
96 | args.append("-c"); |
||
97 | args.append("showpage"); |
||
10866 | fschmid | 98 | // qDebug(args.join(" ").toAscii()); |
10006 | cbradney | 99 | return System( getShortPathName(prefsManager->ghostscriptExecutable()), args ); |
4507 | cbradney | 100 | } |
101 | |||
102 | int callGS(const QString& args_in, const QString device) |
||
103 | { |
||
104 | PrefsManager* prefsManager=PrefsManager::instance(); |
||
105 | QString cmd1 = getShortPathName(prefsManager->ghostscriptExecutable()); |
||
106 | cmd1 += " -q -dNOPAUSE -dQUIET -dPARANOIDSAFER -dBATCH"; |
||
107 | // Choose rendering device |
||
108 | if (!device.isEmpty()) |
||
109 | // user specified device |
||
110 | cmd1 += " -sDEVICE="+device; |
||
10866 | fschmid | 111 | else if (!ScCore->havePNGAlpha()) |
4507 | cbradney | 112 | cmd1 += " -sDEVICE=png16m"; |
113 | else |
||
114 | cmd1 += " -sDEVICE=pngalpha"; |
||
115 | // and antialiasing |
||
116 | if (prefsManager->appPrefs.gs_AntiAliasText) |
||
117 | cmd1 += " -dTextAlphaBits=4"; |
||
118 | if (prefsManager->appPrefs.gs_AntiAliasGraphics) |
||
119 | cmd1 += " -dGraphicsAlphaBits=4"; |
||
120 | |||
121 | // Add any extra font paths being used by Scribus to gs's font search path |
||
122 | PrefsContext *pc = PrefsManager::instance()->prefsFile->getContext("Fonts"); |
||
123 | PrefsTable *extraFonts = pc->getTable("ExtraFontDirs"); |
||
124 | #ifndef _WIN32 |
||
125 | if (extraFonts->getRowCount() >= 1) |
||
126 | cmd1 += QString(" -sFONTPATH='%1'").arg(extraFonts->get(0,0)); |
||
127 | for (int i = 1; i < extraFonts->getRowCount(); ++i) |
||
128 | cmd1 += QString(":'%1'").arg(extraFonts->get(i,0)); |
||
129 | #else |
||
130 | if (extraFonts->getRowCount() >= 1) |
||
131 | cmd1 += QString(" -sFONTPATH=\"%1\"").arg(extraFonts->get(0,0)); |
||
132 | for (int i = 1; i < extraFonts->getRowCount(); ++i) |
||
133 | cmd1 += QString(";\"%1\"").arg(extraFonts->get(i,0)); |
||
134 | #endif |
||
135 | |||
136 | // then add any user specified args and run gs |
||
137 | cmd1 += " " + args_in + " -c showpage"; |
||
138 | // qDebug("Calling gs as: %s", cmd1.ascii()); |
||
10398 | cbradney | 139 | return system(cmd1.toLocal8Bit().constData()); |
4507 | cbradney | 140 | } |
141 | |||
5771 | jghali | 142 | int convertPS2PS(QString in, QString out, const QStringList& opts, int level) |
4507 | cbradney | 143 | { |
144 | PrefsManager* prefsManager=PrefsManager::instance(); |
||
145 | QStringList args; |
||
146 | args.append( "-q" ); |
||
147 | args.append( "-dQUIET" ); |
||
148 | args.append( "-dNOPAUSE" ); |
||
149 | args.append( "-dPARANOIDSAFER" ); |
||
150 | args.append( "-dBATCH" ); |
||
22624 | jghali | 151 | if (level == 2) |
5627 | jghali | 152 | { |
22624 | jghali | 153 | int gsVersion = 0; |
5627 | jghali | 154 | // ps2write cannot be detected with testGSAvailability() |
155 | // so determine availability according to gs version. |
||
22624 | jghali | 156 | getNumericGSVersion(gsVersion); |
157 | if (gsVersion >= 853) |
||
5627 | jghali | 158 | args.append( "-sDEVICE=ps2write" ); |
159 | else |
||
160 | { |
||
161 | args.append( "-sDEVICE=pswrite" ); |
||
162 | args.append( QString("-dLanguageLevel=%1").arg(level) ); |
||
22624 | jghali | 163 | } |
5627 | jghali | 164 | } |
165 | else |
||
166 | { |
||
167 | args.append( "-sDEVICE=pswrite" ); |
||
22624 | jghali | 168 | if (level <= 3) |
5627 | jghali | 169 | args.append( QString("-dLanguageLevel=%1").arg(level) ); |
170 | } |
||
4507 | cbradney | 171 | args += opts; |
16576 | craig | 172 | args.append( QString("-sOutputFile=%1").arg(QDir::toNativeSeparators(out)) ); |
173 | args.append( QDir::toNativeSeparators(in) ); |
||
10006 | cbradney | 174 | int ret = System( getShortPathName(prefsManager->ghostscriptExecutable()), args ); |
4507 | cbradney | 175 | return ret; |
176 | } |
||
177 | |||
12520 | fschmid | 178 | int convertPS2PDF(QString in, QString out, const QStringList& opts) |
179 | { |
||
180 | PrefsManager* prefsManager=PrefsManager::instance(); |
||
181 | QStringList args; |
||
182 | args.append( "-q" ); |
||
183 | args.append( "-dQUIET" ); |
||
184 | args.append( "-dNOPAUSE" ); |
||
185 | args.append( "-dPARANOIDSAFER" ); |
||
186 | args.append( "-dBATCH" ); |
||
187 | args.append( "-sDEVICE=pdfwrite" ); |
||
188 | args += opts; |
||
16576 | craig | 189 | args.append( QString("-sOutputFile=%1").arg(QDir::toNativeSeparators(out)) ); |
190 | args.append( QDir::toNativeSeparators(in) ); |
||
12520 | fschmid | 191 | int ret = System( getShortPathName(prefsManager->ghostscriptExecutable()), args ); |
192 | return ret; |
||
193 | } |
||
194 | |||
10006 | cbradney | 195 | bool testGSAvailability( void ) |
4507 | cbradney | 196 | { |
197 | QStringList args; |
||
198 | PrefsManager* prefsManager = PrefsManager::instance(); |
||
10006 | cbradney | 199 | return testGSAvailability(prefsManager->ghostscriptExecutable()); |
5764 | jghali | 200 | } |
201 | |||
10006 | cbradney | 202 | bool testGSAvailability( const QString& gsPath ) |
5764 | jghali | 203 | { |
204 | QStringList args; |
||
4507 | cbradney | 205 | args.append( "-h" ); |
10006 | cbradney | 206 | QProcess proc; |
207 | proc.start(getShortPathName(gsPath), args); |
||
10032 | jghali | 208 | if (!proc.waitForStarted(5000)) |
209 | return false; |
||
10006 | cbradney | 210 | proc.waitForFinished(5000); |
211 | return (proc.exitCode()==0); |
||
4507 | cbradney | 212 | } |
213 | |||
10006 | cbradney | 214 | bool testGSDeviceAvailability( const QString& device ) |
4507 | cbradney | 215 | { |
216 | QStringList args; |
||
217 | PrefsManager* prefsManager = PrefsManager::instance(); |
||
218 | args.append( QString("-sDEVICE=%1").arg( device ) ); |
||
219 | args.append( "-c" ); |
||
220 | args.append( "quit" ); |
||
10006 | cbradney | 221 | QProcess proc; |
222 | proc.start(getShortPathName(prefsManager->ghostscriptExecutable()), args); |
||
10032 | jghali | 223 | if (!proc.waitForStarted(5000)) |
224 | return false; |
||
10006 | cbradney | 225 | proc.waitForFinished(5000); |
226 | return (proc.exitCode()==0); |
||
4507 | cbradney | 227 | } |
228 | |||
229 | // Return the GhostScript version string, or QString::null if it couldn't be retrived. |
||
230 | QString getGSVersion() |
||
231 | { |
||
232 | QStringList args; |
||
10493 | fschmid | 233 | args.append(QString("--version").toLocal8Bit()); |
4507 | cbradney | 234 | QString gsExe = getShortPathName(PrefsManager::instance()->ghostscriptExecutable()); |
10006 | cbradney | 235 | QProcess proc; |
10493 | fschmid | 236 | proc.start(gsExe.toLocal8Bit(), args); |
10012 | cbradney | 237 | if (proc.waitForStarted(5000)) |
238 | while (!proc.waitForFinished(5000)) |
||
239 | qApp->processEvents(); |
||
10006 | cbradney | 240 | QString gsVer; |
241 | if (proc.exitStatus()==QProcess::NormalExit) |
||
242 | gsVer = proc.readAllStandardOutput(); |
||
4507 | cbradney | 243 | return gsVer; |
244 | } |
||
245 | |||
22624 | jghali | 246 | bool getNumericGSVersion(int &version) |
247 | { |
||
248 | int gsMajor(0), gsMinor(0); |
||
249 | version = 0; |
||
250 | if (getNumericGSVersion(gsMajor, gsMinor)) |
||
251 | { |
||
252 | version = 100 * gsMajor + gsMinor; |
||
253 | return true; |
||
254 | } |
||
255 | return false; |
||
256 | } |
||
257 | |||
4507 | cbradney | 258 | // Return the GhostScript major and minor version numbers. |
259 | bool getNumericGSVersion(int & major, int & minor) |
||
260 | { |
||
261 | QString gs_ver_string(getGSVersion()); |
||
10032 | jghali | 262 | return getNumericGSVersion(gs_ver_string, major, minor); |
263 | } |
||
264 | |||
265 | bool getNumericGSVersion(const QString& ver, int& major, int& minor) |
||
266 | { |
||
4507 | cbradney | 267 | // gs's version string is of the form MAJOR.MINOR, so look for the . |
268 | // then convert to numbers. 7.07 will become (7,7) for example. |
||
269 | bool success = false; |
||
10032 | jghali | 270 | major = ver.section('.', 0, 0).toInt(&success); |
4507 | cbradney | 271 | if (!success) |
272 | return false; |
||
10032 | jghali | 273 | minor = ver.section('.', 1, 1).toInt(&success); |
4507 | cbradney | 274 | if (!success) |
275 | return false; |
||
276 | return true; |
||
277 | } |
||
278 | |||
279 | QString getGSDefaultExeName(void) |
||
280 | { |
||
13052 | cbradney | 281 | QString gsName("gs"); |
4507 | cbradney | 282 | #if defined _WIN32 |
283 | // Set gsName to its default value |
||
284 | gsName = "gswin32c.exe"; |
||
285 | |||
17762 | jghali | 286 | // Test is we are running a 64bit version of WINDOWS |
287 | bool isWindows64 = false; |
||
288 | wchar_t* procArch = _wgetenv(L"PROCESSOR_ARCHITECTURE"); |
||
289 | if (procArch) |
||
290 | { |
||
291 | isWindows64 |= (wcscmp(procArch, L"AMD64") == 0); |
||
292 | isWindows64 |= (wcscmp(procArch, L"IA64") == 0); |
||
293 | } |
||
294 | wchar_t* procArchWow64 = _wgetenv(L"PROCESSOR_ARCHITEW6432"); |
||
295 | if (procArchWow64) isWindows64 = true; |
||
4507 | cbradney | 296 | |
17762 | jghali | 297 | // Search for Ghostsscript executable in native registry |
298 | QMap<int, QString> gsVersions; |
||
299 | gsVersions.unite( getGSExePaths("SOFTWARE\\GPL Ghostscript") ); |
||
300 | gsVersions.unite( getGSExePaths("SOFTWARE\\AFPL Ghostscript") ); |
||
301 | |||
302 | // If running on Windows 64bit, search alternate registry view, |
||
303 | // ie 32bit registry if process is 64bit, 64bit registry if process is 32bit |
||
304 | if (isWindows64) |
||
305 | { |
||
306 | gsVersions.unite( getGSExePaths("SOFTWARE\\GPL Ghostscript", true) ); |
||
307 | gsVersions.unite( getGSExePaths("SOFTWARE\\AFPL Ghostscript", true) ); |
||
308 | } |
||
309 | |||
10032 | jghali | 310 | if (gsVersions.isEmpty()) |
4507 | cbradney | 311 | return gsName; |
312 | |||
10032 | jghali | 313 | int currentVer = 0; |
314 | QString gsPath; |
||
315 | QMap<int, QString>::ConstIterator it, itEnd = gsVersions.constEnd(); |
||
316 | for (it = gsVersions.constBegin(); it != itEnd; ++it) |
||
317 | { |
||
318 | int version = it.key(); |
||
319 | if (version > currentVer) |
||
320 | { |
||
10723 | jghali | 321 | gsPath = it.value(); |
10032 | jghali | 322 | QFileInfo fInfo(gsPath); |
323 | if (fInfo.exists()) |
||
324 | { |
||
325 | gsName = gsPath; |
||
326 | currentVer = version; |
||
327 | } |
||
328 | } |
||
329 | } |
||
4507 | cbradney | 330 | #endif |
13052 | cbradney | 331 | #if defined Q_OS_MAC |
332 | QStringList gsPaths; |
||
13798 | cbradney | 333 | gsPaths << "/usr/bin/gs" << "/usr/local/bin/gs" << "/opt/local/bin/gs" << "/sw/bin/gs"; |
13052 | cbradney | 334 | for (int i = 0; i < gsPaths.size(); ++i) |
335 | { |
||
336 | QFileInfo fInfo(gsPaths.at(i)); |
||
337 | if (fInfo.exists()) |
||
338 | { |
||
339 | gsName = gsPaths.at(i); |
||
340 | break; |
||
341 | } |
||
342 | } |
||
343 | #endif |
||
4507 | cbradney | 344 | return gsName; |
345 | } |
||
346 | |||
17762 | jghali | 347 | QMap<int, QString> SCRIBUS_API getGSExePaths(const QString& regKey, bool alternateView) |
10032 | jghali | 348 | { |
349 | QMap<int, QString> gsVersions; |
||
350 | #if defined _WIN32 |
||
351 | // Try to locate GhostScript thanks to the registry |
||
23782 | jghali | 352 | DWORD size, regVersionSize; |
10032 | jghali | 353 | HKEY hKey1, hKey2; |
354 | DWORD regType = REG_SZ; |
||
17762 | jghali | 355 | REGSAM flags = KEY_READ; |
23782 | jghali | 356 | WCHAR regVersion[MAX_PATH] = {}; |
357 | WCHAR regPath[MAX_PATH] = {}; |
||
358 | WCHAR gsPath[MAX_PATH] = {}; |
||
17762 | jghali | 359 | QString gsVersion, gsExeName, gsName; |
10032 | jghali | 360 | |
17762 | jghali | 361 | bool isWin64Api = false; |
362 | #if defined(_WIN64) |
||
363 | isWin64Api = true; |
||
364 | #endif |
||
365 | |||
366 | gsExeName = isWin64Api ? "gswin64c.exe" : "gswin32c.exe"; |
||
367 | if (alternateView) |
||
10032 | jghali | 368 | { |
17762 | jghali | 369 | gsExeName = isWin64Api ? "gswin32c.exe" : "gswin64c.exe"; |
370 | flags |= (isWin64Api ? KEY_WOW64_32KEY : KEY_WOW64_64KEY); |
||
371 | } |
||
372 | |||
373 | if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, (LPCWSTR) regKey.utf16(), 0, flags, &hKey1) == ERROR_SUCCESS) |
||
374 | { |
||
24757 | jghali | 375 | regVersionSize = sizeof(regVersion) / sizeof(WCHAR); |
10032 | jghali | 376 | DWORD keyIndex = 0; |
23782 | jghali | 377 | while (RegEnumKeyExW(hKey1, keyIndex, regVersion, ®VersionSize, NULL, NULL, NULL, NULL) == ERROR_SUCCESS) |
10032 | jghali | 378 | { |
379 | int gsNumericVer, gsMajor, gsMinor; |
||
10304 | jghali | 380 | wcscpy(regPath, (const wchar_t*) regKey.utf16()); |
381 | wcscat(regPath, L"\\"); |
||
382 | wcscat(regPath, regVersion); |
||
17762 | jghali | 383 | if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, regPath, 0, flags, &hKey2) == ERROR_SUCCESS) |
10032 | jghali | 384 | { |
23782 | jghali | 385 | size = sizeof(gsPath) - 2; |
10304 | jghali | 386 | if (RegQueryValueExW(hKey2, L"GS_DLL", 0, ®Type, (LPBYTE) gsPath, &size) == ERROR_SUCCESS) |
10032 | jghali | 387 | { |
388 | // We now have GhostScript dll path, but we want gswin32c.exe |
||
389 | // Normally gswin32c.exe and gsdll.dll are in the same directory |
||
22624 | jghali | 390 | if (getNumericGSVersion(QString::fromUtf16((const ushort*) regVersion), gsMajor, gsMinor)) |
10032 | jghali | 391 | { |
22624 | jghali | 392 | gsNumericVer = gsMajor * 100 + gsMinor; |
10304 | jghali | 393 | gsName = QString::fromUtf16((const ushort*) gsPath); |
10427 | cbradney | 394 | size = gsName.lastIndexOf("\\"); |
10032 | jghali | 395 | if (size > 0) |
396 | { |
||
397 | gsName = gsName.left(size + 1); |
||
17762 | jghali | 398 | gsName += gsExeName; |
10032 | jghali | 399 | gsName.replace("\\", "/"); |
400 | gsVersions.insert(gsNumericVer, gsName); |
||
401 | } |
||
402 | } |
||
403 | } |
||
404 | RegCloseKey(hKey2); |
||
405 | } |
||
24757 | jghali | 406 | regVersionSize = sizeof(regVersion) / sizeof(WCHAR); |
10032 | jghali | 407 | keyIndex++; |
408 | } |
||
409 | RegCloseKey(hKey1); |
||
410 | } |
||
411 | #else |
||
412 | int gsNumericVer, gsMajor, gsMinor; |
||
413 | PrefsManager* prefsManager=PrefsManager::instance(); |
||
414 | if (getNumericGSVersion(gsMajor, gsMinor)) |
||
415 | { |
||
22624 | jghali | 416 | gsNumericVer = gsMajor * 100 + gsMinor; |
10032 | jghali | 417 | gsVersions.insert(gsNumericVer, prefsManager->ghostscriptExecutable()); |
418 | } |
||
419 | #endif |
||
420 | return gsVersions; |
||
421 | } |
||
422 | |||
4507 | cbradney | 423 | QPixmap LoadPDF(QString fn, int Page, int Size, int *w, int *h) |
424 | { |
||
425 | QString tmp, cmd1, cmd2; |
||
16576 | craig | 426 | QString pdfFile = QDir::toNativeSeparators(fn); |
427 | QString tmpFile = QDir::toNativeSeparators(ScPaths::getTempFileDir() + "sc.png"); |
||
4507 | cbradney | 428 | QPixmap pm; |
429 | int ret = -1; |
||
430 | tmp.setNum(Page); |
||
431 | QStringList args; |
||
432 | args.append("-r72"); |
||
5230 | fschmid | 433 | // args.append("-sOutputFile=\""+tmpFile+"\""); |
434 | args.append("-sOutputFile="+tmpFile); |
||
4507 | cbradney | 435 | args.append("-dFirstPage="+tmp); |
436 | args.append("-dLastPage="+tmp); |
||
5230 | fschmid | 437 | // args.append("\""+pdfFile+"\""); |
438 | args.append(pdfFile); |
||
4507 | cbradney | 439 | ret = callGS(args); |
440 | if (ret == 0) |
||
441 | { |
||
442 | QImage image; |
||
443 | image.load(tmpFile); |
||
10592 | fschmid | 444 | QFile::remove(tmpFile); |
4507 | cbradney | 445 | QImage im2; |
446 | *h = image.height(); |
||
447 | *w = image.width(); |
||
448 | double sx = image.width() / static_cast<double>(Size); |
||
449 | double sy = image.height() / static_cast<double>(Size); |
||
450 | double t = (sy < sx ? sx : sy); |
||
10398 | cbradney | 451 | im2 = image.scaled(static_cast<int>(image.width() / t), static_cast<int>(image.height() / t), Qt::IgnoreAspectRatio, Qt::SmoothTransformation); |
10401 | cbradney | 452 | pm=QPixmap::fromImage(im2); |
4507 | cbradney | 453 | QPainter p; |
454 | p.begin(&pm); |
||
455 | p.setBrush(Qt::NoBrush); |
||
456 | p.setPen(Qt::black); |
||
457 | p.drawRect(0, 0, pm.width(), pm.height()); |
||
458 | p.end(); |
||
459 | im2.detach(); |
||
460 | } |
||
461 | return pm; |
||
462 | } |
||
463 | |||
10032 | jghali | 464 |