1 | /**************************************************************************** |
2 | ** |
3 | ** Copyright (C) 2016 The Qt Company Ltd. |
4 | ** Contact: https://www.qt.io/licensing/ |
5 | ** |
6 | ** This file is part of the test suite of the Qt Toolkit. |
7 | ** |
8 | ** $QT_BEGIN_LICENSE:GPL-EXCEPT$ |
9 | ** Commercial License Usage |
10 | ** Licensees holding valid commercial Qt licenses may use this file in |
11 | ** accordance with the commercial license agreement provided with the |
12 | ** Software or, alternatively, in accordance with the terms contained in |
13 | ** a written agreement between you and The Qt Company. For licensing terms |
14 | ** and conditions see https://www.qt.io/terms-conditions. For further |
15 | ** information use the contact form at https://www.qt.io/contact-us. |
16 | ** |
17 | ** GNU General Public License Usage |
18 | ** Alternatively, this file may be used under the terms of the GNU |
19 | ** General Public License version 3 as published by the Free Software |
20 | ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT |
21 | ** included in the packaging of this file. Please review the following |
22 | ** information to ensure the GNU General Public License requirements will |
23 | ** be met: https://www.gnu.org/licenses/gpl-3.0.html. |
24 | ** |
25 | ** $QT_END_LICENSE$ |
26 | ** |
27 | ****************************************************************************/ |
28 | |
29 | #include <QtTest/QtTest> |
30 | |
31 | #ifdef Q_OS_UNIX |
32 | #include <locale.h> |
33 | #endif |
34 | |
35 | #include <QBuffer> |
36 | #include <QByteArray> |
37 | #include <QDebug> |
38 | #include <QElapsedTimer> |
39 | #include <QFile> |
40 | #include <QTcpSocket> |
41 | #include <QTemporaryDir> |
42 | #include <QTextStream> |
43 | #include <QTextCodec> |
44 | #if QT_CONFIG(process) |
45 | # include <QProcess> |
46 | #endif |
47 | #include "../../../network-settings.h" |
48 | #include "emulationdetector.h" |
49 | |
50 | QT_BEGIN_NAMESPACE |
51 | template<> struct QMetaTypeId<QIODevice::OpenModeFlag> |
52 | { enum { Defined = 1 }; static inline int qt_metatype_id() { return QMetaType::Int; } }; |
53 | QT_END_NAMESPACE |
54 | |
55 | class tst_QTextStream : public QObject |
56 | { |
57 | Q_OBJECT |
58 | |
59 | public: |
60 | tst_QTextStream(); |
61 | |
62 | public slots: |
63 | void initTestCase(); |
64 | void cleanup(); |
65 | void cleanupTestCase(); |
66 | |
67 | private slots: |
68 | void getSetCheck(); |
69 | void construction(); |
70 | |
71 | // lines |
72 | void readLineFromDevice_data(); |
73 | void readLineFromDevice(); |
74 | void readLineFromString_data(); |
75 | void readLineFromString(); |
76 | void readLineFromTextDevice_data(); |
77 | void readLineFromTextDevice(); |
78 | void readLineUntilNull(); |
79 | void readLineMaxlen_data(); |
80 | void readLineMaxlen(); |
81 | void readLinesFromBufferCRCR(); |
82 | void readLineInto(); |
83 | |
84 | // all |
85 | void readAllFromDevice_data(); |
86 | void readAllFromDevice(); |
87 | void readAllFromString_data(); |
88 | void readAllFromString(); |
89 | void readLineFromStringThenChangeString(); |
90 | |
91 | // device tests |
92 | void setDevice(); |
93 | |
94 | // char operators |
95 | void QChar_operators_FromDevice_data(); |
96 | void QChar_operators_FromDevice(); |
97 | void char_operators_FromDevice_data(); |
98 | void char_operators_FromDevice(); |
99 | |
100 | // natural number read operator |
101 | void signedShort_read_operator_FromDevice_data(); |
102 | void signedShort_read_operator_FromDevice(); |
103 | void unsignedShort_read_operator_FromDevice_data(); |
104 | void unsignedShort_read_operator_FromDevice(); |
105 | void signedInt_read_operator_FromDevice_data(); |
106 | void signedInt_read_operator_FromDevice(); |
107 | void unsignedInt_read_operator_FromDevice_data(); |
108 | void unsignedInt_read_operator_FromDevice(); |
109 | void qlonglong_read_operator_FromDevice_data(); |
110 | void qlonglong_read_operator_FromDevice(); |
111 | void qulonglong_read_operator_FromDevice_data(); |
112 | void qulonglong_read_operator_FromDevice(); |
113 | |
114 | // natural number write operator |
115 | void signedShort_write_operator_ToDevice_data(); |
116 | void signedShort_write_operator_ToDevice(); |
117 | void unsignedShort_write_operator_ToDevice_data(); |
118 | void unsignedShort_write_operator_ToDevice(); |
119 | void signedInt_write_operator_ToDevice_data(); |
120 | void signedInt_write_operator_ToDevice(); |
121 | void unsignedInt_write_operator_ToDevice_data(); |
122 | void unsignedInt_write_operator_ToDevice(); |
123 | void qlonglong_write_operator_ToDevice_data(); |
124 | void qlonglong_write_operator_ToDevice(); |
125 | void qulonglong_write_operator_ToDevice_data(); |
126 | void qulonglong_write_operator_ToDevice(); |
127 | |
128 | void int_read_with_locale_data(); |
129 | void int_read_with_locale(); |
130 | |
131 | void int_write_with_locale_data(); |
132 | void int_write_with_locale(); |
133 | |
134 | // real number read operator |
135 | void float_read_operator_FromDevice_data(); |
136 | void float_read_operator_FromDevice(); |
137 | void double_read_operator_FromDevice_data(); |
138 | void double_read_operator_FromDevice(); |
139 | |
140 | // real number write operator |
141 | void float_write_operator_ToDevice_data(); |
142 | void float_write_operator_ToDevice(); |
143 | void double_write_operator_ToDevice_data(); |
144 | void double_write_operator_ToDevice(); |
145 | |
146 | void double_write_with_flags_data(); |
147 | void double_write_with_flags(); |
148 | |
149 | void double_write_with_precision_data(); |
150 | void double_write_with_precision(); |
151 | |
152 | // text read operators |
153 | void charPtr_read_operator_FromDevice_data(); |
154 | void charPtr_read_operator_FromDevice(); |
155 | void stringRef_read_operator_FromDevice_data(); |
156 | void stringRef_read_operator_FromDevice(); |
157 | void byteArray_read_operator_FromDevice_data(); |
158 | void byteArray_read_operator_FromDevice(); |
159 | |
160 | // text write operators |
161 | void string_write_operator_ToDevice_data(); |
162 | void string_write_operator_ToDevice(); |
163 | void latin1String_write_operator_ToDevice(); |
164 | void stringref_write_operator_ToDevice(); |
165 | void stringview_write_operator_ToDevice(); |
166 | |
167 | // other |
168 | void skipWhiteSpace_data(); |
169 | void skipWhiteSpace(); |
170 | void lineCount_data(); |
171 | void lineCount(); |
172 | void performance(); |
173 | void hexTest_data(); |
174 | void hexTest(); |
175 | void binTest_data(); |
176 | void binTest(); |
177 | void octTest_data(); |
178 | void octTest(); |
179 | void zeroTermination(); |
180 | void ws_manipulator(); |
181 | void stillOpenWhenAtEnd(); |
182 | void readNewlines_data(); |
183 | void readNewlines(); |
184 | void seek(); |
185 | void pos(); |
186 | void pos2(); |
187 | void pos3LargeFile(); |
188 | void readStdin(); |
189 | void readAllFromStdin(); |
190 | void readLineFromStdin(); |
191 | void read(); |
192 | void qbool(); |
193 | void forcePoint(); |
194 | void forceSign(); |
195 | void read0d0d0a(); |
196 | void numeralCase_data(); |
197 | void numeralCase(); |
198 | void nanInf(); |
199 | void utf8IncompleteAtBufferBoundary_data(); |
200 | void utf8IncompleteAtBufferBoundary(); |
201 | void writeSeekWriteNoBOM(); |
202 | |
203 | // status |
204 | void status_real_read_data(); |
205 | void status_real_read(); |
206 | void status_integer_read(); |
207 | void status_word_read(); |
208 | void status_write_error(); |
209 | |
210 | // use case tests |
211 | void useCase1(); |
212 | void useCase2(); |
213 | |
214 | // manipulators |
215 | void manipulators_data(); |
216 | void manipulators(); |
217 | |
218 | // UTF-16 BOM (Byte Order Mark) |
219 | void generateBOM(); |
220 | void readBomSeekBackReadBomAgain(); |
221 | |
222 | // Regression tests for old bugs |
223 | void alignAccountingStyle(); |
224 | void setCodec(); |
225 | |
226 | void textModeOnEmptyRead(); |
227 | |
228 | private: |
229 | void generateLineData(bool for_QString); |
230 | void generateAllData(bool for_QString); |
231 | void generateOperatorCharData(bool for_QString); |
232 | void generateNaturalNumbersData(bool for_QString); |
233 | void generateRealNumbersData(bool for_QString); |
234 | void generateStringData(bool for_QString); |
235 | void generateRealNumbersDataWrite(); |
236 | |
237 | QTemporaryDir tempDir; |
238 | QString testFileName; |
239 | #ifdef BUILTIN_TESTDATA |
240 | QSharedPointer<QTemporaryDir> m_dataDir; |
241 | #endif |
242 | const QString m_rfc3261FilePath; |
243 | const QString m_shiftJisFilePath; |
244 | }; |
245 | |
246 | void runOnExit() |
247 | { |
248 | QByteArray buffer; |
249 | QTextStream(&buffer) << "This will try to use QTextCodec::codecForLocale" << Qt::endl; |
250 | } |
251 | Q_DESTRUCTOR_FUNCTION(runOnExit) |
252 | |
253 | tst_QTextStream::tst_QTextStream() |
254 | : tempDir(QDir::tempPath() + "/tst_qtextstream.XXXXXX" ) |
255 | , m_rfc3261FilePath(QFINDTESTDATA("rfc3261.txt" )) |
256 | , m_shiftJisFilePath(QFINDTESTDATA("shift-jis.txt" )) |
257 | { |
258 | } |
259 | |
260 | void tst_QTextStream::initTestCase() |
261 | { |
262 | QVERIFY2(tempDir.isValid(), qPrintable(tempDir.errorString())); |
263 | QVERIFY(!m_rfc3261FilePath.isEmpty()); |
264 | QVERIFY(!m_shiftJisFilePath.isEmpty()); |
265 | |
266 | testFileName = tempDir.path() + "/testfile" ; |
267 | |
268 | #ifdef BUILTIN_TESTDATA |
269 | m_dataDir = QEXTRACTTESTDATA("/" ); |
270 | QVERIFY2(QDir::setCurrent(m_dataDir->path()), qPrintable("Could not chdir to " + m_dataDir->path())); |
271 | #else |
272 | // chdir into the testdata dir and refer to our helper apps with relative paths |
273 | QString testdata_dir = QFileInfo(QFINDTESTDATA("stdinProcess" )).absolutePath(); |
274 | QVERIFY2(QDir::setCurrent(testdata_dir), qPrintable("Could not chdir to " + testdata_dir)); |
275 | #endif |
276 | } |
277 | |
278 | // Testing get/set functions |
279 | void tst_QTextStream::getSetCheck() |
280 | { |
281 | // Initialize codecs |
282 | QTextStream obj1; |
283 | // QTextCodec * QTextStream::codec() |
284 | // void QTextStream::setCodec(QTextCodec *) |
285 | QTextCodec *var1 = QTextCodec::codecForName(name: "en" ); |
286 | obj1.setCodec(var1); |
287 | QCOMPARE(var1, obj1.codec()); |
288 | obj1.setCodec((QTextCodec *)0); |
289 | QCOMPARE((QTextCodec *)0, obj1.codec()); |
290 | |
291 | // bool QTextStream::autoDetectUnicode() |
292 | // void QTextStream::setAutoDetectUnicode(bool) |
293 | obj1.setAutoDetectUnicode(false); |
294 | QCOMPARE(false, obj1.autoDetectUnicode()); |
295 | obj1.setAutoDetectUnicode(true); |
296 | QCOMPARE(true, obj1.autoDetectUnicode()); |
297 | |
298 | // bool QTextStream::generateByteOrderMark() |
299 | // void QTextStream::setGenerateByteOrderMark(bool) |
300 | obj1.setGenerateByteOrderMark(false); |
301 | QCOMPARE(false, obj1.generateByteOrderMark()); |
302 | obj1.setGenerateByteOrderMark(true); |
303 | QCOMPARE(true, obj1.generateByteOrderMark()); |
304 | |
305 | // QIODevice * QTextStream::device() |
306 | // void QTextStream::setDevice(QIODevice *) |
307 | QFile *var4 = new QFile; |
308 | obj1.setDevice(var4); |
309 | QCOMPARE(static_cast<QIODevice *>(var4), obj1.device()); |
310 | obj1.setDevice((QIODevice *)0); |
311 | QCOMPARE((QIODevice *)0, obj1.device()); |
312 | delete var4; |
313 | |
314 | // Status QTextStream::status() |
315 | // void QTextStream::setStatus(Status) |
316 | obj1.setStatus(QTextStream::Status(QTextStream::Ok)); |
317 | QCOMPARE(QTextStream::Status(QTextStream::Ok), obj1.status()); |
318 | obj1.setStatus(QTextStream::Status(QTextStream::ReadPastEnd)); |
319 | QCOMPARE(QTextStream::Status(QTextStream::ReadPastEnd), obj1.status()); |
320 | obj1.resetStatus(); |
321 | obj1.setStatus(QTextStream::Status(QTextStream::ReadCorruptData)); |
322 | QCOMPARE(QTextStream::Status(QTextStream::ReadCorruptData), obj1.status()); |
323 | |
324 | // FieldAlignment QTextStream::fieldAlignment() |
325 | // void QTextStream::setFieldAlignment(FieldAlignment) |
326 | obj1.setFieldAlignment(QTextStream::FieldAlignment(QTextStream::AlignLeft)); |
327 | QCOMPARE(QTextStream::FieldAlignment(QTextStream::AlignLeft), obj1.fieldAlignment()); |
328 | obj1.setFieldAlignment(QTextStream::FieldAlignment(QTextStream::AlignRight)); |
329 | QCOMPARE(QTextStream::FieldAlignment(QTextStream::AlignRight), obj1.fieldAlignment()); |
330 | obj1.setFieldAlignment(QTextStream::FieldAlignment(QTextStream::AlignCenter)); |
331 | QCOMPARE(QTextStream::FieldAlignment(QTextStream::AlignCenter), obj1.fieldAlignment()); |
332 | obj1.setFieldAlignment(QTextStream::FieldAlignment(QTextStream::AlignAccountingStyle)); |
333 | QCOMPARE(QTextStream::FieldAlignment(QTextStream::AlignAccountingStyle), obj1.fieldAlignment()); |
334 | |
335 | // QChar QTextStream::padChar() |
336 | // void QTextStream::setPadChar(QChar) |
337 | QChar var7 = 'Q'; |
338 | obj1.setPadChar(var7); |
339 | QCOMPARE(var7, obj1.padChar()); |
340 | obj1.setPadChar(QChar()); |
341 | QCOMPARE(QChar(), obj1.padChar()); |
342 | |
343 | // int QTextStream::fieldWidth() |
344 | // void QTextStream::setFieldWidth(int) |
345 | obj1.setFieldWidth(0); |
346 | QCOMPARE(0, obj1.fieldWidth()); |
347 | obj1.setFieldWidth(INT_MIN); |
348 | QCOMPARE(INT_MIN, obj1.fieldWidth()); |
349 | obj1.setFieldWidth(INT_MAX); |
350 | QCOMPARE(INT_MAX, obj1.fieldWidth()); |
351 | |
352 | // NumberFlags QTextStream::numberFlags() |
353 | // void QTextStream::setNumberFlags(NumberFlags) |
354 | obj1.setNumberFlags(QTextStream::NumberFlags(QTextStream::ShowBase)); |
355 | QCOMPARE(QTextStream::NumberFlags(QTextStream::ShowBase), obj1.numberFlags()); |
356 | obj1.setNumberFlags(QTextStream::NumberFlags(QTextStream::ForcePoint)); |
357 | QCOMPARE(QTextStream::NumberFlags(QTextStream::ForcePoint), obj1.numberFlags()); |
358 | obj1.setNumberFlags(QTextStream::NumberFlags(QTextStream::ForceSign)); |
359 | QCOMPARE(QTextStream::NumberFlags(QTextStream::ForceSign), obj1.numberFlags()); |
360 | obj1.setNumberFlags(QTextStream::NumberFlags(QTextStream::UppercaseBase)); |
361 | QCOMPARE(QTextStream::NumberFlags(QTextStream::UppercaseBase), obj1.numberFlags()); |
362 | obj1.setNumberFlags(QTextStream::NumberFlags(QTextStream::UppercaseDigits)); |
363 | QCOMPARE(QTextStream::NumberFlags(QTextStream::UppercaseDigits), obj1.numberFlags()); |
364 | |
365 | // int QTextStream::integerBase() |
366 | // void QTextStream::setIntegerBase(int) |
367 | obj1.setIntegerBase(0); |
368 | QCOMPARE(0, obj1.integerBase()); |
369 | obj1.setIntegerBase(INT_MIN); |
370 | QCOMPARE(INT_MIN, obj1.integerBase()); |
371 | obj1.setIntegerBase(INT_MAX); |
372 | QCOMPARE(INT_MAX, obj1.integerBase()); |
373 | |
374 | // RealNumberNotation QTextStream::realNumberNotation() |
375 | // void QTextStream::setRealNumberNotation(RealNumberNotation) |
376 | obj1.setRealNumberNotation(QTextStream::RealNumberNotation(QTextStream::SmartNotation)); |
377 | QCOMPARE(QTextStream::RealNumberNotation(QTextStream::SmartNotation), obj1.realNumberNotation()); |
378 | obj1.setRealNumberNotation(QTextStream::RealNumberNotation(QTextStream::FixedNotation)); |
379 | QCOMPARE(QTextStream::RealNumberNotation(QTextStream::FixedNotation), obj1.realNumberNotation()); |
380 | obj1.setRealNumberNotation(QTextStream::RealNumberNotation(QTextStream::ScientificNotation)); |
381 | QCOMPARE(QTextStream::RealNumberNotation(QTextStream::ScientificNotation), obj1.realNumberNotation()); |
382 | |
383 | // int QTextStream::realNumberPrecision() |
384 | // void QTextStream::setRealNumberPrecision(int) |
385 | obj1.setRealNumberPrecision(0); |
386 | QCOMPARE(0, obj1.realNumberPrecision()); |
387 | obj1.setRealNumberPrecision(INT_MIN); |
388 | QCOMPARE(6, obj1.realNumberPrecision()); // Setting a negative precision reverts it to the default value (6). |
389 | obj1.setRealNumberPrecision(INT_MAX); |
390 | QCOMPARE(INT_MAX, obj1.realNumberPrecision()); |
391 | } |
392 | |
393 | void tst_QTextStream::cleanup() |
394 | { |
395 | QCoreApplication::instance()->processEvents(); |
396 | } |
397 | |
398 | void tst_QTextStream::cleanupTestCase() |
399 | { |
400 | #ifdef BUILTIN_TESTDATA |
401 | QDir::setCurrent(QCoreApplication::applicationDirPath()); |
402 | #endif |
403 | } |
404 | |
405 | // ------------------------------------------------------------------------------ |
406 | void tst_QTextStream::construction() |
407 | { |
408 | QTextStream stream; |
409 | QCOMPARE(stream.codec(), QTextCodec::codecForLocale()); |
410 | QCOMPARE(stream.device(), static_cast<QIODevice *>(0)); |
411 | QCOMPARE(stream.string(), static_cast<QString *>(0)); |
412 | |
413 | QTest::ignoreMessage(type: QtWarningMsg, message: "QTextStream: No device" ); |
414 | QVERIFY(stream.atEnd()); |
415 | |
416 | QTest::ignoreMessage(type: QtWarningMsg, message: "QTextStream: No device" ); |
417 | QCOMPARE(stream.readAll(), QString()); |
418 | |
419 | } |
420 | |
421 | void tst_QTextStream::generateLineData(bool for_QString) |
422 | { |
423 | QTest::addColumn<QByteArray>(name: "data" ); |
424 | QTest::addColumn<QStringList>(name: "lines" ); |
425 | |
426 | // latin-1 |
427 | QTest::newRow(dataTag: "emptyer" ) << QByteArray() << QStringList(); |
428 | QTest::newRow(dataTag: "lf" ) << QByteArray("\n" ) << (QStringList() << "" ); |
429 | QTest::newRow(dataTag: "crlf" ) << QByteArray("\r\n" ) << (QStringList() << "" ); |
430 | QTest::newRow(dataTag: "oneline/nothing" ) << QByteArray("ole" ) << (QStringList() << "ole" ); |
431 | QTest::newRow(dataTag: "oneline/lf" ) << QByteArray("ole\n" ) << (QStringList() << "ole" ); |
432 | QTest::newRow(dataTag: "oneline/crlf" ) << QByteArray("ole\r\n" ) << (QStringList() << "ole" ); |
433 | QTest::newRow(dataTag: "twolines/lf/lf" ) << QByteArray("ole\ndole\n" ) << (QStringList() << "ole" << "dole" ); |
434 | QTest::newRow(dataTag: "twolines/crlf/crlf" ) << QByteArray("ole\r\ndole\r\n" ) << (QStringList() << "ole" << "dole" ); |
435 | QTest::newRow(dataTag: "twolines/lf/crlf" ) << QByteArray("ole\ndole\r\n" ) << (QStringList() << "ole" << "dole" ); |
436 | QTest::newRow(dataTag: "twolines/lf/nothing" ) << QByteArray("ole\ndole" ) << (QStringList() << "ole" << "dole" ); |
437 | QTest::newRow(dataTag: "twolines/crlf/nothing" ) << QByteArray("ole\r\ndole" ) << (QStringList() << "ole" << "dole" ); |
438 | QTest::newRow(dataTag: "threelines/lf/lf/lf" ) << QByteArray("ole\ndole\ndoffen\n" ) << (QStringList() << "ole" << "dole" << "doffen" ); |
439 | QTest::newRow(dataTag: "threelines/crlf/crlf/crlf" ) << QByteArray("ole\r\ndole\r\ndoffen\r\n" ) << (QStringList() << "ole" << "dole" << "doffen" ); |
440 | QTest::newRow(dataTag: "threelines/crlf/crlf/nothing" ) << QByteArray("ole\r\ndole\r\ndoffen" ) << (QStringList() << "ole" << "dole" << "doffen" ); |
441 | |
442 | if (!for_QString) { |
443 | // utf-8 |
444 | QTest::newRow(dataTag: "utf8/twolines" ) |
445 | << QByteArray("\xef\xbb\xbf" |
446 | "\x66\x67\x65\x0a" |
447 | "\x66\x67\x65\x0a" , 11) |
448 | << (QStringList() << "fge" << "fge" ); |
449 | |
450 | // utf-16 |
451 | // one line |
452 | QTest::newRow(dataTag: "utf16-BE/nothing" ) |
453 | << QByteArray("\xfe\xff" |
454 | "\x00\xe5\x00\x67\x00\x65" , 8) << (QStringList() << QLatin1String("\345ge" )); |
455 | QTest::newRow(dataTag: "utf16-LE/nothing" ) |
456 | << QByteArray("\xff\xfe" |
457 | "\xe5\x00\x67\x00\x65\x00" , 8) << (QStringList() << QLatin1String("\345ge" )); |
458 | QTest::newRow(dataTag: "utf16-BE/lf" ) |
459 | << QByteArray("\xfe\xff" |
460 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 10) << (QStringList() << QLatin1String("\345ge" )); |
461 | QTest::newRow(dataTag: "utf16-LE/lf" ) |
462 | << QByteArray("\xff\xfe" |
463 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 10) << (QStringList() << QLatin1String("\345ge" )); |
464 | |
465 | // two lines |
466 | QTest::newRow(dataTag: "utf16-BE/twolines" ) |
467 | << QByteArray("\xfe\xff" |
468 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
469 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 18) |
470 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
471 | QTest::newRow(dataTag: "utf16-LE/twolines" ) |
472 | << QByteArray("\xff\xfe" |
473 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
474 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 18) |
475 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
476 | |
477 | // three lines |
478 | QTest::newRow(dataTag: "utf16-BE/threelines" ) |
479 | << QByteArray("\xfe\xff" |
480 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
481 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
482 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 26) |
483 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
484 | QTest::newRow(dataTag: "utf16-LE/threelines" ) |
485 | << QByteArray("\xff\xfe" |
486 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
487 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
488 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 26) |
489 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
490 | |
491 | // utf-32 |
492 | QTest::newRow(dataTag: "utf32-BE/twolines" ) |
493 | << QByteArray("\x00\x00\xfe\xff" |
494 | "\x00\x00\x00\xe5\x00\x00\x00\x67\x00\x00\x00\x65\x00\x00\x00\x0a" |
495 | "\x00\x00\x00\xe5\x00\x00\x00\x67\x00\x00\x00\x65\x00\x00\x00\x0a" , 36) |
496 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
497 | QTest::newRow(dataTag: "utf32-LE/twolines" ) |
498 | << QByteArray("\xff\xfe\x00\x00" |
499 | "\xe5\x00\x00\x00\x67\x00\x00\x00\x65\x00\x00\x00\x0a\x00\x00\x00" |
500 | "\xe5\x00\x00\x00\x67\x00\x00\x00\x65\x00\x00\x00\x0a\x00\x00\x00" , 36) |
501 | << (QStringList() << QLatin1String("\345ge" ) << QLatin1String("\345ge" )); |
502 | } |
503 | |
504 | // partials |
505 | QTest::newRow(dataTag: "cr" ) << QByteArray("\r" ) << (QStringList() << "" ); |
506 | QTest::newRow(dataTag: "oneline/cr" ) << QByteArray("ole\r" ) << (QStringList() << "ole" ); |
507 | if (!for_QString) |
508 | QTest::newRow(dataTag: "utf16-BE/cr" ) << QByteArray("\xfe\xff\x00\xe5\x00\x67\x00\x65\x00\x0d" , 10) << (QStringList() << QLatin1String("\345ge" )); |
509 | } |
510 | |
511 | // ------------------------------------------------------------------------------ |
512 | void tst_QTextStream::readLineFromDevice_data() |
513 | { |
514 | generateLineData(for_QString: false); |
515 | } |
516 | |
517 | // ------------------------------------------------------------------------------ |
518 | void tst_QTextStream::readLineFromDevice() |
519 | { |
520 | QFETCH(QByteArray, data); |
521 | QFETCH(QStringList, lines); |
522 | |
523 | QFile::remove(fileName: testFileName); |
524 | QFile file(testFileName); |
525 | QVERIFY(file.open(QFile::ReadWrite)); |
526 | QCOMPARE(file.write(data), qlonglong(data.size())); |
527 | QVERIFY(file.flush()); |
528 | file.seek(offset: 0); |
529 | |
530 | QTextStream stream(&file); |
531 | QStringList list; |
532 | while (!stream.atEnd()) |
533 | list << stream.readLine(); |
534 | |
535 | QCOMPARE(list, lines); |
536 | } |
537 | |
538 | // ------------------------------------------------------------------------------ |
539 | void tst_QTextStream::readLineMaxlen_data() |
540 | { |
541 | QTest::addColumn<QString>(name: "input" ); |
542 | QTest::addColumn<QStringList>(name: "lines" ); |
543 | |
544 | QTest::newRow(dataTag: "Hey" ) |
545 | << QString("Hey" ) |
546 | << (QStringList() << QString("Hey" ) << QString("" )); |
547 | QTest::newRow(dataTag: "Hey\\n" ) |
548 | << QString("Hey\n" ) |
549 | << (QStringList() << QString("Hey" ) << QString("" )); |
550 | QTest::newRow(dataTag: "HelloWorld" ) |
551 | << QString("HelloWorld" ) |
552 | << (QStringList() << QString("Hello" ) << QString("World" )); |
553 | QTest::newRow(dataTag: "Helo\\nWorlds" ) |
554 | << QString("Helo\nWorlds" ) |
555 | << (QStringList() << QString("Helo" ) << QString("World" )); |
556 | QTest::newRow(dataTag: "AAAAA etc." ) |
557 | << QString(16385, QLatin1Char('A')) |
558 | << (QStringList() << QString("AAAAA" ) << QString("AAAAA" )); |
559 | QTest::newRow(dataTag: "multibyte string" ) |
560 | << QString::fromUtf8(str: "\341\233\222\341\233\226\341\232\251\341\232\271\341\232\242\341\233\232\341\232\240\n" ) |
561 | << (QStringList() << QString::fromUtf8(str: "\341\233\222\341\233\226\341\232\251\341\232\271\341\232\242" ) |
562 | << QString::fromUtf8(str: "\341\233\232\341\232\240" )); |
563 | } |
564 | |
565 | // ------------------------------------------------------------------------------ |
566 | void tst_QTextStream::readLineMaxlen() |
567 | { |
568 | QFETCH(QString, input); |
569 | QFETCH(QStringList, lines); |
570 | for (int i = 0; i < 2; ++i) { |
571 | bool useDevice = (i == 1); |
572 | QTextStream stream; |
573 | QFile::remove(fileName: "testfile" ); |
574 | QFile file("testfile" ); |
575 | if (useDevice) { |
576 | file.open(flags: QIODevice::ReadWrite); |
577 | file.write(data: input.toUtf8()); |
578 | file.seek(offset: 0); |
579 | stream.setDevice(&file); |
580 | stream.setCodec("utf-8" ); |
581 | } else { |
582 | stream.setString(string: &input); |
583 | } |
584 | |
585 | QStringList list; |
586 | list << stream.readLine(maxlen: 5); |
587 | list << stream.readLine(maxlen: 5); |
588 | |
589 | QCOMPARE(list, lines); |
590 | } |
591 | } |
592 | |
593 | // ------------------------------------------------------------------------------ |
594 | void tst_QTextStream::readLinesFromBufferCRCR() |
595 | { |
596 | QBuffer buffer; |
597 | buffer.open(openMode: QIODevice::WriteOnly); |
598 | QByteArray data("0123456789\r\r\n" ); |
599 | |
600 | for (int i = 0; i < 10000; ++i) |
601 | buffer.write(data); |
602 | |
603 | buffer.close(); |
604 | if (buffer.open(openMode: QIODevice::ReadOnly|QIODevice::Text)) { |
605 | QTextStream stream(&buffer); |
606 | while (!stream.atEnd()) |
607 | QCOMPARE(stream.readLine(), QString("0123456789" )); |
608 | } |
609 | } |
610 | |
611 | class ErrorDevice : public QIODevice |
612 | { |
613 | protected: |
614 | qint64 readData(char *data, qint64 maxlen) override |
615 | { |
616 | Q_UNUSED(data) |
617 | Q_UNUSED(maxlen) |
618 | return -1; |
619 | } |
620 | |
621 | qint64 writeData(const char *data, qint64 len) override |
622 | { |
623 | Q_UNUSED(data) |
624 | Q_UNUSED(len) |
625 | return -1; |
626 | } |
627 | }; |
628 | |
629 | void tst_QTextStream::readLineInto() |
630 | { |
631 | QByteArray data = "1\n2\n3" ; |
632 | |
633 | QTextStream ts(&data); |
634 | QString line; |
635 | |
636 | ts.readLineInto(line: &line); |
637 | QCOMPARE(line, QStringLiteral("1" )); |
638 | |
639 | ts.readLineInto(line: nullptr, maxlen: 0); // read the second line, but don't store it |
640 | |
641 | ts.readLineInto(line: &line); |
642 | QCOMPARE(line, QStringLiteral("3" )); |
643 | |
644 | QVERIFY(!ts.readLineInto(&line)); |
645 | QVERIFY(line.isEmpty()); |
646 | |
647 | QFile file(m_rfc3261FilePath); |
648 | QVERIFY(file.open(QFile::ReadOnly)); |
649 | |
650 | ts.setDevice(&file); |
651 | line.reserve(asize: 1); |
652 | int maxLineCapacity = line.capacity(); |
653 | |
654 | while (ts.readLineInto(line: &line)) { |
655 | QVERIFY(line.capacity() >= maxLineCapacity); |
656 | maxLineCapacity = line.capacity(); |
657 | } |
658 | |
659 | line = "Test string" ; |
660 | ErrorDevice errorDevice; |
661 | QVERIFY(errorDevice.open(QIODevice::ReadOnly)); |
662 | ts.setDevice(&errorDevice); |
663 | |
664 | QVERIFY(!ts.readLineInto(&line)); |
665 | QVERIFY(line.isEmpty()); |
666 | } |
667 | |
668 | // ------------------------------------------------------------------------------ |
669 | void tst_QTextStream::readLineFromString_data() |
670 | { |
671 | generateLineData(for_QString: true); |
672 | } |
673 | |
674 | // ------------------------------------------------------------------------------ |
675 | void tst_QTextStream::readLineFromString() |
676 | { |
677 | QFETCH(QByteArray, data); |
678 | QFETCH(QStringList, lines); |
679 | |
680 | QString dataString = data; |
681 | |
682 | QTextStream stream(&dataString, QIODevice::ReadOnly); |
683 | QStringList list; |
684 | while (!stream.atEnd()) |
685 | list << stream.readLine(); |
686 | |
687 | QCOMPARE(list, lines); |
688 | } |
689 | |
690 | // ------------------------------------------------------------------------------ |
691 | void tst_QTextStream::readLineFromStringThenChangeString() |
692 | { |
693 | QString first = "First string" ; |
694 | QString second = "Second string" ; |
695 | |
696 | QTextStream stream(&first, QIODevice::ReadOnly); |
697 | QString result = stream.readLine(); |
698 | QCOMPARE(first, result); |
699 | |
700 | stream.setString(string: &second, openMode: QIODevice::ReadOnly); |
701 | result = stream.readLine(); |
702 | QCOMPARE(second, result); |
703 | } |
704 | |
705 | // ------------------------------------------------------------------------------ |
706 | void tst_QTextStream::setDevice() |
707 | { |
708 | // Check that the read buffer is reset after setting a new device |
709 | QByteArray data1("Hello World" ); |
710 | QByteArray data2("How are you" ); |
711 | |
712 | QBuffer bufferOld(&data1); |
713 | bufferOld.open(openMode: QIODevice::ReadOnly); |
714 | |
715 | QBuffer bufferNew(&data2); |
716 | bufferNew.open(openMode: QIODevice::ReadOnly); |
717 | |
718 | QString text; |
719 | QTextStream stream(&bufferOld); |
720 | stream >> text; |
721 | QCOMPARE(text, QString("Hello" )); |
722 | |
723 | stream.setDevice(&bufferNew); |
724 | stream >> text; |
725 | QCOMPARE(text, QString("How" )); |
726 | } |
727 | |
728 | // ------------------------------------------------------------------------------ |
729 | void tst_QTextStream::readLineFromTextDevice_data() |
730 | { |
731 | generateLineData(for_QString: false); |
732 | } |
733 | |
734 | // ------------------------------------------------------------------------------ |
735 | void tst_QTextStream::readLineFromTextDevice() |
736 | { |
737 | QFETCH(QByteArray, data); |
738 | QFETCH(QStringList, lines); |
739 | |
740 | for (int i = 0; i < 8; ++i) { |
741 | QBuffer buffer(&data); |
742 | if (i < 4) |
743 | QVERIFY(buffer.open(QIODevice::ReadOnly | QIODevice::Text)); |
744 | else |
745 | QVERIFY(buffer.open(QIODevice::ReadOnly)); |
746 | |
747 | QTextStream stream(&buffer); |
748 | QStringList list; |
749 | while (!stream.atEnd()) { |
750 | stream.pos(); // <- triggers side effects |
751 | QString line; |
752 | |
753 | if (i & 1) { |
754 | QChar c; |
755 | while (!stream.atEnd()) { |
756 | stream >> c; |
757 | if (stream.status() == QTextStream::Ok) { |
758 | if (c != QLatin1Char('\n') && c != QLatin1Char('\r')) |
759 | line += c; |
760 | if (c == QLatin1Char('\n')) |
761 | break; |
762 | } |
763 | } |
764 | } else { |
765 | line = stream.readLine(); |
766 | } |
767 | |
768 | if ((i & 3) == 3 && !QString(QTest::currentDataTag()).contains(s: "utf16" )) |
769 | stream.seek(pos: stream.pos()); |
770 | list << line; |
771 | } |
772 | QCOMPARE(list, lines); |
773 | } |
774 | } |
775 | |
776 | // ------------------------------------------------------------------------------ |
777 | void tst_QTextStream::generateAllData(bool for_QString) |
778 | { |
779 | QTest::addColumn<QByteArray>(name: "input" ); |
780 | QTest::addColumn<QString>(name: "output" ); |
781 | |
782 | // latin-1 |
783 | QTest::newRow(dataTag: "empty" ) << QByteArray() << QString(); |
784 | QTest::newRow(dataTag: "latin1-a" ) << QByteArray("a" ) << QString("a" ); |
785 | QTest::newRow(dataTag: "latin1-a\\r" ) << QByteArray("a\r" ) << QString("a\r" ); |
786 | QTest::newRow(dataTag: "latin1-a\\r\\n" ) << QByteArray("a\r\n" ) << QString("a\r\n" ); |
787 | QTest::newRow(dataTag: "latin1-a\\n" ) << QByteArray("a\n" ) << QString("a\n" ); |
788 | |
789 | // utf-16 |
790 | if (!for_QString) { |
791 | // one line |
792 | QTest::newRow(dataTag: "utf16-BE/nothing" ) |
793 | << QByteArray("\xfe\xff" |
794 | "\x00\xe5\x00\x67\x00\x65" , 8) << QString::fromLatin1(str: "\345ge" ); |
795 | QTest::newRow(dataTag: "utf16-LE/nothing" ) |
796 | << QByteArray("\xff\xfe" |
797 | "\xe5\x00\x67\x00\x65\x00" , 8) << QString::fromLatin1(str: "\345ge" ); |
798 | QTest::newRow(dataTag: "utf16-BE/lf" ) |
799 | << QByteArray("\xfe\xff" |
800 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 10) << QString::fromLatin1(str: "\345ge\n" ); |
801 | QTest::newRow(dataTag: "utf16-LE/lf" ) |
802 | << QByteArray("\xff\xfe" |
803 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 10) << QString::fromLatin1(str: "\345ge\n" ); |
804 | QTest::newRow(dataTag: "utf16-BE/crlf" ) |
805 | << QByteArray("\xfe\xff" |
806 | "\x00\xe5\x00\x67\x00\x65\x00\x0d\x00\x0a" , 12) << QString::fromLatin1(str: "\345ge\r\n" ); |
807 | QTest::newRow(dataTag: "utf16-LE/crlf" ) |
808 | << QByteArray("\xff\xfe" |
809 | "\xe5\x00\x67\x00\x65\x00\x0d\x00\x0a\x00" , 12) << QString::fromLatin1(str: "\345ge\r\n" ); |
810 | |
811 | // two lines |
812 | QTest::newRow(dataTag: "utf16-BE/twolines" ) |
813 | << QByteArray("\xfe\xff" |
814 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
815 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 18) |
816 | << QString::fromLatin1(str: "\345ge\n\345ge\n" ); |
817 | QTest::newRow(dataTag: "utf16-LE/twolines" ) |
818 | << QByteArray("\xff\xfe" |
819 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
820 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 18) |
821 | << QString::fromLatin1(str: "\345ge\n\345ge\n" ); |
822 | |
823 | // three lines |
824 | QTest::newRow(dataTag: "utf16-BE/threelines" ) |
825 | << QByteArray("\xfe\xff" |
826 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
827 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" |
828 | "\x00\xe5\x00\x67\x00\x65\x00\x0a" , 26) |
829 | << QString::fromLatin1(str: "\345ge\n\345ge\n\345ge\n" ); |
830 | QTest::newRow(dataTag: "utf16-LE/threelines" ) |
831 | << QByteArray("\xff\xfe" |
832 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
833 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" |
834 | "\xe5\x00\x67\x00\x65\x00\x0a\x00" , 26) |
835 | << QString::fromLatin1(str: "\345ge\n\345ge\n\345ge\n" ); |
836 | } |
837 | } |
838 | |
839 | // ------------------------------------------------------------------------------ |
840 | void tst_QTextStream::readLineUntilNull() |
841 | { |
842 | QFile file(m_rfc3261FilePath); |
843 | QVERIFY(file.open(QFile::ReadOnly)); |
844 | |
845 | QTextStream stream(&file); |
846 | for (int i = 0; i < 15066; ++i) { |
847 | QString line = stream.readLine(); |
848 | QVERIFY(!line.isNull()); |
849 | QVERIFY(!line.isNull()); |
850 | } |
851 | QVERIFY(!stream.readLine().isNull()); |
852 | QVERIFY(stream.readLine().isNull()); |
853 | } |
854 | |
855 | // ------------------------------------------------------------------------------ |
856 | void tst_QTextStream::readAllFromDevice_data() |
857 | { |
858 | generateAllData(for_QString: false); |
859 | } |
860 | |
861 | // ------------------------------------------------------------------------------ |
862 | void tst_QTextStream::readAllFromDevice() |
863 | { |
864 | QFETCH(QByteArray, input); |
865 | QFETCH(QString, output); |
866 | |
867 | QBuffer buffer(&input); |
868 | buffer.open(openMode: QBuffer::ReadOnly); |
869 | |
870 | QTextStream stream(&buffer); |
871 | QCOMPARE(stream.readAll(), output); |
872 | } |
873 | |
874 | // ------------------------------------------------------------------------------ |
875 | void tst_QTextStream::readAllFromString_data() |
876 | { |
877 | generateAllData(for_QString: true); |
878 | } |
879 | |
880 | // ------------------------------------------------------------------------------ |
881 | void tst_QTextStream::readAllFromString() |
882 | { |
883 | QFETCH(QByteArray, input); |
884 | QFETCH(QString, output); |
885 | |
886 | QString str = input; |
887 | |
888 | QTextStream stream(&str); |
889 | QCOMPARE(stream.readAll(), output); |
890 | } |
891 | |
892 | // ------------------------------------------------------------------------------ |
893 | void tst_QTextStream::skipWhiteSpace_data() |
894 | { |
895 | QTest::addColumn<QByteArray>(name: "input" ); |
896 | QTest::addColumn<QChar>(name: "output" ); |
897 | |
898 | // latin1 |
899 | QTest::newRow(dataTag: "empty" ) << QByteArray() << QChar('\0'); |
900 | QTest::newRow(dataTag: " one" ) << QByteArray(" one" ) << QChar('o'); |
901 | QTest::newRow(dataTag: "\\none" ) << QByteArray("\none" ) << QChar('o'); |
902 | QTest::newRow(dataTag: "\\n one" ) << QByteArray("\n one" ) << QChar('o'); |
903 | QTest::newRow(dataTag: " \\r\\n one" ) << QByteArray(" \r\n one" ) << QChar('o'); |
904 | |
905 | // utf-16 |
906 | QTest::newRow(dataTag: "utf16-BE (empty)" ) << QByteArray("\xfe\xff" , 2) << QChar('\0'); |
907 | QTest::newRow(dataTag: "utf16-BE ( one)" ) << QByteArray("\xfe\xff\x00 \x00o\x00n\x00e" , 10) << QChar('o'); |
908 | QTest::newRow(dataTag: "utf16-BE (\\none)" ) << QByteArray("\xfe\xff\x00\n\x00o\x00n\x00e" , 10) << QChar('o'); |
909 | QTest::newRow(dataTag: "utf16-BE (\\n one)" ) << QByteArray("\xfe\xff\x00\n\x00 \x00o\x00n\x00e" , 12) << QChar('o'); |
910 | QTest::newRow(dataTag: "utf16-BE ( \\r\\n one)" ) << QByteArray("\xfe\xff\x00 \x00\r\x00\n\x00 \x00o\x00n\x00e" , 16) << QChar('o'); |
911 | |
912 | QTest::newRow(dataTag: "utf16-LE (empty)" ) << QByteArray("\xff\xfe" , 2) << QChar('\0'); |
913 | QTest::newRow(dataTag: "utf16-LE ( one)" ) << QByteArray("\xff\xfe \x00o\x00n\x00e\x00" , 10) << QChar('o'); |
914 | QTest::newRow(dataTag: "utf16-LE (\\none)" ) << QByteArray("\xff\xfe\n\x00o\x00n\x00e\x00" , 10) << QChar('o'); |
915 | QTest::newRow(dataTag: "utf16-LE (\\n one)" ) << QByteArray("\xff\xfe\n\x00 \x00o\x00n\x00e\x00" , 12) << QChar('o'); |
916 | QTest::newRow(dataTag: "utf16-LE ( \\r\\n one)" ) << QByteArray("\xff\xfe \x00\r\x00\n\x00 \x00o\x00n\x00e\x00" , 16) << QChar('o'); |
917 | } |
918 | |
919 | // ------------------------------------------------------------------------------ |
920 | void tst_QTextStream::skipWhiteSpace() |
921 | { |
922 | QFETCH(QByteArray, input); |
923 | QFETCH(QChar, output); |
924 | |
925 | QBuffer buffer(&input); |
926 | buffer.open(openMode: QBuffer::ReadOnly); |
927 | |
928 | QTextStream stream(&buffer); |
929 | stream.skipWhiteSpace(); |
930 | |
931 | QChar tmp; |
932 | stream >> tmp; |
933 | |
934 | QCOMPARE(tmp, output); |
935 | |
936 | QString str = input; |
937 | QTextStream stream2(&input); |
938 | stream2.skipWhiteSpace(); |
939 | |
940 | stream2 >> tmp; |
941 | |
942 | QCOMPARE(tmp, output); |
943 | } |
944 | |
945 | // ------------------------------------------------------------------------------ |
946 | void tst_QTextStream::lineCount_data() |
947 | { |
948 | QTest::addColumn<QByteArray>(name: "data" ); |
949 | QTest::addColumn<int>(name: "lineCount" ); |
950 | |
951 | QTest::newRow(dataTag: "empty" ) << QByteArray() << 0; |
952 | QTest::newRow(dataTag: "oneline" ) << QByteArray("a\n" ) << 1; |
953 | QTest::newRow(dataTag: "twolines" ) << QByteArray("a\nb\n" ) << 2; |
954 | QTest::newRow(dataTag: "oneemptyline" ) << QByteArray("\n" ) << 1; |
955 | QTest::newRow(dataTag: "twoemptylines" ) << QByteArray("\n\n" ) << 2; |
956 | QTest::newRow(dataTag: "buffersize-1 line" ) << QByteArray(16382, '\n') << 16382; |
957 | QTest::newRow(dataTag: "buffersize line" ) << QByteArray(16383, '\n') << 16383; |
958 | QTest::newRow(dataTag: "buffersize+1 line" ) << QByteArray(16384, '\n') << 16384; |
959 | QTest::newRow(dataTag: "buffersize+2 line" ) << QByteArray(16385, '\n') << 16385; |
960 | |
961 | QFile file(m_rfc3261FilePath); file.open(flags: QFile::ReadOnly); |
962 | QTest::newRow(dataTag: "rfc3261" ) << file.readAll() << 15067; |
963 | } |
964 | |
965 | // ------------------------------------------------------------------------------ |
966 | void tst_QTextStream::lineCount() |
967 | { |
968 | QFETCH(QByteArray, data); |
969 | QFETCH(int, lineCount); |
970 | |
971 | QFile out("out.txt" ); |
972 | out.open(flags: QFile::WriteOnly); |
973 | |
974 | QTextStream lineReader(data); |
975 | int lines = 0; |
976 | while (!lineReader.atEnd()) { |
977 | QString line = lineReader.readLine(); |
978 | out.write(data: line.toLatin1() + "\n" ); |
979 | ++lines; |
980 | } |
981 | |
982 | out.close(); |
983 | QCOMPARE(lines, lineCount); |
984 | } |
985 | |
986 | // ------------------------------------------------------------------------------ |
987 | struct CompareIndicesForArray |
988 | { |
989 | int *array; |
990 | CompareIndicesForArray(int *array) : array(array) {} |
991 | bool operator() (const int i1, const int i2) |
992 | { |
993 | return array[i1] < array[i2]; |
994 | } |
995 | }; |
996 | |
997 | void tst_QTextStream::performance() |
998 | { |
999 | // Phase #1 - test speed of reading a huge text file with QFile. |
1000 | QElapsedTimer stopWatch; |
1001 | |
1002 | const int N = 3; |
1003 | const char * readMethods[N] = { |
1004 | "QFile::readLine()" , |
1005 | "QTextStream::readLine()" , |
1006 | "QTextStream::readLine(QString *)" |
1007 | }; |
1008 | int elapsed[N] = {0, 0, 0}; |
1009 | |
1010 | stopWatch.restart(); |
1011 | int nlines1 = 0; |
1012 | QFile file(m_rfc3261FilePath); |
1013 | QVERIFY(file.open(QFile::ReadOnly)); |
1014 | |
1015 | while (!file.atEnd()) { |
1016 | ++nlines1; |
1017 | file.readLine(); |
1018 | } |
1019 | |
1020 | elapsed[0] = stopWatch.elapsed(); |
1021 | stopWatch.restart(); |
1022 | |
1023 | int nlines2 = 0; |
1024 | QFile file2(m_rfc3261FilePath); |
1025 | QVERIFY(file2.open(QFile::ReadOnly)); |
1026 | |
1027 | QTextStream stream(&file2); |
1028 | while (!stream.atEnd()) { |
1029 | ++nlines2; |
1030 | stream.readLine(); |
1031 | } |
1032 | |
1033 | elapsed[1] = stopWatch.elapsed(); |
1034 | stopWatch.restart(); |
1035 | |
1036 | int nlines3 = 0; |
1037 | QFile file3(m_rfc3261FilePath); |
1038 | QVERIFY(file3.open(QFile::ReadOnly)); |
1039 | |
1040 | QTextStream stream2(&file3); |
1041 | QString line; |
1042 | while (stream2.readLineInto(line: &line)) |
1043 | ++nlines3; |
1044 | |
1045 | elapsed[2] = stopWatch.elapsed(); |
1046 | |
1047 | QCOMPARE(nlines1, nlines2); |
1048 | QCOMPARE(nlines2, nlines3); |
1049 | |
1050 | for (int i = 0; i < N; i++) { |
1051 | qDebug(msg: "%s used %.3f seconds to read the file" , readMethods[i], |
1052 | elapsed[i] / 1000.0); |
1053 | } |
1054 | |
1055 | int idx[N] = {0, 1, 2}; |
1056 | std::sort(first: idx, last: idx + N, comp: CompareIndicesForArray(elapsed)); |
1057 | |
1058 | for (int i = 0; i < N-1; i++) { |
1059 | int i1 = idx[i]; |
1060 | int i2 = idx[i+1]; |
1061 | qDebug(msg: "Reading by %s is %.2fx faster than by %s" , |
1062 | readMethods[i1], |
1063 | double(elapsed[i2]) / double(elapsed[i1]), |
1064 | readMethods[i2]); |
1065 | } |
1066 | } |
1067 | |
1068 | // ------------------------------------------------------------------------------ |
1069 | void tst_QTextStream::hexTest_data() |
1070 | { |
1071 | QTest::addColumn<qlonglong>(name: "number" ); |
1072 | QTest::addColumn<QByteArray>(name: "data" ); |
1073 | |
1074 | QTest::newRow(dataTag: "0" ) << Q_INT64_C(0) << QByteArray("0x0" ); |
1075 | QTest::newRow(dataTag: "1" ) << Q_INT64_C(1) << QByteArray("0x1" ); |
1076 | QTest::newRow(dataTag: "2" ) << Q_INT64_C(2) << QByteArray("0x2" ); |
1077 | QTest::newRow(dataTag: "3" ) << Q_INT64_C(3) << QByteArray("0x3" ); |
1078 | QTest::newRow(dataTag: "4" ) << Q_INT64_C(4) << QByteArray("0x4" ); |
1079 | QTest::newRow(dataTag: "5" ) << Q_INT64_C(5) << QByteArray("0x5" ); |
1080 | QTest::newRow(dataTag: "6" ) << Q_INT64_C(6) << QByteArray("0x6" ); |
1081 | QTest::newRow(dataTag: "7" ) << Q_INT64_C(7) << QByteArray("0x7" ); |
1082 | QTest::newRow(dataTag: "8" ) << Q_INT64_C(8) << QByteArray("0x8" ); |
1083 | QTest::newRow(dataTag: "9" ) << Q_INT64_C(9) << QByteArray("0x9" ); |
1084 | QTest::newRow(dataTag: "a" ) << Q_INT64_C(0xa) << QByteArray("0xa" ); |
1085 | QTest::newRow(dataTag: "b" ) << Q_INT64_C(0xb) << QByteArray("0xb" ); |
1086 | QTest::newRow(dataTag: "c" ) << Q_INT64_C(0xc) << QByteArray("0xc" ); |
1087 | QTest::newRow(dataTag: "d" ) << Q_INT64_C(0xd) << QByteArray("0xd" ); |
1088 | QTest::newRow(dataTag: "e" ) << Q_INT64_C(0xe) << QByteArray("0xe" ); |
1089 | QTest::newRow(dataTag: "f" ) << Q_INT64_C(0xf) << QByteArray("0xf" ); |
1090 | QTest::newRow(dataTag: "-1" ) << Q_INT64_C(-1) << QByteArray("-0x1" ); |
1091 | QTest::newRow(dataTag: "0xffffffff" ) << Q_INT64_C(0xffffffff) << QByteArray("0xffffffff" ); |
1092 | QTest::newRow(dataTag: "0xfffffffffffffffe" ) << Q_INT64_C(0xfffffffffffffffe) << QByteArray("-0x2" ); |
1093 | QTest::newRow(dataTag: "0xffffffffffffffff" ) << Q_INT64_C(0xffffffffffffffff) << QByteArray("-0x1" ); |
1094 | QTest::newRow(dataTag: "0x7fffffffffffffff" ) << Q_INT64_C(0x7fffffffffffffff) << QByteArray("0x7fffffffffffffff" ); |
1095 | } |
1096 | |
1097 | // ------------------------------------------------------------------------------ |
1098 | void tst_QTextStream::hexTest() |
1099 | { |
1100 | QFETCH(qlonglong, number); |
1101 | QFETCH(QByteArray, data); |
1102 | |
1103 | QByteArray array; |
1104 | QTextStream stream(&array); |
1105 | |
1106 | stream << Qt::showbase << Qt::hex << number; |
1107 | stream.flush(); |
1108 | QCOMPARE(array, data); |
1109 | } |
1110 | |
1111 | // ------------------------------------------------------------------------------ |
1112 | void tst_QTextStream::binTest_data() |
1113 | { |
1114 | QTest::addColumn<int>(name: "number" ); |
1115 | QTest::addColumn<QByteArray>(name: "data" ); |
1116 | |
1117 | QTest::newRow(dataTag: "0" ) << 0 << QByteArray("0b0" ); |
1118 | QTest::newRow(dataTag: "1" ) << 1 << QByteArray("0b1" ); |
1119 | QTest::newRow(dataTag: "2" ) << 2 << QByteArray("0b10" ); |
1120 | QTest::newRow(dataTag: "5" ) << 5 << QByteArray("0b101" ); |
1121 | QTest::newRow(dataTag: "-1" ) << -1 << QByteArray("-0b1" ); |
1122 | QTest::newRow(dataTag: "11111111" ) << 0xff << QByteArray("0b11111111" ); |
1123 | QTest::newRow(dataTag: "1111111111111111" ) << 0xffff << QByteArray("0b1111111111111111" ); |
1124 | QTest::newRow(dataTag: "1111111011111110" ) << 0xfefe << QByteArray("0b1111111011111110" ); |
1125 | } |
1126 | |
1127 | // ------------------------------------------------------------------------------ |
1128 | void tst_QTextStream::binTest() |
1129 | { |
1130 | QFETCH(int, number); |
1131 | QFETCH(QByteArray, data); |
1132 | |
1133 | QByteArray array; |
1134 | QTextStream stream(&array); |
1135 | |
1136 | stream << Qt::showbase << Qt::bin << number; |
1137 | stream.flush(); |
1138 | QCOMPARE(array.constData(), data.constData()); |
1139 | } |
1140 | |
1141 | // ------------------------------------------------------------------------------ |
1142 | void tst_QTextStream::octTest_data() |
1143 | { |
1144 | QTest::addColumn<int>(name: "number" ); |
1145 | QTest::addColumn<QByteArray>(name: "data" ); |
1146 | |
1147 | QTest::newRow(dataTag: "0" ) << 0 << QByteArray("00" ); |
1148 | } |
1149 | |
1150 | // ------------------------------------------------------------------------------ |
1151 | void tst_QTextStream::octTest() |
1152 | { |
1153 | QFETCH(int, number); |
1154 | QFETCH(QByteArray, data); |
1155 | |
1156 | QByteArray array; |
1157 | QTextStream stream(&array); |
1158 | |
1159 | stream << Qt::showbase << Qt::oct << number; |
1160 | stream.flush(); |
1161 | QCOMPARE(array, data); |
1162 | } |
1163 | |
1164 | // ------------------------------------------------------------------------------ |
1165 | void tst_QTextStream::zeroTermination() |
1166 | { |
1167 | QTextStream stream; |
1168 | char c = '@'; |
1169 | |
1170 | QTest::ignoreMessage(type: QtWarningMsg, message: "QTextStream: No device" ); |
1171 | stream >> c; |
1172 | QCOMPARE(c, '\0'); |
1173 | |
1174 | c = '@'; |
1175 | |
1176 | QTest::ignoreMessage(type: QtWarningMsg, message: "QTextStream: No device" ); |
1177 | stream >> &c; |
1178 | QCOMPARE(c, '\0'); |
1179 | } |
1180 | |
1181 | // ------------------------------------------------------------------------------ |
1182 | void tst_QTextStream::ws_manipulator() |
1183 | { |
1184 | { |
1185 | QString string = "a b c d" ; |
1186 | QTextStream stream(&string); |
1187 | |
1188 | char a, b, c, d; |
1189 | stream >> a >> b >> c >> d; |
1190 | QCOMPARE(a, 'a'); |
1191 | QCOMPARE(b, ' '); |
1192 | QCOMPARE(c, 'b'); |
1193 | QCOMPARE(d, ' '); |
1194 | } |
1195 | { |
1196 | QString string = "a b c d" ; |
1197 | QTextStream stream(&string); |
1198 | |
1199 | char a, b, c, d; |
1200 | stream >> a >> Qt::ws >> b >> Qt::ws >> c >> Qt::ws >> d; |
1201 | QCOMPARE(a, 'a'); |
1202 | QCOMPARE(b, 'b'); |
1203 | QCOMPARE(c, 'c'); |
1204 | QCOMPARE(d, 'd'); |
1205 | } |
1206 | } |
1207 | |
1208 | // ------------------------------------------------------------------------------ |
1209 | void tst_QTextStream::stillOpenWhenAtEnd() |
1210 | { |
1211 | QFile file(QFINDTESTDATA("tst_qtextstream.cpp" )); |
1212 | QVERIFY(file.open(QFile::ReadOnly)); |
1213 | |
1214 | QTextStream stream(&file); |
1215 | while (!stream.readLine().isNull()) {} |
1216 | QVERIFY(file.isOpen()); |
1217 | |
1218 | if (!QtNetworkSettings::verifyTestNetworkSettings()) |
1219 | QSKIP("No network test server available" ); |
1220 | |
1221 | QTcpSocket socket; |
1222 | socket.connectToHost(hostName: QtNetworkSettings::serverName(), port: 143); |
1223 | QVERIFY(socket.waitForReadyRead(5000)); |
1224 | |
1225 | QTextStream stream2(&socket); |
1226 | while (!stream2.readLine().isNull()) {} |
1227 | QVERIFY(socket.isOpen()); |
1228 | } |
1229 | |
1230 | // ------------------------------------------------------------------------------ |
1231 | void tst_QTextStream::readNewlines_data() |
1232 | { |
1233 | QTest::addColumn<QByteArray>(name: "input" ); |
1234 | QTest::addColumn<QString>(name: "output" ); |
1235 | |
1236 | QTest::newRow(dataTag: "empty" ) << QByteArray() << QString(); |
1237 | QTest::newRow(dataTag: "\\r\\n" ) << QByteArray("\r\n" ) << QString("\n" ); |
1238 | QTest::newRow(dataTag: "\\r\\r\\n" ) << QByteArray("\r\r\n" ) << QString("\n" ); |
1239 | QTest::newRow(dataTag: "\\r\\n\\r\\n" ) << QByteArray("\r\n\r\n" ) << QString("\n\n" ); |
1240 | QTest::newRow(dataTag: "\\n" ) << QByteArray("\n" ) << QString("\n" ); |
1241 | QTest::newRow(dataTag: "\\n\\n" ) << QByteArray("\n\n" ) << QString("\n\n" ); |
1242 | } |
1243 | |
1244 | // ------------------------------------------------------------------------------ |
1245 | void tst_QTextStream::readNewlines() |
1246 | { |
1247 | QFETCH(QByteArray, input); |
1248 | QFETCH(QString, output); |
1249 | |
1250 | QBuffer buffer(&input); |
1251 | buffer.open(openMode: QBuffer::ReadOnly | QBuffer::Text); |
1252 | QTextStream stream(&buffer); |
1253 | QCOMPARE(stream.readAll(), output); |
1254 | } |
1255 | |
1256 | // ------------------------------------------------------------------------------ |
1257 | void tst_QTextStream::seek() |
1258 | { |
1259 | QFile file(m_rfc3261FilePath); |
1260 | QVERIFY(file.open(QFile::ReadOnly)); |
1261 | |
1262 | QTextStream stream(&file); |
1263 | QString tmp; |
1264 | stream >> tmp; |
1265 | QCOMPARE(tmp, QString::fromLatin1("Network" )); |
1266 | |
1267 | // QTextStream::seek(0) should both clear its internal read/write buffers |
1268 | // and seek the device. |
1269 | for (int i = 0; i < 4; ++i) { |
1270 | stream.seek(pos: 12 + i); |
1271 | stream >> tmp; |
1272 | QCOMPARE(tmp, QString("Network" ).mid(i)); |
1273 | } |
1274 | for (int i = 0; i < 4; ++i) { |
1275 | stream.seek(pos: 16 - i); |
1276 | stream >> tmp; |
1277 | QCOMPARE(tmp, QString("Network" ).mid(4 - i)); |
1278 | } |
1279 | stream.seek(pos: 139181); |
1280 | stream >> tmp; |
1281 | QCOMPARE(tmp, QString("information" )); |
1282 | stream.seek(pos: 388683); |
1283 | stream >> tmp; |
1284 | QCOMPARE(tmp, QString("telephone" )); |
1285 | |
1286 | // Also test this with a string |
1287 | QString words = QLatin1String("thisisa" ); |
1288 | QTextStream stream2(&words, QIODevice::ReadOnly); |
1289 | stream2 >> tmp; |
1290 | QCOMPARE(tmp, QString::fromLatin1("thisisa" )); |
1291 | |
1292 | for (int i = 0; i < 4; ++i) { |
1293 | stream2.seek(pos: i); |
1294 | stream2 >> tmp; |
1295 | QCOMPARE(tmp, QString("thisisa" ).mid(i)); |
1296 | } |
1297 | for (int i = 0; i < 4; ++i) { |
1298 | stream2.seek(pos: 4 - i); |
1299 | stream2 >> tmp; |
1300 | QCOMPARE(tmp, QString("thisisa" ).mid(4 - i)); |
1301 | } |
1302 | } |
1303 | |
1304 | // ------------------------------------------------------------------------------ |
1305 | void tst_QTextStream::pos() |
1306 | { |
1307 | { |
1308 | // Strings |
1309 | QString str("this is a test" ); |
1310 | QTextStream stream(&str, QIODevice::ReadWrite); |
1311 | |
1312 | QCOMPARE(stream.pos(), qint64(0)); |
1313 | for (int i = 0; i <= str.size(); ++i) { |
1314 | QVERIFY(stream.seek(i)); |
1315 | QCOMPARE(stream.pos(), qint64(i)); |
1316 | } |
1317 | for (int j = str.size(); j >= 0; --j) { |
1318 | QVERIFY(stream.seek(j)); |
1319 | QCOMPARE(stream.pos(), qint64(j)); |
1320 | } |
1321 | |
1322 | QVERIFY(stream.seek(0)); |
1323 | |
1324 | QChar ch; |
1325 | stream >> ch; |
1326 | QCOMPARE(ch, QChar('t')); |
1327 | |
1328 | QCOMPARE(stream.pos(), qint64(1)); |
1329 | QVERIFY(stream.seek(1)); |
1330 | QCOMPARE(stream.pos(), qint64(1)); |
1331 | QVERIFY(stream.seek(0)); |
1332 | |
1333 | QString strtmp; |
1334 | stream >> strtmp; |
1335 | QCOMPARE(strtmp, QString("this" )); |
1336 | |
1337 | QCOMPARE(stream.pos(), qint64(4)); |
1338 | stream.seek(pos: 0); |
1339 | stream.seek(pos: 4); |
1340 | |
1341 | stream >> ch; |
1342 | QCOMPARE(ch, QChar(' ')); |
1343 | QCOMPARE(stream.pos(), qint64(5)); |
1344 | |
1345 | stream.seek(pos: 10); |
1346 | stream >> strtmp; |
1347 | QCOMPARE(strtmp, QString("test" )); |
1348 | QCOMPARE(stream.pos(), qint64(14)); |
1349 | } |
1350 | { |
1351 | // Latin1 device |
1352 | QFile file(m_rfc3261FilePath); |
1353 | QVERIFY(file.open(QIODevice::ReadOnly)); |
1354 | |
1355 | QTextStream stream(&file); |
1356 | |
1357 | QCOMPARE(stream.pos(), qint64(0)); |
1358 | |
1359 | for (int i = 0; i <= file.size(); i += 7) { |
1360 | QVERIFY(stream.seek(i)); |
1361 | QCOMPARE(stream.pos(), qint64(i)); |
1362 | } |
1363 | for (int j = file.size(); j >= 0; j -= 7) { |
1364 | QVERIFY(stream.seek(j)); |
1365 | QCOMPARE(stream.pos(), qint64(j)); |
1366 | } |
1367 | |
1368 | stream.seek(pos: 0); |
1369 | |
1370 | QString strtmp; |
1371 | stream >> strtmp; |
1372 | QCOMPARE(strtmp, QString("Network" )); |
1373 | QCOMPARE(stream.pos(), qint64(19)); |
1374 | |
1375 | stream.seek(pos: 2598); |
1376 | QCOMPARE(stream.pos(), qint64(2598)); |
1377 | stream >> strtmp; |
1378 | QCOMPARE(stream.pos(), qint64(2607)); |
1379 | QCOMPARE(strtmp, QString("locations" )); |
1380 | } |
1381 | { |
1382 | // Shift-JIS device |
1383 | for (int i = 0; i < 2; ++i) { |
1384 | QFile file(m_shiftJisFilePath); |
1385 | if (i == 0) |
1386 | QVERIFY(file.open(QIODevice::ReadOnly)); |
1387 | else |
1388 | QVERIFY(file.open(QIODevice::ReadOnly | QIODevice::Text)); |
1389 | |
1390 | QTextStream stream(&file); |
1391 | stream.setCodec("Shift-JIS" ); |
1392 | QVERIFY(stream.codec()); |
1393 | |
1394 | QCOMPARE(stream.pos(), qint64(0)); |
1395 | for (int i = 0; i <= file.size(); i += 7) { |
1396 | QVERIFY(stream.seek(i)); |
1397 | QCOMPARE(stream.pos(), qint64(i)); |
1398 | } |
1399 | for (int j = file.size(); j >= 0; j -= 7) { |
1400 | QVERIFY(stream.seek(j)); |
1401 | QCOMPARE(stream.pos(), qint64(j)); |
1402 | } |
1403 | |
1404 | stream.seek(pos: 2089); |
1405 | QString strtmp; |
1406 | stream >> strtmp; |
1407 | QCOMPARE(strtmp, QString("AUnicode" )); |
1408 | QCOMPARE(stream.pos(), qint64(2097)); |
1409 | |
1410 | stream.seek(pos: 43325); |
1411 | stream >> strtmp; |
1412 | QCOMPARE(strtmp, QString("Shift-JIS" )); |
1413 | stream >> strtmp; |
1414 | QCOMPARE(strtmp, QString::fromUtf8("\343\201\247\346\233\270\343\201\213\343\202\214\343\201\237" )); |
1415 | QCOMPARE(stream.pos(), qint64(43345)); |
1416 | stream >> strtmp; |
1417 | QCOMPARE(strtmp, QString("POD" )); |
1418 | QCOMPARE(stream.pos(), qint64(43349)); |
1419 | } |
1420 | } |
1421 | } |
1422 | |
1423 | // ------------------------------------------------------------------------------ |
1424 | void tst_QTextStream::pos2() |
1425 | { |
1426 | QByteArray data("abcdef\r\nghijkl\r\n" ); |
1427 | QBuffer buffer(&data); |
1428 | QVERIFY(buffer.open(QIODevice::ReadOnly | QIODevice::Text)); |
1429 | |
1430 | QTextStream stream(&buffer); |
1431 | |
1432 | QChar ch; |
1433 | |
1434 | QCOMPARE(stream.pos(), qint64(0)); |
1435 | stream >> ch; |
1436 | QCOMPARE(ch, QChar('a')); |
1437 | QCOMPARE(stream.pos(), qint64(1)); |
1438 | |
1439 | QString str; |
1440 | stream >> str; |
1441 | QCOMPARE(str, QString("bcdef" )); |
1442 | QCOMPARE(stream.pos(), qint64(6)); |
1443 | |
1444 | stream >> str; |
1445 | QCOMPARE(str, QString("ghijkl" )); |
1446 | QCOMPARE(stream.pos(), qint64(14)); |
1447 | |
1448 | // Seek back and try again |
1449 | stream.seek(pos: 1); |
1450 | QCOMPARE(stream.pos(), qint64(1)); |
1451 | stream >> str; |
1452 | QCOMPARE(str, QString("bcdef" )); |
1453 | QCOMPARE(stream.pos(), qint64(6)); |
1454 | |
1455 | stream.seek(pos: 6); |
1456 | stream >> str; |
1457 | QCOMPARE(str, QString("ghijkl" )); |
1458 | QCOMPARE(stream.pos(), qint64(14)); |
1459 | } |
1460 | |
1461 | // ------------------------------------------------------------------------------ |
1462 | void tst_QTextStream::pos3LargeFile() |
1463 | { |
1464 | if (EmulationDetector::isRunningArmOnX86()) |
1465 | QSKIP("Running QTextStream::pos() in tight loop is too slow on emulator" ); |
1466 | |
1467 | { |
1468 | QFile file(testFileName); |
1469 | file.open(flags: QIODevice::WriteOnly | QIODevice::Text); |
1470 | QTextStream out( &file ); |
1471 | // NOTE: The unusual spacing is to ensure non-1-character whitespace. |
1472 | QString lineString = " 0 1 2\t3 4\t \t5 6 7 8 9 \n" ; |
1473 | // Approximate 50kb text file |
1474 | const int NbLines = (50*1024) / lineString.length() + 1; |
1475 | for (int line = 0; line < NbLines; ++line) |
1476 | out << lineString; |
1477 | // File is automatically flushed and closed on destruction. |
1478 | } |
1479 | QFile file(testFileName); |
1480 | file.open(flags: QIODevice::ReadOnly | QIODevice::Text); |
1481 | QTextStream in( &file ); |
1482 | const int testValues[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; |
1483 | int value; |
1484 | while (true) { |
1485 | in.pos(); |
1486 | for ( int i = 0; i < 10; ++i ) { |
1487 | in >> value; |
1488 | if (in.status() != QTextStream::Ok) { |
1489 | // End case, i == 0 && eof reached. |
1490 | QCOMPARE(i, 0); |
1491 | QCOMPARE(in.status(), QTextStream::ReadPastEnd); |
1492 | return; |
1493 | } |
1494 | QCOMPARE(value, testValues[i]); |
1495 | } |
1496 | } |
1497 | } |
1498 | |
1499 | // ------------------------------------------------------------------------------ |
1500 | void tst_QTextStream::readStdin() |
1501 | { |
1502 | #if !QT_CONFIG(process) |
1503 | QSKIP("No qprocess support" , SkipAll); |
1504 | #else |
1505 | QProcess stdinProcess; |
1506 | stdinProcess.start(command: "stdinProcess/stdinProcess" ); |
1507 | stdinProcess.setReadChannel(QProcess::StandardError); |
1508 | |
1509 | QTextStream stream(&stdinProcess); |
1510 | stream << "1" << Qt::endl; |
1511 | stream << "2" << Qt::endl; |
1512 | stream << "3" << Qt::endl; |
1513 | |
1514 | stdinProcess.closeWriteChannel(); |
1515 | |
1516 | QVERIFY(stdinProcess.waitForFinished(5000)); |
1517 | |
1518 | int a, b, c; |
1519 | stream >> a >> b >> c; |
1520 | QCOMPARE(a, 1); |
1521 | QCOMPARE(b, 2); |
1522 | QCOMPARE(c, 3); |
1523 | #endif |
1524 | } |
1525 | |
1526 | // ------------------------------------------------------------------------------ |
1527 | void tst_QTextStream::readAllFromStdin() |
1528 | { |
1529 | #if !QT_CONFIG(process) |
1530 | QSKIP("No qprocess support" , SkipAll); |
1531 | #else |
1532 | QProcess stdinProcess; |
1533 | stdinProcess.start(command: "readAllStdinProcess/readAllStdinProcess" , mode: QIODevice::ReadWrite | QIODevice::Text); |
1534 | stdinProcess.setReadChannel(QProcess::StandardError); |
1535 | |
1536 | QTextStream stream(&stdinProcess); |
1537 | stream.setCodec("ISO-8859-1" ); |
1538 | stream << "hello world" << Qt::flush; |
1539 | |
1540 | stdinProcess.closeWriteChannel(); |
1541 | |
1542 | QVERIFY(stdinProcess.waitForFinished(5000)); |
1543 | QCOMPARE(stream.readAll(), QString::fromLatin1("hello world\n" )); |
1544 | #endif |
1545 | } |
1546 | |
1547 | // ------------------------------------------------------------------------------ |
1548 | void tst_QTextStream::readLineFromStdin() |
1549 | { |
1550 | #if !QT_CONFIG(process) |
1551 | QSKIP("No qprocess support" , SkipAll); |
1552 | #else |
1553 | QProcess stdinProcess; |
1554 | stdinProcess.start(command: "readLineStdinProcess/readLineStdinProcess" , mode: QIODevice::ReadWrite | QIODevice::Text); |
1555 | stdinProcess.setReadChannel(QProcess::StandardError); |
1556 | |
1557 | stdinProcess.write(data: "abc\n" ); |
1558 | QVERIFY(stdinProcess.waitForReadyRead(5000)); |
1559 | QCOMPARE(stdinProcess.readAll().data(), QByteArray("abc" ).data()); |
1560 | |
1561 | stdinProcess.write(data: "def\n" ); |
1562 | QVERIFY(stdinProcess.waitForReadyRead(5000)); |
1563 | QCOMPARE(stdinProcess.readAll(), QByteArray("def" )); |
1564 | |
1565 | stdinProcess.closeWriteChannel(); |
1566 | |
1567 | QVERIFY(stdinProcess.waitForFinished(5000)); |
1568 | #endif |
1569 | } |
1570 | |
1571 | // ------------------------------------------------------------------------------ |
1572 | void tst_QTextStream::read() |
1573 | { |
1574 | { |
1575 | QFile::remove(fileName: "testfile" ); |
1576 | QFile file("testfile" ); |
1577 | file.open(flags: QFile::WriteOnly); |
1578 | file.write(data: "4.15 abc ole" ); |
1579 | file.close(); |
1580 | |
1581 | QVERIFY(file.open(QFile::ReadOnly)); |
1582 | QTextStream stream(&file); |
1583 | QCOMPARE(stream.read(0), QString("" )); |
1584 | QCOMPARE(stream.read(4), QString("4.15" )); |
1585 | QCOMPARE(stream.read(4), QString(" abc" )); |
1586 | stream.seek(pos: 1); |
1587 | QCOMPARE(stream.read(4), QString(".15 " )); |
1588 | stream.seek(pos: 1); |
1589 | QCOMPARE(stream.read(4), QString(".15 " )); |
1590 | stream.seek(pos: 2); |
1591 | QCOMPARE(stream.read(4), QString("15 a" )); |
1592 | // ### add tests for reading \r\n etc.. |
1593 | } |
1594 | |
1595 | { |
1596 | // File larger than QTEXTSTREAM_BUFFERSIZE |
1597 | QFile::remove(fileName: "testfile" ); |
1598 | QFile file("testfile" ); |
1599 | file.open(flags: QFile::WriteOnly); |
1600 | for (int i = 0; i < 16384 / 8; ++i) |
1601 | file.write(data: "01234567" ); |
1602 | file.write(data: "0" ); |
1603 | file.close(); |
1604 | |
1605 | QVERIFY(file.open(QFile::ReadOnly)); |
1606 | QTextStream stream(&file); |
1607 | QCOMPARE(stream.read(10), QString("0123456701" )); |
1608 | QCOMPARE(stream.read(10), QString("2345670123" )); |
1609 | QCOMPARE(stream.readAll().size(), 16385-20); |
1610 | } |
1611 | } |
1612 | |
1613 | // ------------------------------------------------------------------------------ |
1614 | void tst_QTextStream::qbool() |
1615 | { |
1616 | QString s; |
1617 | QTextStream stream(&s); |
1618 | stream << s.contains(s: QString("hei" )); |
1619 | QCOMPARE(s, QString("0" )); |
1620 | } |
1621 | |
1622 | // ------------------------------------------------------------------------------ |
1623 | void tst_QTextStream::forcePoint() |
1624 | { |
1625 | QString str; |
1626 | QTextStream stream(&str); |
1627 | stream << Qt::fixed << Qt::forcepoint << 1.0 << ' ' << 1 << ' ' << 0 << ' ' << -1.0 << ' ' << -1; |
1628 | QCOMPARE(str, QString("1.000000 1 0 -1.000000 -1" )); |
1629 | |
1630 | str.clear(); |
1631 | stream.seek(pos: 0); |
1632 | stream << Qt::scientific << Qt::forcepoint << 1.0 << ' ' << 1 << ' ' << 0 << ' ' << -1.0 << ' ' << -1; |
1633 | QCOMPARE(str, QString("1.000000e+00 1 0 -1.000000e+00 -1" )); |
1634 | |
1635 | str.clear(); |
1636 | stream.seek(pos: 0); |
1637 | stream.setRealNumberNotation(QTextStream::SmartNotation); |
1638 | stream << Qt::forcepoint << 1.0 << ' ' << 1 << ' ' << 0 << ' ' << -1.0 << ' ' << -1; |
1639 | QCOMPARE(str, QString("1.00000 1 0 -1.00000 -1" )); |
1640 | |
1641 | } |
1642 | |
1643 | // ------------------------------------------------------------------------------ |
1644 | void tst_QTextStream::forceSign() |
1645 | { |
1646 | QString str; |
1647 | QTextStream stream(&str); |
1648 | stream << Qt::forcesign << 1.2 << ' ' << -1.2 << ' ' << 0; |
1649 | QCOMPARE(str, QString("+1.2 -1.2 +0" )); |
1650 | } |
1651 | |
1652 | // ------------------------------------------------------------------------------ |
1653 | void tst_QTextStream::read0d0d0a() |
1654 | { |
1655 | QFile file("task113817.txt" ); |
1656 | file.open(flags: QIODevice::ReadOnly | QIODevice::Text); |
1657 | |
1658 | QTextStream stream(&file); |
1659 | while (!stream.atEnd()) |
1660 | stream.readLine(); |
1661 | } |
1662 | |
1663 | // ------------------------------------------------------------------------------ |
1664 | |
1665 | Q_DECLARE_METATYPE(QTextStreamFunction); |
1666 | |
1667 | // Also tests that we can have namespaces that conflict with our QTextStream constants. |
1668 | namespace ws { |
1669 | QTextStream &noop(QTextStream &s) { return s; } |
1670 | } |
1671 | |
1672 | void tst_QTextStream::numeralCase_data() |
1673 | { |
1674 | QTextStreamFunction noop_ = ws::noop; |
1675 | QTextStreamFunction bin = Qt::bin; |
1676 | QTextStreamFunction oct = Qt::oct; |
1677 | QTextStreamFunction hex = Qt::hex; |
1678 | QTextStreamFunction base = Qt::showbase; |
1679 | QTextStreamFunction ucb = Qt::uppercasebase; |
1680 | QTextStreamFunction lcb = Qt::lowercasebase; |
1681 | QTextStreamFunction ucd = Qt::uppercasedigits; |
1682 | QTextStreamFunction lcd = Qt::lowercasedigits; |
1683 | |
1684 | QTest::addColumn<QTextStreamFunction>(name: "func1" ); |
1685 | QTest::addColumn<QTextStreamFunction>(name: "func2" ); |
1686 | QTest::addColumn<QTextStreamFunction>(name: "func3" ); |
1687 | QTest::addColumn<QTextStreamFunction>(name: "func4" ); |
1688 | QTest::addColumn<int>(name: "value" ); |
1689 | QTest::addColumn<QString>(name: "expected" ); |
1690 | QTest::newRow(dataTag: "dec 1" ) << noop_ << noop_ << noop_ << noop_ << 31 << "31" ; |
1691 | QTest::newRow(dataTag: "dec 2" ) << noop_ << base << noop_ << noop_ << 31 << "31" ; |
1692 | |
1693 | QTest::newRow(dataTag: "hex 1" ) << hex << noop_ << noop_ << noop_ << 31 << "1f" ; |
1694 | QTest::newRow(dataTag: "hex 2" ) << hex << noop_ << noop_ << lcd << 31 << "1f" ; |
1695 | QTest::newRow(dataTag: "hex 3" ) << hex << noop_ << ucb << noop_ << 31 << "1f" ; |
1696 | QTest::newRow(dataTag: "hex 4" ) << hex << noop_ << noop_ << ucd << 31 << "1F" ; |
1697 | QTest::newRow(dataTag: "hex 5" ) << hex << noop_ << lcb << ucd << 31 << "1F" ; |
1698 | QTest::newRow(dataTag: "hex 6" ) << hex << noop_ << ucb << ucd << 31 << "1F" ; |
1699 | QTest::newRow(dataTag: "hex 7" ) << hex << base << noop_ << noop_ << 31 << "0x1f" ; |
1700 | QTest::newRow(dataTag: "hex 8" ) << hex << base << lcb << lcd << 31 << "0x1f" ; |
1701 | QTest::newRow(dataTag: "hex 9" ) << hex << base << ucb << noop_ << 31 << "0X1f" ; |
1702 | QTest::newRow(dataTag: "hex 10" ) << hex << base << ucb << lcd << 31 << "0X1f" ; |
1703 | QTest::newRow(dataTag: "hex 11" ) << hex << base << noop_ << ucd << 31 << "0x1F" ; |
1704 | QTest::newRow(dataTag: "hex 12" ) << hex << base << lcb << ucd << 31 << "0x1F" ; |
1705 | QTest::newRow(dataTag: "hex 13" ) << hex << base << ucb << ucd << 31 << "0X1F" ; |
1706 | |
1707 | QTest::newRow(dataTag: "bin 1" ) << bin << noop_ << noop_ << noop_ << 31 << "11111" ; |
1708 | QTest::newRow(dataTag: "bin 2" ) << bin << base << noop_ << noop_ << 31 << "0b11111" ; |
1709 | QTest::newRow(dataTag: "bin 3" ) << bin << base << lcb << noop_ << 31 << "0b11111" ; |
1710 | QTest::newRow(dataTag: "bin 4" ) << bin << base << ucb << noop_ << 31 << "0B11111" ; |
1711 | QTest::newRow(dataTag: "bin 5" ) << bin << base << noop_ << ucd << 31 << "0b11111" ; |
1712 | QTest::newRow(dataTag: "bin 6" ) << bin << base << lcb << ucd << 31 << "0b11111" ; |
1713 | QTest::newRow(dataTag: "bin 7" ) << bin << base << ucb << ucd << 31 << "0B11111" ; |
1714 | |
1715 | QTest::newRow(dataTag: "oct 1" ) << oct << noop_ << noop_ << noop_ << 31 << "37" ; |
1716 | QTest::newRow(dataTag: "oct 2" ) << oct << base << noop_ << noop_ << 31 << "037" ; |
1717 | } |
1718 | |
1719 | void tst_QTextStream::numeralCase() |
1720 | { |
1721 | QFETCH(QTextStreamFunction, func1); |
1722 | QFETCH(QTextStreamFunction, func2); |
1723 | QFETCH(QTextStreamFunction, func3); |
1724 | QFETCH(QTextStreamFunction, func4); |
1725 | QFETCH(int, value); |
1726 | QFETCH(QString, expected); |
1727 | |
1728 | QString str; |
1729 | QTextStream stream(&str); |
1730 | stream << func1 << func2 << func3 << func4 << value; |
1731 | QCOMPARE(str, expected); |
1732 | } |
1733 | |
1734 | // ------------------------------------------------------------------------------ |
1735 | void tst_QTextStream::nanInf() |
1736 | { |
1737 | // Cannot use test data in this function, as comparing nans and infs isn't |
1738 | // well defined. |
1739 | QString str("nan NAN nAn +nan +NAN +nAn -nan -NAN -nAn" |
1740 | " inf INF iNf +inf +INF +iNf -inf -INF -iNf" ); |
1741 | |
1742 | QTextStream stream(&str); |
1743 | |
1744 | double tmpD = 0; |
1745 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1746 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1747 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1748 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1749 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1750 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1751 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1752 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1753 | stream >> tmpD; QVERIFY(qIsNaN(tmpD)); tmpD = 0; |
1754 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1755 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1756 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1757 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1758 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1759 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD > 0); tmpD = 0; |
1760 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD < 0); tmpD = 0; |
1761 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD < 0); tmpD = 0; |
1762 | stream >> tmpD; QVERIFY(qIsInf(tmpD)); QVERIFY(tmpD < 0); tmpD = 0; |
1763 | |
1764 | stream.seek(pos: 0); |
1765 | |
1766 | float tmpF = 0; |
1767 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1768 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1769 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1770 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1771 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1772 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1773 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1774 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1775 | stream >> tmpF; QVERIFY(qIsNaN(tmpF)); tmpD = 0; |
1776 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1777 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1778 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1779 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1780 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1781 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF > 0); tmpD = 0; |
1782 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF < 0); tmpD = 0; |
1783 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF < 0); tmpD = 0; |
1784 | stream >> tmpF; QVERIFY(qIsInf(tmpF)); QVERIFY(tmpF < 0); |
1785 | |
1786 | QString s; |
1787 | QTextStream out(&s); |
1788 | out << qInf() << ' ' << -qInf() << ' ' << qQNaN() |
1789 | << Qt::uppercasedigits << ' ' |
1790 | << qInf() << ' ' << -qInf() << ' ' << qQNaN() |
1791 | << Qt::flush; |
1792 | |
1793 | QCOMPARE(s, QString("inf -inf nan INF -INF NAN" )); |
1794 | } |
1795 | |
1796 | // ------------------------------------------------------------------------------ |
1797 | void tst_QTextStream::utf8IncompleteAtBufferBoundary_data() |
1798 | { |
1799 | QTest::addColumn<bool>(name: "useLocale" ); |
1800 | |
1801 | QTest::newRow(dataTag: "utf8" ) << false; |
1802 | |
1803 | // is this locale UTF-8? |
1804 | if (QString(QChar::ReplacementCharacter).toLocal8Bit() == "\xef\xbf\xbd" ) |
1805 | QTest::newRow(dataTag: "locale" ) << true; |
1806 | } |
1807 | |
1808 | void tst_QTextStream::utf8IncompleteAtBufferBoundary() |
1809 | { |
1810 | QFile::remove(fileName: testFileName); |
1811 | QFile data(testFileName); |
1812 | |
1813 | QTextCodec *utf8Codec = QTextCodec::codecForMib(mib: 106); |
1814 | QString lineContents = QString::fromUtf8(str: "\342\200\223" // U+2013 EN DASH |
1815 | "\342\200\223" |
1816 | "\342\200\223" |
1817 | "\342\200\223" |
1818 | "\342\200\223" |
1819 | "\342\200\223" ); |
1820 | |
1821 | data.open(flags: QFile::WriteOnly | QFile::Truncate); |
1822 | { |
1823 | QTextStream out(&data); |
1824 | out.setCodec(utf8Codec); |
1825 | out.setFieldWidth(3); |
1826 | |
1827 | for (int i = 0; i < 1000; ++i) { |
1828 | out << i << lineContents << Qt::endl; |
1829 | } |
1830 | } |
1831 | data.close(); |
1832 | |
1833 | data.open(flags: QFile::ReadOnly); |
1834 | QTextStream in(&data); |
1835 | |
1836 | QFETCH(bool, useLocale); |
1837 | if (!useLocale) |
1838 | in.setCodec(utf8Codec); // QUtf8Codec |
1839 | else |
1840 | in.setCodec(QTextCodec::codecForLocale()); |
1841 | |
1842 | int i = 0; |
1843 | do { |
1844 | QString line = in.readLine().trimmed(); |
1845 | ++i; |
1846 | QVERIFY2(line.endsWith(lineContents), QString("Line %1: %2" ).arg(i).arg(line).toLocal8Bit()); |
1847 | } while (!in.atEnd()); |
1848 | } |
1849 | |
1850 | // ------------------------------------------------------------------------------ |
1851 | |
1852 | // Make sure we don't write a BOM after seek()ing |
1853 | |
1854 | void tst_QTextStream::writeSeekWriteNoBOM() |
1855 | { |
1856 | |
1857 | //First with the default codec (normally either latin-1 or UTF-8) |
1858 | |
1859 | QBuffer out; |
1860 | out.open(openMode: QIODevice::WriteOnly); |
1861 | QTextStream stream(&out); |
1862 | |
1863 | int number = 0; |
1864 | QString sizeStr = QLatin1String("Size=" ) |
1865 | + QString::number(number).rightJustified(width: 10, fill: QLatin1Char('0')); |
1866 | stream << sizeStr << Qt::endl; |
1867 | stream << "Version=" << QString::number(14) << Qt::endl; |
1868 | stream << "blah blah blah" << Qt::endl; |
1869 | stream.flush(); |
1870 | |
1871 | QCOMPARE(out.buffer().constData(), "Size=0000000000\nVersion=14\nblah blah blah\n" ); |
1872 | |
1873 | // Now overwrite the size header item |
1874 | number = 42; |
1875 | stream.seek(pos: 0); |
1876 | sizeStr = QLatin1String("Size=" ) |
1877 | + QString::number(number).rightJustified(width: 10, fill: QLatin1Char('0')); |
1878 | stream << sizeStr << Qt::endl; |
1879 | stream.flush(); |
1880 | |
1881 | // Check buffer is still OK |
1882 | QCOMPARE(out.buffer().constData(), "Size=0000000042\nVersion=14\nblah blah blah\n" ); |
1883 | |
1884 | |
1885 | //Then UTF-16 |
1886 | |
1887 | QBuffer out16; |
1888 | out16.open(openMode: QIODevice::WriteOnly); |
1889 | QTextStream stream16(&out16); |
1890 | stream16.setCodec("UTF-16" ); |
1891 | |
1892 | stream16 << "one" << "two" << QLatin1String("three" ); |
1893 | stream16.flush(); |
1894 | |
1895 | // save that output |
1896 | QByteArray first = out16.buffer(); |
1897 | |
1898 | stream16.seek(pos: 0); |
1899 | stream16 << "one" ; |
1900 | stream16.flush(); |
1901 | |
1902 | QCOMPARE(out16.buffer(), first); |
1903 | } |
1904 | |
1905 | // ------------------------------------------------------------------------------ |
1906 | void tst_QTextStream::generateOperatorCharData(bool for_QString) |
1907 | { |
1908 | QTest::addColumn<QByteArray>(name: "input" ); |
1909 | QTest::addColumn<QChar>(name: "qchar_output" ); |
1910 | QTest::addColumn<char>(name: "char_output" ); |
1911 | QTest::addColumn<QByteArray>(name: "write_output" ); |
1912 | |
1913 | QTest::newRow(dataTag: "empty" ) << QByteArray() << QChar('\0') << '\0' << QByteArray("\0" , 1); |
1914 | QTest::newRow(dataTag: "a" ) << QByteArray("a" ) << QChar('a') << 'a' << QByteArray("a" ); |
1915 | QTest::newRow(dataTag: "\\na" ) << QByteArray("\na" ) << QChar('\n') << '\n' << QByteArray("\n" ); |
1916 | QTest::newRow(dataTag: "\\0" ) << QByteArray("\0" ) << QChar('\0') << '\0' << QByteArray("\0" , 1); |
1917 | QTest::newRow(dataTag: "\\xff" ) << QByteArray("\xff" ) << QChar('\xff') << '\xff' << QByteArray("\xff" ); |
1918 | QTest::newRow(dataTag: "\\xfe" ) << QByteArray("\xfe" ) << QChar('\xfe') << '\xfe' << QByteArray("\xfe" ); |
1919 | |
1920 | if (!for_QString) { |
1921 | QTest::newRow(dataTag: "utf16-BE (empty)" ) << QByteArray("\xff\xfe" , 2) << QChar('\0') << '\0' << QByteArray("\0" , 1); |
1922 | QTest::newRow(dataTag: "utf16-BE (a)" ) << QByteArray("\xff\xfe\x61\x00" , 4) << QChar('a') << 'a' << QByteArray("a" ); |
1923 | QTest::newRow(dataTag: "utf16-LE (empty)" ) << QByteArray("\xfe\xff" , 2) << QChar('\0') << '\0' << QByteArray("\0" , 1); |
1924 | QTest::newRow(dataTag: "utf16-LE (a)" ) << QByteArray("\xfe\xff\x00\x61" , 4) << QChar('a') << 'a' << QByteArray("a" ); |
1925 | } |
1926 | } |
1927 | |
1928 | // ------------------------------------------------------------------------------ |
1929 | void tst_QTextStream::QChar_operators_FromDevice_data() |
1930 | { |
1931 | generateOperatorCharData(for_QString: false); |
1932 | } |
1933 | |
1934 | // ------------------------------------------------------------------------------ |
1935 | void tst_QTextStream::QChar_operators_FromDevice() |
1936 | { |
1937 | QFETCH(QByteArray, input); |
1938 | QFETCH(QChar, qchar_output); |
1939 | QFETCH(QByteArray, write_output); |
1940 | |
1941 | QBuffer buf(&input); |
1942 | buf.open(openMode: QBuffer::ReadOnly); |
1943 | QTextStream stream(&buf); |
1944 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
1945 | QChar tmp; |
1946 | stream >> tmp; |
1947 | QCOMPARE(tmp, qchar_output); |
1948 | |
1949 | QBuffer writeBuf; |
1950 | writeBuf.open(openMode: QBuffer::WriteOnly); |
1951 | |
1952 | QTextStream writeStream(&writeBuf); |
1953 | writeStream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
1954 | writeStream << qchar_output; |
1955 | writeStream.flush(); |
1956 | |
1957 | QCOMPARE(writeBuf.buffer().size(), write_output.size()); |
1958 | QCOMPARE(writeBuf.buffer().constData(), write_output.constData()); |
1959 | } |
1960 | |
1961 | // ------------------------------------------------------------------------------ |
1962 | void tst_QTextStream::char_operators_FromDevice_data() |
1963 | { |
1964 | generateOperatorCharData(for_QString: false); |
1965 | } |
1966 | |
1967 | // ------------------------------------------------------------------------------ |
1968 | void tst_QTextStream::char_operators_FromDevice() |
1969 | { |
1970 | QFETCH(QByteArray, input); |
1971 | QFETCH(char, char_output); |
1972 | QFETCH(QByteArray, write_output); |
1973 | |
1974 | QBuffer buf(&input); |
1975 | buf.open(openMode: QBuffer::ReadOnly); |
1976 | QTextStream stream(&buf); |
1977 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
1978 | char tmp; |
1979 | stream >> tmp; |
1980 | QCOMPARE(tmp, char_output); |
1981 | |
1982 | QBuffer writeBuf; |
1983 | writeBuf.open(openMode: QBuffer::WriteOnly); |
1984 | |
1985 | QTextStream writeStream(&writeBuf); |
1986 | writeStream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
1987 | writeStream << char_output; |
1988 | writeStream.flush(); |
1989 | |
1990 | QCOMPARE(writeBuf.buffer().size(), write_output.size()); |
1991 | QCOMPARE(writeBuf.buffer().constData(), write_output.constData()); |
1992 | } |
1993 | |
1994 | // ------------------------------------------------------------------------------ |
1995 | void tst_QTextStream::generateNaturalNumbersData(bool for_QString) |
1996 | { |
1997 | QTest::addColumn<QByteArray>(name: "input" ); |
1998 | QTest::addColumn<qulonglong>(name: "output" ); |
1999 | |
2000 | QTest::newRow(dataTag: "empty" ) << QByteArray() << qulonglong(0); |
2001 | QTest::newRow(dataTag: "a" ) << QByteArray("a" ) << qulonglong(0); |
2002 | QTest::newRow(dataTag: " " ) << QByteArray(" " ) << qulonglong(0); |
2003 | QTest::newRow(dataTag: "0" ) << QByteArray("0" ) << qulonglong(0); |
2004 | QTest::newRow(dataTag: "1" ) << QByteArray("1" ) << qulonglong(1); |
2005 | QTest::newRow(dataTag: "12" ) << QByteArray("12" ) << qulonglong(12); |
2006 | QTest::newRow(dataTag: "-12" ) << QByteArray("-12" ) << qulonglong(-12); |
2007 | QTest::newRow(dataTag: "-0" ) << QByteArray("-0" ) << qulonglong(0); |
2008 | QTest::newRow(dataTag: " 1" ) << QByteArray(" 1" ) << qulonglong(1); |
2009 | QTest::newRow(dataTag: " \\r\\n\\r\\n123" ) << QByteArray(" \r\n\r\n123" ) << qulonglong(123); |
2010 | |
2011 | // bit boundary tests |
2012 | QTest::newRow(dataTag: "127" ) << QByteArray("127" ) << qulonglong(127); |
2013 | QTest::newRow(dataTag: "128" ) << QByteArray("128" ) << qulonglong(128); |
2014 | QTest::newRow(dataTag: "129" ) << QByteArray("129" ) << qulonglong(129); |
2015 | QTest::newRow(dataTag: "-127" ) << QByteArray("-127" ) << qulonglong(-127); |
2016 | QTest::newRow(dataTag: "-128" ) << QByteArray("-128" ) << qulonglong(-128); |
2017 | QTest::newRow(dataTag: "-129" ) << QByteArray("-129" ) << qulonglong(-129); |
2018 | QTest::newRow(dataTag: "32767" ) << QByteArray("32767" ) << qulonglong(32767); |
2019 | QTest::newRow(dataTag: "32768" ) << QByteArray("32768" ) << qulonglong(32768); |
2020 | QTest::newRow(dataTag: "32769" ) << QByteArray("32769" ) << qulonglong(32769); |
2021 | QTest::newRow(dataTag: "-32767" ) << QByteArray("-32767" ) << qulonglong(-32767); |
2022 | QTest::newRow(dataTag: "-32768" ) << QByteArray("-32768" ) << qulonglong(-32768); |
2023 | QTest::newRow(dataTag: "-32769" ) << QByteArray("-32769" ) << qulonglong(-32769); |
2024 | QTest::newRow(dataTag: "65537" ) << QByteArray("65537" ) << qulonglong(65537); |
2025 | QTest::newRow(dataTag: "65536" ) << QByteArray("65536" ) << qulonglong(65536); |
2026 | QTest::newRow(dataTag: "65535" ) << QByteArray("65535" ) << qulonglong(65535); |
2027 | QTest::newRow(dataTag: "-65537" ) << QByteArray("-65537" ) << qulonglong(-65537); |
2028 | QTest::newRow(dataTag: "-65536" ) << QByteArray("-65536" ) << qulonglong(-65536); |
2029 | QTest::newRow(dataTag: "-65535" ) << QByteArray("-65535" ) << qulonglong(-65535); |
2030 | QTest::newRow(dataTag: "2147483646" ) << QByteArray("2147483646" ) << qulonglong(2147483646); |
2031 | QTest::newRow(dataTag: "2147483647" ) << QByteArray("2147483647" ) << qulonglong(2147483647); |
2032 | QTest::newRow(dataTag: "2147483648" ) << QByteArray("2147483648" ) << Q_UINT64_C(2147483648); |
2033 | QTest::newRow(dataTag: "-2147483646" ) << QByteArray("-2147483646" ) << qulonglong(-2147483646); |
2034 | QTest::newRow(dataTag: "-2147483647" ) << QByteArray("-2147483647" ) << qulonglong(-2147483647); |
2035 | QTest::newRow(dataTag: "-2147483648" ) << QByteArray("-2147483648" ) << quint64(-2147483648LL); |
2036 | QTest::newRow(dataTag: "4294967296" ) << QByteArray("4294967296" ) << Q_UINT64_C(4294967296); |
2037 | QTest::newRow(dataTag: "4294967297" ) << QByteArray("4294967297" ) << Q_UINT64_C(4294967297); |
2038 | QTest::newRow(dataTag: "4294967298" ) << QByteArray("4294967298" ) << Q_UINT64_C(4294967298); |
2039 | QTest::newRow(dataTag: "-4294967296" ) << QByteArray("-4294967296" ) << quint64(-4294967296); |
2040 | QTest::newRow(dataTag: "-4294967297" ) << QByteArray("-4294967297" ) << quint64(-4294967297); |
2041 | QTest::newRow(dataTag: "-4294967298" ) << QByteArray("-4294967298" ) << quint64(-4294967298); |
2042 | QTest::newRow(dataTag: "9223372036854775807" ) << QByteArray("9223372036854775807" ) << Q_UINT64_C(9223372036854775807); |
2043 | QTest::newRow(dataTag: "9223372036854775808" ) << QByteArray("9223372036854775808" ) << Q_UINT64_C(9223372036854775808); |
2044 | QTest::newRow(dataTag: "9223372036854775809" ) << QByteArray("9223372036854775809" ) << Q_UINT64_C(9223372036854775809); |
2045 | QTest::newRow(dataTag: "18446744073709551615" ) << QByteArray("18446744073709551615" ) << Q_UINT64_C(18446744073709551615); |
2046 | QTest::newRow(dataTag: "18446744073709551616" ) << QByteArray("18446744073709551616" ) << Q_UINT64_C(0); |
2047 | QTest::newRow(dataTag: "18446744073709551617" ) << QByteArray("18446744073709551617" ) << Q_UINT64_C(1); |
2048 | // 18446744073709551617 bytes should be enough for anyone.... ;-) |
2049 | |
2050 | // hex tests |
2051 | QTest::newRow(dataTag: "0x0" ) << QByteArray("0x0" ) << qulonglong(0); |
2052 | QTest::newRow(dataTag: "0x" ) << QByteArray("0x" ) << qulonglong(0); |
2053 | QTest::newRow(dataTag: "0x1" ) << QByteArray("0x1" ) << qulonglong(1); |
2054 | QTest::newRow(dataTag: "0xf" ) << QByteArray("0xf" ) << qulonglong(15); |
2055 | QTest::newRow(dataTag: "0xdeadbeef" ) << QByteArray("0xdeadbeef" ) << Q_UINT64_C(3735928559); |
2056 | QTest::newRow(dataTag: "0XDEADBEEF" ) << QByteArray("0XDEADBEEF" ) << Q_UINT64_C(3735928559); |
2057 | QTest::newRow(dataTag: "0xdeadbeefZzzzz" ) << QByteArray("0xdeadbeefZzzzz" ) << Q_UINT64_C(3735928559); |
2058 | QTest::newRow(dataTag: " 0xdeadbeefZzzzz" ) << QByteArray(" 0xdeadbeefZzzzz" ) << Q_UINT64_C(3735928559); |
2059 | |
2060 | // oct tests |
2061 | QTest::newRow(dataTag: "00" ) << QByteArray("00" ) << qulonglong(0); |
2062 | QTest::newRow(dataTag: "0141" ) << QByteArray("0141" ) << qulonglong(97); |
2063 | QTest::newRow(dataTag: "01419999" ) << QByteArray("01419999" ) << qulonglong(97); |
2064 | QTest::newRow(dataTag: " 01419999" ) << QByteArray(" 01419999" ) << qulonglong(97); |
2065 | |
2066 | // bin tests |
2067 | QTest::newRow(dataTag: "0b0" ) << QByteArray("0b0" ) << qulonglong(0); |
2068 | QTest::newRow(dataTag: "0b1" ) << QByteArray("0b1" ) << qulonglong(1); |
2069 | QTest::newRow(dataTag: "0b10" ) << QByteArray("0b10" ) << qulonglong(2); |
2070 | QTest::newRow(dataTag: "0B10" ) << QByteArray("0B10" ) << qulonglong(2); |
2071 | QTest::newRow(dataTag: "0b101010" ) << QByteArray("0b101010" ) << qulonglong(42); |
2072 | QTest::newRow(dataTag: "0b1010102345" ) << QByteArray("0b1010102345" ) << qulonglong(42); |
2073 | QTest::newRow(dataTag: " 0b1010102345" ) << QByteArray(" 0b1010102345" ) << qulonglong(42); |
2074 | |
2075 | // utf-16 tests |
2076 | if (!for_QString) { |
2077 | QTest::newRow(dataTag: "utf16-BE (empty)" ) << QByteArray("\xfe\xff" , 2) << qulonglong(0); |
2078 | QTest::newRow(dataTag: "utf16-BE (0xdeadbeef)" ) |
2079 | << QByteArray("\xfe\xff" |
2080 | "\x00\x30\x00\x78\x00\x64\x00\x65\x00\x61\x00\x64\x00\x62\x00\x65\x00\x65\x00\x66" , 22) |
2081 | << Q_UINT64_C(3735928559); |
2082 | QTest::newRow(dataTag: "utf16-LE (empty)" ) << QByteArray("\xff\xfe" , 2) << Q_UINT64_C(0); |
2083 | QTest::newRow(dataTag: "utf16-LE (0xdeadbeef)" ) |
2084 | << QByteArray("\xff\xfe" |
2085 | "\x30\x00\x78\x00\x64\x00\x65\x00\x61\x00\x64\x00\x62\x00\x65\x00\x65\x00\x66\x00" , 22) |
2086 | << Q_UINT64_C(3735928559); |
2087 | } |
2088 | } |
2089 | |
2090 | // ------------------------------------------------------------------------------ |
2091 | #define IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(texttype, type) \ |
2092 | void tst_QTextStream:: texttype##_read_operator_FromDevice_data() \ |
2093 | { generateNaturalNumbersData(false); } \ |
2094 | void tst_QTextStream:: texttype##_read_operator_FromDevice() \ |
2095 | { \ |
2096 | QFETCH(QByteArray, input); \ |
2097 | QFETCH(qulonglong, output); \ |
2098 | type sh; \ |
2099 | QTextStream stream(&input); \ |
2100 | stream >> sh; \ |
2101 | QCOMPARE(sh, (type)output); \ |
2102 | } |
2103 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(signedShort, signed short) |
2104 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(unsignedShort, unsigned short) |
2105 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(signedInt, signed int) |
2106 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(unsignedInt, unsigned int) |
2107 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(qlonglong, qlonglong) |
2108 | IMPLEMENT_STREAM_RIGHT_INT_OPERATOR_TEST(qulonglong, qulonglong) |
2109 | ; |
2110 | |
2111 | // ------------------------------------------------------------------------------ |
2112 | void tst_QTextStream::generateRealNumbersData(bool for_QString) |
2113 | { |
2114 | QTest::addColumn<QByteArray>(name: "input" ); |
2115 | QTest::addColumn<double>(name: "output" ); |
2116 | |
2117 | QTest::newRow(dataTag: "empty" ) << QByteArray() << 0.0; |
2118 | QTest::newRow(dataTag: "a" ) << QByteArray("a" ) << 0.0; |
2119 | QTest::newRow(dataTag: "1.0" ) << QByteArray("1.0" ) << 1.0; |
2120 | QTest::newRow(dataTag: " 1" ) << QByteArray(" 1" ) << 1.0; |
2121 | QTest::newRow(dataTag: " \\r\\n1.2" ) << QByteArray(" \r\n1.2" ) << 1.2; |
2122 | QTest::newRow(dataTag: "3.14" ) << QByteArray("3.14" ) << 3.14; |
2123 | QTest::newRow(dataTag: "-3.14" ) << QByteArray("-3.14" ) << -3.14; |
2124 | QTest::newRow(dataTag: " -3.14" ) << QByteArray(" -3.14" ) << -3.14; |
2125 | QTest::newRow(dataTag: "314e-02" ) << QByteArray("314e-02" ) << 3.14; |
2126 | QTest::newRow(dataTag: "314E-02" ) << QByteArray("314E-02" ) << 3.14; |
2127 | QTest::newRow(dataTag: "314e+02" ) << QByteArray("314e+02" ) << 31400.; |
2128 | QTest::newRow(dataTag: "314E+02" ) << QByteArray("314E+02" ) << 31400.; |
2129 | |
2130 | // ### add numbers with exponents |
2131 | |
2132 | if (!for_QString) { |
2133 | QTest::newRow(dataTag: "utf16-BE (empty)" ) << QByteArray("\xff\xfe" , 2) << 0.0; |
2134 | QTest::newRow(dataTag: "utf16-LE (empty)" ) << QByteArray("\xfe\xff" , 2) << 0.0; |
2135 | } |
2136 | } |
2137 | |
2138 | // ------------------------------------------------------------------------------ |
2139 | #define IMPLEMENT_STREAM_RIGHT_REAL_OPERATOR_TEST(texttype, type) \ |
2140 | void tst_QTextStream:: texttype##_read_operator_FromDevice_data() \ |
2141 | { generateRealNumbersData(false); } \ |
2142 | void tst_QTextStream:: texttype##_read_operator_FromDevice() \ |
2143 | { \ |
2144 | QFETCH(QByteArray, input); \ |
2145 | QFETCH(double, output); \ |
2146 | type sh; \ |
2147 | QTextStream stream(&input); \ |
2148 | stream >> sh; \ |
2149 | QCOMPARE(sh, (type)output); \ |
2150 | } |
2151 | IMPLEMENT_STREAM_RIGHT_REAL_OPERATOR_TEST(float, float) |
2152 | IMPLEMENT_STREAM_RIGHT_REAL_OPERATOR_TEST(double, double) |
2153 | ; |
2154 | |
2155 | // ------------------------------------------------------------------------------ |
2156 | void tst_QTextStream::generateStringData(bool for_QString) |
2157 | { |
2158 | QTest::addColumn<QByteArray>(name: "input" ); |
2159 | QTest::addColumn<QByteArray>(name: "array_output" ); |
2160 | QTest::addColumn<QString>(name: "string_output" ); |
2161 | |
2162 | QTest::newRow(dataTag: "empty" ) << QByteArray() << QByteArray() << QString(); |
2163 | QTest::newRow(dataTag: "a" ) << QByteArray("a" ) << QByteArray("a" ) << QString("a" ); |
2164 | QTest::newRow(dataTag: "a b" ) << QByteArray("a b" ) << QByteArray("a" ) << QString("a" ); |
2165 | QTest::newRow(dataTag: " a b" ) << QByteArray(" a b" ) << QByteArray("a" ) << QString("a" ); |
2166 | QTest::newRow(dataTag: "a1" ) << QByteArray("a1" ) << QByteArray("a1" ) << QString("a1" ); |
2167 | QTest::newRow(dataTag: "a1 b1" ) << QByteArray("a1 b1" ) << QByteArray("a1" ) << QString("a1" ); |
2168 | QTest::newRow(dataTag: " a1 b1" ) << QByteArray(" a1 b1" ) << QByteArray("a1" ) << QString("a1" ); |
2169 | QTest::newRow(dataTag: "\\n\\n\\nole i dole\\n" ) << QByteArray("\n\n\nole i dole\n" ) << QByteArray("ole" ) << QString("ole" ); |
2170 | |
2171 | if (!for_QString) { |
2172 | QTest::newRow(dataTag: "utf16-BE (empty)" ) << QByteArray("\xff\xfe" , 2) << QByteArray() << QString(); |
2173 | QTest::newRow(dataTag: "utf16-BE (corrupt)" ) << QByteArray("\xff" , 1) << QByteArray("\xff" ) << QString::fromLatin1(str: "\xff" ); |
2174 | QTest::newRow(dataTag: "utf16-LE (empty)" ) << QByteArray("\xfe\xff" , 2) << QByteArray() << QString(); |
2175 | QTest::newRow(dataTag: "utf16-LE (corrupt)" ) << QByteArray("\xfe" , 1) << QByteArray("\xfe" ) << QString::fromLatin1(str: "\xfe" ); |
2176 | } |
2177 | } |
2178 | |
2179 | // ------------------------------------------------------------------------------ |
2180 | void tst_QTextStream::charPtr_read_operator_FromDevice_data() |
2181 | { |
2182 | generateStringData(for_QString: false); |
2183 | } |
2184 | |
2185 | // ------------------------------------------------------------------------------ |
2186 | void tst_QTextStream::charPtr_read_operator_FromDevice() |
2187 | { |
2188 | QFETCH(QByteArray, input); |
2189 | QFETCH(QByteArray, array_output); |
2190 | |
2191 | QBuffer buffer(&input); |
2192 | buffer.open(openMode: QBuffer::ReadOnly); |
2193 | QTextStream stream(&buffer); |
2194 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2195 | stream.setAutoDetectUnicode(true); |
2196 | |
2197 | char buf[1024]; |
2198 | stream >> buf; |
2199 | |
2200 | QCOMPARE((const char *)buf, array_output.constData()); |
2201 | } |
2202 | |
2203 | // ------------------------------------------------------------------------------ |
2204 | void tst_QTextStream::stringRef_read_operator_FromDevice_data() |
2205 | { |
2206 | generateStringData(for_QString: false); |
2207 | } |
2208 | |
2209 | // ------------------------------------------------------------------------------ |
2210 | void tst_QTextStream::stringRef_read_operator_FromDevice() |
2211 | { |
2212 | QFETCH(QByteArray, input); |
2213 | QFETCH(QString, string_output); |
2214 | |
2215 | QBuffer buffer(&input); |
2216 | buffer.open(openMode: QBuffer::ReadOnly); |
2217 | QTextStream stream(&buffer); |
2218 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2219 | stream.setAutoDetectUnicode(true); |
2220 | |
2221 | QString tmp; |
2222 | stream >> tmp; |
2223 | |
2224 | QCOMPARE(tmp, string_output); |
2225 | } |
2226 | |
2227 | // ------------------------------------------------------------------------------ |
2228 | void tst_QTextStream::byteArray_read_operator_FromDevice_data() |
2229 | { |
2230 | generateStringData(for_QString: false); |
2231 | } |
2232 | |
2233 | // ------------------------------------------------------------------------------ |
2234 | void tst_QTextStream::byteArray_read_operator_FromDevice() |
2235 | { |
2236 | QFETCH(QByteArray, input); |
2237 | QFETCH(QByteArray, array_output); |
2238 | |
2239 | QBuffer buffer(&input); |
2240 | buffer.open(openMode: QBuffer::ReadOnly); |
2241 | QTextStream stream(&buffer); |
2242 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2243 | stream.setAutoDetectUnicode(true); |
2244 | |
2245 | QByteArray array; |
2246 | stream >> array; |
2247 | |
2248 | QCOMPARE(array, array_output); |
2249 | } |
2250 | |
2251 | // ------------------------------------------------------------------------------ |
2252 | #define IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(texttype, type) \ |
2253 | void tst_QTextStream:: texttype##_write_operator_ToDevice() \ |
2254 | { \ |
2255 | QFETCH(qulonglong, number); \ |
2256 | QFETCH(QByteArray, data); \ |
2257 | QFETCH(QByteArray, dataWithSeparators); \ |
2258 | \ |
2259 | QBuffer buffer; \ |
2260 | buffer.open(QBuffer::WriteOnly); \ |
2261 | QTextStream stream(&buffer); \ |
2262 | stream.setLocale(QLocale::c()); \ |
2263 | stream << (type)number; \ |
2264 | stream.flush(); \ |
2265 | QCOMPARE(buffer.data().constData(), data.constData()); \ |
2266 | \ |
2267 | QLocale locale("en-US"); \ |
2268 | buffer.reset(); buffer.buffer().clear(); \ |
2269 | stream.setLocale(locale); \ |
2270 | stream << (type)number; \ |
2271 | stream.flush(); \ |
2272 | QCOMPARE(buffer.data(), dataWithSeparators); \ |
2273 | \ |
2274 | locale.setNumberOptions(QLocale::OmitGroupSeparator); \ |
2275 | buffer.reset(); buffer.buffer().clear(); \ |
2276 | stream.setLocale(locale); \ |
2277 | stream << (type)number; \ |
2278 | stream.flush(); \ |
2279 | QCOMPARE(buffer.data().constData(), data.constData()); \ |
2280 | \ |
2281 | locale = QLocale("de-DE"); \ |
2282 | buffer.reset(); buffer.buffer().clear(); \ |
2283 | stream.setLocale(locale); \ |
2284 | stream << (type)number; \ |
2285 | stream.flush(); \ |
2286 | QCOMPARE(buffer.data(), dataWithSeparators.replace(',', '.')); \ |
2287 | } |
2288 | |
2289 | // ------------------------------------------------------------------------------ |
2290 | void tst_QTextStream::signedShort_write_operator_ToDevice_data() |
2291 | { |
2292 | QTest::addColumn<qulonglong>(name: "number" ); |
2293 | QTest::addColumn<QByteArray>(name: "data" ); |
2294 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2295 | |
2296 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2297 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2298 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("-1" ) << QByteArray("-1" ); |
2299 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2300 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("-32768" ) << QByteArray("-32,768" ); |
2301 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("-32767" ) << QByteArray("-32,767" ); |
2302 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("-1" ) << QByteArray("-1" ); |
2303 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("0" ) << QByteArray("0" ); |
2304 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("1" ) << QByteArray("1" ); |
2305 | } |
2306 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(signedShort, signed short) |
2307 | ; |
2308 | |
2309 | // ------------------------------------------------------------------------------ |
2310 | void tst_QTextStream::unsignedShort_write_operator_ToDevice_data() |
2311 | { |
2312 | QTest::addColumn<qulonglong>(name: "number" ); |
2313 | QTest::addColumn<QByteArray>(name: "data" ); |
2314 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2315 | |
2316 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2317 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2318 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("65535" ) << QByteArray("65,535" ); |
2319 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2320 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("32768" ) << QByteArray("32,768" ); |
2321 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("32769" ) << QByteArray("32,769" ); |
2322 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("65535" ) << QByteArray("65,535" ); |
2323 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("0" ) << QByteArray("0" ); |
2324 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("1" ) << QByteArray("1" ); |
2325 | } |
2326 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(unsignedShort, unsigned short) |
2327 | ; |
2328 | |
2329 | // ------------------------------------------------------------------------------ |
2330 | void tst_QTextStream::signedInt_write_operator_ToDevice_data() |
2331 | { |
2332 | QTest::addColumn<qulonglong>(name: "number" ); |
2333 | QTest::addColumn<QByteArray>(name: "data" ); |
2334 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2335 | |
2336 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2337 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2338 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("-1" ) << QByteArray("-1" ); |
2339 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2340 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("32768" ) << QByteArray("32,768" ); |
2341 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("32769" ) << QByteArray("32,769" ); |
2342 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("65535" ) << QByteArray("65,535" ); |
2343 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("65536" ) << QByteArray("65,536" ); |
2344 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("65537" ) << QByteArray("65,537" ); |
2345 | QTest::newRow(dataTag: "2147483647" ) << Q_UINT64_C(2147483647) << QByteArray("2147483647" ) << QByteArray("2,147,483,647" ); |
2346 | QTest::newRow(dataTag: "2147483648" ) << Q_UINT64_C(2147483648) << QByteArray("-2147483648" ) << QByteArray("-2,147,483,648" ); |
2347 | QTest::newRow(dataTag: "2147483649" ) << Q_UINT64_C(2147483649) << QByteArray("-2147483647" ) << QByteArray("-2,147,483,647" ); |
2348 | QTest::newRow(dataTag: "4294967295" ) << Q_UINT64_C(4294967295) << QByteArray("-1" ) << QByteArray("-1" ); |
2349 | QTest::newRow(dataTag: "4294967296" ) << Q_UINT64_C(4294967296) << QByteArray("0" ) << QByteArray("0" ); |
2350 | QTest::newRow(dataTag: "4294967297" ) << Q_UINT64_C(4294967297) << QByteArray("1" ) << QByteArray("1" ); |
2351 | } |
2352 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(signedInt, signed int) |
2353 | ; |
2354 | |
2355 | // ------------------------------------------------------------------------------ |
2356 | void tst_QTextStream::unsignedInt_write_operator_ToDevice_data() |
2357 | { |
2358 | QTest::addColumn<qulonglong>(name: "number" ); |
2359 | QTest::addColumn<QByteArray>(name: "data" ); |
2360 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2361 | |
2362 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2363 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2364 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("4294967295" ) << QByteArray("4,294,967,295" ); |
2365 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2366 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("32768" ) << QByteArray("32,768" ); |
2367 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("32769" ) << QByteArray("32,769" ); |
2368 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("65535" ) << QByteArray("65,535" ); |
2369 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("65536" ) << QByteArray("65,536" ); |
2370 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("65537" ) << QByteArray("65,537" ); |
2371 | QTest::newRow(dataTag: "2147483647" ) << Q_UINT64_C(2147483647) << QByteArray("2147483647" ) << QByteArray("2,147,483,647" ); |
2372 | QTest::newRow(dataTag: "2147483648" ) << Q_UINT64_C(2147483648) << QByteArray("2147483648" ) << QByteArray("2,147,483,648" ); |
2373 | QTest::newRow(dataTag: "2147483649" ) << Q_UINT64_C(2147483649) << QByteArray("2147483649" ) << QByteArray("2,147,483,649" ); |
2374 | QTest::newRow(dataTag: "4294967295" ) << Q_UINT64_C(4294967295) << QByteArray("4294967295" ) << QByteArray("4,294,967,295" ); |
2375 | QTest::newRow(dataTag: "4294967296" ) << Q_UINT64_C(4294967296) << QByteArray("0" ) << QByteArray("0" ); |
2376 | QTest::newRow(dataTag: "4294967297" ) << Q_UINT64_C(4294967297) << QByteArray("1" ) << QByteArray("1" ); |
2377 | } |
2378 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(unsignedInt, unsigned int) |
2379 | ; |
2380 | |
2381 | // ------------------------------------------------------------------------------ |
2382 | void tst_QTextStream::qlonglong_write_operator_ToDevice_data() |
2383 | { |
2384 | QTest::addColumn<qulonglong>(name: "number" ); |
2385 | QTest::addColumn<QByteArray>(name: "data" ); |
2386 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2387 | |
2388 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2389 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2390 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("-1" ) << QByteArray("-1" ); |
2391 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2392 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("32768" ) << QByteArray("32,768" ); |
2393 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("32769" ) << QByteArray("32,769" ); |
2394 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("65535" ) << QByteArray("65,535" ); |
2395 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("65536" ) << QByteArray("65,536" ); |
2396 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("65537" ) << QByteArray("65,537" ); |
2397 | QTest::newRow(dataTag: "2147483647" ) << Q_UINT64_C(2147483647) << QByteArray("2147483647" ) << QByteArray("2,147,483,647" ); |
2398 | QTest::newRow(dataTag: "2147483648" ) << Q_UINT64_C(2147483648) << QByteArray("2147483648" ) << QByteArray("2,147,483,648" ); |
2399 | QTest::newRow(dataTag: "2147483649" ) << Q_UINT64_C(2147483649) << QByteArray("2147483649" ) << QByteArray("2,147,483,649" ); |
2400 | QTest::newRow(dataTag: "4294967295" ) << Q_UINT64_C(4294967295) << QByteArray("4294967295" ) << QByteArray("4,294,967,295" ); |
2401 | QTest::newRow(dataTag: "4294967296" ) << Q_UINT64_C(4294967296) << QByteArray("4294967296" ) << QByteArray("4,294,967,296" ); |
2402 | QTest::newRow(dataTag: "4294967297" ) << Q_UINT64_C(4294967297) << QByteArray("4294967297" ) << QByteArray("4,294,967,297" ); |
2403 | QTest::newRow(dataTag: "9223372036854775807" ) << Q_UINT64_C(9223372036854775807) << QByteArray("9223372036854775807" ) << QByteArray("9,223,372,036,854,775,807" ); |
2404 | QTest::newRow(dataTag: "9223372036854775808" ) << Q_UINT64_C(9223372036854775808) << QByteArray("-9223372036854775808" ) << QByteArray("-9,223,372,036,854,775,808" ); |
2405 | QTest::newRow(dataTag: "9223372036854775809" ) << Q_UINT64_C(9223372036854775809) << QByteArray("-9223372036854775807" ) << QByteArray("-9,223,372,036,854,775,807" ); |
2406 | QTest::newRow(dataTag: "18446744073709551615" ) << Q_UINT64_C(18446744073709551615) << QByteArray("-1" ) << QByteArray("-1" ); |
2407 | } |
2408 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(qlonglong, qlonglong) |
2409 | ; |
2410 | |
2411 | // ------------------------------------------------------------------------------ |
2412 | void tst_QTextStream::qulonglong_write_operator_ToDevice_data() |
2413 | { |
2414 | QTest::addColumn<qulonglong>(name: "number" ); |
2415 | QTest::addColumn<QByteArray>(name: "data" ); |
2416 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2417 | |
2418 | QTest::newRow(dataTag: "0" ) << Q_UINT64_C(0) << QByteArray("0" ) << QByteArray("0" ); |
2419 | QTest::newRow(dataTag: "1" ) << Q_UINT64_C(1) << QByteArray("1" ) << QByteArray("1" ); |
2420 | QTest::newRow(dataTag: "-1" ) << quint64(-1) << QByteArray("18446744073709551615" ) << QByteArray("18,446,744,073,709,551,615" ); |
2421 | QTest::newRow(dataTag: "32767" ) << Q_UINT64_C(32767) << QByteArray("32767" ) << QByteArray("32,767" ); |
2422 | QTest::newRow(dataTag: "32768" ) << Q_UINT64_C(32768) << QByteArray("32768" ) << QByteArray("32,768" ); |
2423 | QTest::newRow(dataTag: "32769" ) << Q_UINT64_C(32769) << QByteArray("32769" ) << QByteArray("32,769" ); |
2424 | QTest::newRow(dataTag: "65535" ) << Q_UINT64_C(65535) << QByteArray("65535" ) << QByteArray("65,535" ); |
2425 | QTest::newRow(dataTag: "65536" ) << Q_UINT64_C(65536) << QByteArray("65536" ) << QByteArray("65,536" ); |
2426 | QTest::newRow(dataTag: "65537" ) << Q_UINT64_C(65537) << QByteArray("65537" ) << QByteArray("65,537" ); |
2427 | QTest::newRow(dataTag: "2147483647" ) << Q_UINT64_C(2147483647) << QByteArray("2147483647" ) << QByteArray("2,147,483,647" ); |
2428 | QTest::newRow(dataTag: "2147483648" ) << Q_UINT64_C(2147483648) << QByteArray("2147483648" ) << QByteArray("2,147,483,648" ); |
2429 | QTest::newRow(dataTag: "2147483649" ) << Q_UINT64_C(2147483649) << QByteArray("2147483649" ) << QByteArray("2,147,483,649" ); |
2430 | QTest::newRow(dataTag: "4294967295" ) << Q_UINT64_C(4294967295) << QByteArray("4294967295" ) << QByteArray("4,294,967,295" ); |
2431 | QTest::newRow(dataTag: "4294967296" ) << Q_UINT64_C(4294967296) << QByteArray("4294967296" ) << QByteArray("4,294,967,296" ); |
2432 | QTest::newRow(dataTag: "4294967297" ) << Q_UINT64_C(4294967297) << QByteArray("4294967297" ) << QByteArray("4,294,967,297" ); |
2433 | QTest::newRow(dataTag: "9223372036854775807" ) << Q_UINT64_C(9223372036854775807) << QByteArray("9223372036854775807" ) << QByteArray("9,223,372,036,854,775,807" ); |
2434 | QTest::newRow(dataTag: "9223372036854775808" ) << Q_UINT64_C(9223372036854775808) << QByteArray("9223372036854775808" ) << QByteArray("9,223,372,036,854,775,808" ); |
2435 | QTest::newRow(dataTag: "9223372036854775809" ) << Q_UINT64_C(9223372036854775809) << QByteArray("9223372036854775809" ) << QByteArray("9,223,372,036,854,775,809" ); |
2436 | QTest::newRow(dataTag: "18446744073709551615" ) << Q_UINT64_C(18446744073709551615) << QByteArray("18446744073709551615" ) << QByteArray("18,446,744,073,709,551,615" ); |
2437 | } |
2438 | IMPLEMENT_STREAM_LEFT_INT_OPERATOR_TEST(qulonglong, qulonglong) |
2439 | ; |
2440 | |
2441 | |
2442 | // ------------------------------------------------------------------------------ |
2443 | void tst_QTextStream::generateRealNumbersDataWrite() |
2444 | { |
2445 | QTest::addColumn<double>(name: "number" ); |
2446 | QTest::addColumn<QByteArray>(name: "data" ); |
2447 | QTest::addColumn<QByteArray>(name: "dataWithSeparators" ); |
2448 | |
2449 | QTest::newRow(dataTag: "0" ) << 0.0 << QByteArray("0" ) << QByteArray("0" ); |
2450 | QTest::newRow(dataTag: "3.14" ) << 3.14 << QByteArray("3.14" ) << QByteArray("3.14" ); |
2451 | QTest::newRow(dataTag: "-3.14" ) << -3.14 << QByteArray("-3.14" ) << QByteArray("-3.14" ); |
2452 | QTest::newRow(dataTag: "1.2e+10" ) << 1.2e+10 << QByteArray("1.2e+10" ) << QByteArray("1.2e+10" ); |
2453 | QTest::newRow(dataTag: "-1.2e+10" ) << -1.2e+10 << QByteArray("-1.2e+10" ) << QByteArray("-1.2e+10" ); |
2454 | QTest::newRow(dataTag: "12345" ) << 12345. << QByteArray("12345" ) << QByteArray("12,345" ); |
2455 | } |
2456 | |
2457 | // ------------------------------------------------------------------------------ |
2458 | #define IMPLEMENT_STREAM_LEFT_REAL_OPERATOR_TEST(texttype, type) \ |
2459 | void tst_QTextStream:: texttype##_write_operator_ToDevice_data() \ |
2460 | { generateRealNumbersDataWrite(); } \ |
2461 | void tst_QTextStream:: texttype##_write_operator_ToDevice() \ |
2462 | { \ |
2463 | QFETCH(double, number); \ |
2464 | QFETCH(QByteArray, data); \ |
2465 | QFETCH(QByteArray, dataWithSeparators); \ |
2466 | \ |
2467 | QBuffer buffer; \ |
2468 | buffer.open(QBuffer::WriteOnly); \ |
2469 | QTextStream stream(&buffer); \ |
2470 | stream.setLocale(QLocale::c()); \ |
2471 | float f = (float)number; \ |
2472 | stream << f; \ |
2473 | stream.flush(); \ |
2474 | QCOMPARE(buffer.data().constData(), data.constData()); \ |
2475 | \ |
2476 | buffer.reset(); \ |
2477 | stream.setLocale(QLocale("en-US")); \ |
2478 | stream << f; \ |
2479 | stream.flush(); \ |
2480 | QCOMPARE(buffer.data(), dataWithSeparators); \ |
2481 | } |
2482 | IMPLEMENT_STREAM_LEFT_REAL_OPERATOR_TEST(float, float) |
2483 | IMPLEMENT_STREAM_LEFT_REAL_OPERATOR_TEST(double, float) |
2484 | ; |
2485 | |
2486 | // ------------------------------------------------------------------------------ |
2487 | void tst_QTextStream::string_write_operator_ToDevice_data() |
2488 | { |
2489 | QTest::addColumn<QByteArray>(name: "bytedata" ); |
2490 | QTest::addColumn<QString>(name: "stringdata" ); |
2491 | QTest::addColumn<QByteArray>(name: "result" ); |
2492 | |
2493 | QTest::newRow(dataTag: "empty" ) << QByteArray("" , 1) << QString(1, '\0') << QByteArray("" , 1); |
2494 | QTest::newRow(dataTag: "a" ) << QByteArray("a" ) << QString("a" ) << QByteArray("a" ); |
2495 | QTest::newRow(dataTag: "a cow jumped over the moon" ) |
2496 | << QByteArray("a cow jumped over the moon" ) |
2497 | << QString("a cow jumped over the moon" ) |
2498 | << QByteArray("a cow jumped over the moon" ); |
2499 | |
2500 | // ### get the utf16-be test on its legs. |
2501 | /* |
2502 | QTest::newRow("utf16-BE (a cow jumped over the moon)") |
2503 | << QByteArray("\xff\xfe\x00\x61\x00\x20\x00\x63\x00\x6f\x00\x77\x00\x20\x00\x6a\x00\x75\x00\x6d\x00\x70\x00\x65\x00\x64\x00\x20\x00\x6f\x00\x76\x00\x65\x00\x72\x00\x20\x00\x74\x00\x68\x00\x65\x00\x20\x00\x6d\x00\x6f\x00\x6f\x00\x6e\x00\x0a", 56) |
2504 | << QString("a cow jumped over the moon") |
2505 | << QByteArray("a cow jumped over the moon"); |
2506 | */ |
2507 | } |
2508 | |
2509 | // ------------------------------------------------------------------------------ |
2510 | void tst_QTextStream::string_write_operator_ToDevice() |
2511 | { |
2512 | QFETCH(QByteArray, bytedata); |
2513 | QFETCH(QString, stringdata); |
2514 | QFETCH(QByteArray, result); |
2515 | |
2516 | { |
2517 | // char* |
2518 | QBuffer buf; |
2519 | buf.open(openMode: QBuffer::WriteOnly); |
2520 | QTextStream stream(&buf); |
2521 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2522 | stream.setAutoDetectUnicode(true); |
2523 | |
2524 | stream << bytedata.constData(); |
2525 | stream.flush(); |
2526 | QCOMPARE(buf.buffer().constData(), result.constData()); |
2527 | } |
2528 | { |
2529 | // QByteArray |
2530 | QBuffer buf; |
2531 | buf.open(openMode: QBuffer::WriteOnly); |
2532 | QTextStream stream(&buf); |
2533 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2534 | stream.setAutoDetectUnicode(true); |
2535 | |
2536 | stream << bytedata; |
2537 | stream.flush(); |
2538 | QCOMPARE(buf.buffer().constData(), result.constData()); |
2539 | } |
2540 | { |
2541 | // QString |
2542 | QBuffer buf; |
2543 | buf.open(openMode: QBuffer::WriteOnly); |
2544 | QTextStream stream(&buf); |
2545 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2546 | stream.setAutoDetectUnicode(true); |
2547 | |
2548 | stream << stringdata; |
2549 | stream.flush(); |
2550 | QCOMPARE(buf.buffer().constData(), result.constData()); |
2551 | } |
2552 | } |
2553 | |
2554 | void tst_QTextStream::latin1String_write_operator_ToDevice() |
2555 | { |
2556 | QBuffer buf; |
2557 | buf.open(openMode: QBuffer::WriteOnly); |
2558 | QTextStream stream(&buf); |
2559 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2560 | stream.setAutoDetectUnicode(true); |
2561 | |
2562 | stream << QLatin1String("No explicit length" ); |
2563 | stream << QLatin1String("Explicit length - ignore this part" , 15); |
2564 | stream.flush(); |
2565 | QCOMPARE(buf.buffer().constData(), "No explicit lengthExplicit length" ); |
2566 | } |
2567 | |
2568 | void tst_QTextStream::stringref_write_operator_ToDevice() |
2569 | { |
2570 | QBuffer buf; |
2571 | buf.open(openMode: QBuffer::WriteOnly); |
2572 | QTextStream stream(&buf); |
2573 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2574 | stream.setAutoDetectUnicode(true); |
2575 | |
2576 | const QString expected = "No explicit lengthExplicit length" ; |
2577 | |
2578 | stream << expected.leftRef(n: 18); |
2579 | stream << expected.midRef(position: 18); |
2580 | stream.flush(); |
2581 | QCOMPARE(buf.buffer().constData(), "No explicit lengthExplicit length" ); |
2582 | } |
2583 | |
2584 | void tst_QTextStream::stringview_write_operator_ToDevice() |
2585 | { |
2586 | QBuffer buf; |
2587 | buf.open(openMode: QBuffer::WriteOnly); |
2588 | QTextStream stream(&buf); |
2589 | const QStringView expected = u"expectedStringView" ; |
2590 | stream << expected; |
2591 | stream.flush(); |
2592 | QCOMPARE(buf.buffer().constData(), "expectedStringView" ); |
2593 | } |
2594 | |
2595 | // ------------------------------------------------------------------------------ |
2596 | void tst_QTextStream::useCase1() |
2597 | { |
2598 | QFile::remove(fileName: "testfile" ); |
2599 | QFile file("testfile" ); |
2600 | QVERIFY(file.open(QFile::ReadWrite)); |
2601 | |
2602 | { |
2603 | QTextStream stream(&file); |
2604 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2605 | stream.setAutoDetectUnicode(true); |
2606 | |
2607 | stream << 4.15 << ' ' << QByteArray("abc" ) << ' ' << QString("ole" ); |
2608 | } |
2609 | |
2610 | file.seek(offset: 0); |
2611 | QCOMPARE(file.readAll(), QByteArray("4.15 abc ole" )); |
2612 | file.seek(offset: 0); |
2613 | |
2614 | { |
2615 | double d; |
2616 | QByteArray a; |
2617 | QString s; |
2618 | QTextStream stream(&file); |
2619 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2620 | stream.setAutoDetectUnicode(true); |
2621 | |
2622 | stream >> d; |
2623 | stream >> a; |
2624 | stream >> s; |
2625 | |
2626 | QCOMPARE(d, 4.15); |
2627 | QCOMPARE(a, QByteArray("abc" )); |
2628 | QCOMPARE(s, QString("ole" )); |
2629 | } |
2630 | } |
2631 | |
2632 | // ------------------------------------------------------------------------------ |
2633 | void tst_QTextStream::useCase2() |
2634 | { |
2635 | QFile::remove(fileName: "testfile" ); |
2636 | QFile file("testfile" ); |
2637 | QVERIFY(file.open(QFile::ReadWrite)); |
2638 | |
2639 | QTextStream stream(&file); |
2640 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2641 | stream.setAutoDetectUnicode(true); |
2642 | |
2643 | stream << 4.15 << ' ' << QByteArray("abc" ) << ' ' << QString("ole" ); |
2644 | |
2645 | file.close(); |
2646 | QVERIFY(file.open(QFile::ReadWrite)); |
2647 | |
2648 | QCOMPARE(file.readAll(), QByteArray("4.15 abc ole" )); |
2649 | |
2650 | file.close(); |
2651 | QVERIFY(file.open(QFile::ReadWrite)); |
2652 | |
2653 | double d; |
2654 | QByteArray a; |
2655 | QString s; |
2656 | QTextStream stream2(&file); |
2657 | stream2.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2658 | stream2.setAutoDetectUnicode(true); |
2659 | |
2660 | stream2 >> d; |
2661 | stream2 >> a; |
2662 | stream2 >> s; |
2663 | |
2664 | QCOMPARE(d, 4.15); |
2665 | QCOMPARE(a, QByteArray("abc" )); |
2666 | QCOMPARE(s, QString("ole" )); |
2667 | } |
2668 | |
2669 | // ------------------------------------------------------------------------------ |
2670 | void tst_QTextStream::manipulators_data() |
2671 | { |
2672 | QTest::addColumn<int>(name: "base" ); |
2673 | QTest::addColumn<int>(name: "alignFlag" ); |
2674 | QTest::addColumn<int>(name: "numberFlag" ); |
2675 | QTest::addColumn<int>(name: "width" ); |
2676 | QTest::addColumn<double>(name: "realNumber" ); |
2677 | QTest::addColumn<int>(name: "intNumber" ); |
2678 | QTest::addColumn<QString>(name: "textData" ); |
2679 | QTest::addColumn<QByteArray>(name: "result" ); |
2680 | |
2681 | QTest::newRow(dataTag: "no flags" ) << 10 << 0 << 0 << 0 << 5.0 << 5 << QString("five" ) << QByteArray("55five" ); |
2682 | QTest::newRow(dataTag: "rightadjust" ) << 10 << int(QTextStream::AlignRight) << 0 << 10 << 5.0 << 5 << QString("five" ) << QByteArray(" 5 5 five" ); |
2683 | QTest::newRow(dataTag: "leftadjust" ) << 10 << int(QTextStream::AlignLeft) << 0 << 10 << 5.0 << 5 << QString("five" ) << QByteArray("5 5 five " ); |
2684 | QTest::newRow(dataTag: "showpos" ) << 10 << int(QTextStream::AlignRight) << int(QTextStream::ForceSign) << 10 << 5.0 << 5 << QString("five" ) << QByteArray(" +5 +5 five" ); |
2685 | QTest::newRow(dataTag: "showpos2" ) << 10 << int(QTextStream::AlignRight) << int(QTextStream::ForceSign) << 5 << 3.14 << -5 << QString("five" ) << QByteArray("+3.14 -5 five" ); |
2686 | QTest::newRow(dataTag: "hex" ) << 16 << int(QTextStream::AlignRight) << int(QTextStream::ShowBase) << 5 << 3.14 << -5 << QString("five" ) << QByteArray(" 3.14 -0x5 five" ); |
2687 | QTest::newRow(dataTag: "hex" ) << 16 << int(QTextStream::AlignRight) << int(QTextStream::ShowBase | QTextStream::UppercaseBase) << 5 << 3.14 << -5 << QString("five" ) << QByteArray(" 3.14 -0X5 five" ); |
2688 | } |
2689 | |
2690 | // ------------------------------------------------------------------------------ |
2691 | void tst_QTextStream::manipulators() |
2692 | { |
2693 | QFETCH(int, base); |
2694 | QFETCH(int, alignFlag); |
2695 | QFETCH(int, numberFlag); |
2696 | QFETCH(int, width); |
2697 | QFETCH(double, realNumber); |
2698 | QFETCH(int, intNumber); |
2699 | QFETCH(QString, textData); |
2700 | QFETCH(QByteArray, result); |
2701 | |
2702 | QBuffer buffer; |
2703 | buffer.open(openMode: QBuffer::WriteOnly); |
2704 | |
2705 | QTextStream stream(&buffer); |
2706 | stream.setCodec(QTextCodec::codecForName(name: "ISO-8859-1" )); |
2707 | stream.setAutoDetectUnicode(true); |
2708 | |
2709 | stream.setIntegerBase(base); |
2710 | stream.setFieldAlignment(QTextStream::FieldAlignment(alignFlag)); |
2711 | stream.setNumberFlags(QTextStream::NumberFlag(numberFlag)); |
2712 | stream.setFieldWidth(width); |
2713 | stream << realNumber; |
2714 | stream << intNumber; |
2715 | stream << textData; |
2716 | stream.flush(); |
2717 | |
2718 | QCOMPARE(buffer.data(), result); |
2719 | } |
2720 | |
2721 | void tst_QTextStream::generateBOM() |
2722 | { |
2723 | QFile::remove(fileName: "bom.txt" ); |
2724 | { |
2725 | QFile file("bom.txt" ); |
2726 | QVERIFY(file.open(QFile::ReadWrite | QFile::Truncate)); |
2727 | |
2728 | QTextStream stream(&file); |
2729 | stream.setCodec(QTextCodec::codecForName(name: "UTF-16LE" )); |
2730 | stream << "Hello" << Qt::endl; |
2731 | |
2732 | file.close(); |
2733 | QVERIFY(file.open(QFile::ReadOnly)); |
2734 | QCOMPARE(file.readAll(), QByteArray("\x48\x00\x65\00\x6c\00\x6c\00\x6f\x00\x0a\x00" , 12)); |
2735 | } |
2736 | |
2737 | QFile::remove(fileName: "bom.txt" ); |
2738 | { |
2739 | QFile file("bom.txt" ); |
2740 | QVERIFY(file.open(QFile::ReadWrite | QFile::Truncate)); |
2741 | |
2742 | QTextStream stream(&file); |
2743 | stream.setCodec(QTextCodec::codecForName(name: "UTF-16LE" )); |
2744 | stream << Qt::bom << "Hello" << Qt::endl; |
2745 | |
2746 | file.close(); |
2747 | QVERIFY(file.open(QFile::ReadOnly)); |
2748 | QCOMPARE(file.readAll(), QByteArray("\xff\xfe\x48\x00\x65\00\x6c\00\x6c\00\x6f\x00\x0a\x00" , 14)); |
2749 | } |
2750 | } |
2751 | |
2752 | void tst_QTextStream::readBomSeekBackReadBomAgain() |
2753 | { |
2754 | QFile::remove(fileName: "utf8bom" ); |
2755 | QFile file("utf8bom" ); |
2756 | QVERIFY(file.open(QFile::ReadWrite)); |
2757 | file.write(data: "\xef\xbb\xbf" "Andreas" ); |
2758 | file.seek(offset: 0); |
2759 | QCOMPARE(file.pos(), qint64(0)); |
2760 | |
2761 | QTextStream stream(&file); |
2762 | stream.setCodec("UTF-8" ); |
2763 | QString Andreas; |
2764 | stream >> Andreas; |
2765 | QCOMPARE(Andreas, QString("Andreas" )); |
2766 | stream.seek(pos: 0); |
2767 | stream >> Andreas; |
2768 | QCOMPARE(Andreas, QString("Andreas" )); |
2769 | } |
2770 | |
2771 | // ------------------------------------------------------------------------------ |
2772 | void tst_QTextStream::status_real_read_data() |
2773 | { |
2774 | QTest::addColumn<QString>(name: "input" ); |
2775 | QTest::addColumn<double>(name: "expected_f" ); |
2776 | QTest::addColumn<QString>(name: "expected_w" ); |
2777 | QTest::addColumn<QList<int> >(name: "results" ); |
2778 | |
2779 | QTest::newRow(dataTag: "1.23 abc " ) << QString("1.23 abc " ) << 1.23 << QString("abc" ) |
2780 | << (QList<int>() |
2781 | << (int)QTextStream::Ok |
2782 | << (int)QTextStream::ReadCorruptData |
2783 | << (int)QTextStream::Ok |
2784 | << (int)QTextStream::Ok |
2785 | << (int)QTextStream::ReadPastEnd); |
2786 | } |
2787 | |
2788 | void tst_QTextStream::status_real_read() |
2789 | { |
2790 | QFETCH(QString, input); |
2791 | QFETCH(double, expected_f); |
2792 | QFETCH(QString, expected_w); |
2793 | QFETCH(QList<int>, results); |
2794 | |
2795 | QTextStream s(&input); |
2796 | double f = 0.0; |
2797 | QString w; |
2798 | s >> f; |
2799 | QCOMPARE((int)s.status(), results.at(0)); |
2800 | QCOMPARE(f, expected_f); |
2801 | s >> f; |
2802 | QCOMPARE((int)s.status(), results.at(1)); |
2803 | s.resetStatus(); |
2804 | QCOMPARE((int)s.status(), results.at(2)); |
2805 | s >> w; |
2806 | QCOMPARE((int)s.status(), results.at(3)); |
2807 | QCOMPARE(w, expected_w); |
2808 | s >> f; |
2809 | QCOMPARE((int)s.status(), results.at(4)); |
2810 | } |
2811 | |
2812 | void tst_QTextStream::status_integer_read() |
2813 | { |
2814 | QTextStream s("123 abc " ); |
2815 | int i; |
2816 | QString w; |
2817 | s >> i; |
2818 | QCOMPARE(s.status(), QTextStream::Ok); |
2819 | s >> i; |
2820 | QCOMPARE(s.status(), QTextStream::ReadCorruptData); |
2821 | s.resetStatus(); |
2822 | QCOMPARE(s.status(), QTextStream::Ok); |
2823 | s >> w; |
2824 | QCOMPARE(s.status(), QTextStream::Ok); |
2825 | QCOMPARE(w, QString("abc" )); |
2826 | s >> i; |
2827 | QCOMPARE(s.status(), QTextStream::ReadPastEnd); |
2828 | } |
2829 | |
2830 | void tst_QTextStream::status_word_read() |
2831 | { |
2832 | QTextStream s("abc " ); |
2833 | QString w; |
2834 | s >> w; |
2835 | QCOMPARE(s.status(), QTextStream::Ok); |
2836 | s >> w; |
2837 | QCOMPARE(s.status(), QTextStream::ReadPastEnd); |
2838 | } |
2839 | |
2840 | class FakeBuffer : public QBuffer |
2841 | { |
2842 | protected: |
2843 | qint64 writeData(const char *c, qint64 i) { return m_lock ? 0 : QBuffer::writeData(data: c, len: i); } |
2844 | public: |
2845 | FakeBuffer(bool locked = false) : m_lock(locked) {} |
2846 | void setLocked(bool locked) { m_lock = locked; } |
2847 | private: |
2848 | bool m_lock; |
2849 | }; |
2850 | |
2851 | void tst_QTextStream::status_write_error() |
2852 | { |
2853 | FakeBuffer fb(false); |
2854 | QVERIFY(fb.open(QBuffer::ReadWrite)); |
2855 | QTextStream fs(&fb); |
2856 | fs.setCodec(QTextCodec::codecForName(name: "latin1" )); |
2857 | /* first write some initial content */ |
2858 | fs << "hello" ; |
2859 | fs.flush(); |
2860 | QCOMPARE(fs.status(), QTextStream::Ok); |
2861 | QCOMPARE(fb.data(), QByteArray("hello" )); |
2862 | /* then test that writing can cause an error */ |
2863 | fb.setLocked(true); |
2864 | fs << "error" ; |
2865 | fs.flush(); |
2866 | QCOMPARE(fs.status(), QTextStream::WriteFailed); |
2867 | QCOMPARE(fb.data(), QByteArray("hello" )); |
2868 | /* finally test that writing after an error doesn't change the stream any more */ |
2869 | fb.setLocked(false); |
2870 | fs << "can't do that" ; |
2871 | fs.flush(); |
2872 | QCOMPARE(fs.status(), QTextStream::WriteFailed); |
2873 | QCOMPARE(fb.data(), QByteArray("hello" )); |
2874 | } |
2875 | |
2876 | void tst_QTextStream::alignAccountingStyle() |
2877 | { |
2878 | { |
2879 | QString result; |
2880 | QTextStream out(&result); |
2881 | out.setFieldAlignment(QTextStream::AlignAccountingStyle); |
2882 | out.setFieldWidth(4); |
2883 | out.setPadChar('0'); |
2884 | out << -1; |
2885 | QCOMPARE(result, QLatin1String("-001" )); |
2886 | } |
2887 | |
2888 | { |
2889 | QString result; |
2890 | QTextStream out(&result); |
2891 | out.setFieldAlignment(QTextStream::AlignAccountingStyle); |
2892 | out.setFieldWidth(4); |
2893 | out.setPadChar('0'); |
2894 | out << "-1" ; |
2895 | QCOMPARE(result, QLatin1String("00-1" )); |
2896 | } |
2897 | |
2898 | { |
2899 | QString result; |
2900 | QTextStream out(&result); |
2901 | out.setFieldAlignment(QTextStream::AlignAccountingStyle); |
2902 | out.setFieldWidth(6); |
2903 | out.setPadChar('0'); |
2904 | out << -1.2; |
2905 | QCOMPARE(result, QLatin1String("-001.2" )); |
2906 | } |
2907 | |
2908 | { |
2909 | QString result; |
2910 | QTextStream out(&result); |
2911 | out.setFieldAlignment(QTextStream::AlignAccountingStyle); |
2912 | out.setFieldWidth(6); |
2913 | out.setPadChar('0'); |
2914 | out << "-1.2" ; |
2915 | QCOMPARE(result, QLatin1String("00-1.2" )); |
2916 | } |
2917 | } |
2918 | |
2919 | void tst_QTextStream::setCodec() |
2920 | { |
2921 | QByteArray ba("\xe5 v\xe6r\n\xc3\xa5 v\xc3\xa6r\n" ); |
2922 | QString res = QLatin1String("\xe5 v\xe6r" ); |
2923 | |
2924 | QTextStream stream(ba); |
2925 | stream.setCodec("ISO 8859-1" ); |
2926 | QCOMPARE(stream.readLine(),res); |
2927 | stream.setCodec("UTF-8" ); |
2928 | QCOMPARE(stream.readLine(),res); |
2929 | } |
2930 | |
2931 | void tst_QTextStream::double_write_with_flags_data() |
2932 | { |
2933 | QTest::addColumn<double>(name: "number" ); |
2934 | QTest::addColumn<QString>(name: "output" ); |
2935 | QTest::addColumn<int>(name: "numberFlags" ); |
2936 | QTest::addColumn<int>(name: "realNumberNotation" ); |
2937 | |
2938 | QTest::newRow(dataTag: "-ForceSign" ) << -1.23 << QString("-1.23" ) << (int)QTextStream::ForceSign << 0; |
2939 | QTest::newRow(dataTag: "+ForceSign" ) << 1.23 << QString("+1.23" ) << (int)QTextStream::ForceSign << 0; |
2940 | QTest::newRow(dataTag: "inf" ) << qInf() << QString("inf" ) << 0 << 0; |
2941 | QTest::newRow(dataTag: "-inf" ) << -qInf() << QString("-inf" ) << 0 << 0; |
2942 | QTest::newRow(dataTag: "inf uppercase" ) << qInf() << QString("INF" ) << (int)QTextStream::UppercaseDigits << 0; |
2943 | QTest::newRow(dataTag: "-inf uppercase" ) << -qInf() << QString("-INF" ) << (int)QTextStream::UppercaseDigits << 0; |
2944 | QTest::newRow(dataTag: "nan" ) << qQNaN() << QString("nan" ) << 0 << 0; |
2945 | QTest::newRow(dataTag: "NAN" ) << qQNaN() << QString("NAN" ) << (int)QTextStream::UppercaseDigits << 0; |
2946 | QTest::newRow(dataTag: "scientific" ) << 1.234567e+02 << QString("1.234567e+02" ) << 0 << (int)QTextStream::ScientificNotation; |
2947 | QTest::newRow(dataTag: "scientific2" ) << 1.234567e+02 << QString("1.234567e+02" ) << (int)QTextStream::UppercaseBase << (int)QTextStream::ScientificNotation; |
2948 | QTest::newRow(dataTag: "scientific uppercase" ) << 1.234567e+02 << QString("1.234567E+02" ) << (int)QTextStream::UppercaseDigits << (int)QTextStream::ScientificNotation; |
2949 | } |
2950 | |
2951 | void tst_QTextStream::double_write_with_flags() |
2952 | { |
2953 | QFETCH(double, number); |
2954 | QFETCH(QString, output); |
2955 | QFETCH(int, numberFlags); |
2956 | QFETCH(int, realNumberNotation); |
2957 | |
2958 | QString buf; |
2959 | QTextStream stream(&buf); |
2960 | if (numberFlags) |
2961 | stream.setNumberFlags(QTextStream::NumberFlag(numberFlags)); |
2962 | if (realNumberNotation) |
2963 | stream.setRealNumberNotation(QTextStream::RealNumberNotation(realNumberNotation)); |
2964 | stream << number; |
2965 | QCOMPARE(buf, output); |
2966 | } |
2967 | |
2968 | void tst_QTextStream::double_write_with_precision_data() |
2969 | { |
2970 | QTest::addColumn<int>(name: "precision" ); |
2971 | QTest::addColumn<double>(name: "value" ); |
2972 | QTest::addColumn<QString>(name: "result" ); |
2973 | |
2974 | QTest::ignoreMessage(type: QtWarningMsg, message: "QTextStream::setRealNumberPrecision: Invalid precision (-1)" ); |
2975 | QTest::newRow(dataTag: "-1" ) << -1 << 3.14159 << QString("3.14159" ); |
2976 | QTest::newRow(dataTag: "0" ) << 0 << 3.14159 << QString("3" ); |
2977 | QTest::newRow(dataTag: "1" ) << 1 << 3.14159 << QString("3" ); |
2978 | QTest::newRow(dataTag: "2" ) << 2 << 3.14159 << QString("3.1" ); |
2979 | QTest::newRow(dataTag: "3" ) << 3 << 3.14159 << QString("3.14" ); |
2980 | QTest::newRow(dataTag: "5" ) << 5 << 3.14159 << QString("3.1416" ); |
2981 | QTest::newRow(dataTag: "6" ) << 6 << 3.14159 << QString("3.14159" ); |
2982 | QTest::newRow(dataTag: "7" ) << 7 << 3.14159 << QString("3.14159" ); |
2983 | QTest::newRow(dataTag: "10" ) << 10 << 3.14159 << QString("3.14159" ); |
2984 | } |
2985 | |
2986 | void tst_QTextStream::double_write_with_precision() |
2987 | { |
2988 | QFETCH(int, precision); |
2989 | QFETCH(double, value); |
2990 | QFETCH(QString, result); |
2991 | |
2992 | QString buf; |
2993 | QTextStream stream(&buf); |
2994 | stream.setRealNumberPrecision(precision); |
2995 | stream << value; |
2996 | QCOMPARE(buf, result); |
2997 | } |
2998 | |
2999 | void tst_QTextStream::int_read_with_locale_data() |
3000 | { |
3001 | QTest::addColumn<QString>(name: "locale" ); |
3002 | QTest::addColumn<QString>(name: "input" ); |
3003 | QTest::addColumn<int>(name: "output" ); |
3004 | |
3005 | QTest::newRow(dataTag: "C -123" ) << QString("C" ) << QString("-123" ) << -123; |
3006 | QTest::newRow(dataTag: "C +123" ) << QString("C" ) << QString("+123" ) << 123; |
3007 | QTest::newRow(dataTag: "C 12345" ) << QString("C" ) << QString("12345" ) << 12345; |
3008 | QTest::newRow(dataTag: "C 12,345" ) << QString("C" ) << QString("12,345" ) << 12; |
3009 | QTest::newRow(dataTag: "C 12.345" ) << QString("C" ) << QString("12.345" ) << 12; |
3010 | |
3011 | QTest::newRow(dataTag: "de_DE -123" ) << QString("de_DE" ) << QString("-123" ) << -123; |
3012 | QTest::newRow(dataTag: "de_DE +123" ) << QString("de_DE" ) << QString("+123" ) << 123; |
3013 | QTest::newRow(dataTag: "de_DE 12345" ) << QString("de_DE" ) << QString("12345" ) << 12345; |
3014 | QTest::newRow(dataTag: "de_DE 12.345" ) << QString("de_DE" ) << QString("12.345" ) << 12345; |
3015 | QTest::newRow(dataTag: "de_DE .12345" ) << QString("de_DE" ) << QString(".12345" ) << 0; |
3016 | } |
3017 | |
3018 | void tst_QTextStream::int_read_with_locale() |
3019 | { |
3020 | QFETCH(QString, locale); |
3021 | QFETCH(QString, input); |
3022 | QFETCH(int, output); |
3023 | |
3024 | QTextStream stream(&input); |
3025 | stream.setLocale(locale); |
3026 | int result; |
3027 | stream >> result; |
3028 | QCOMPARE(result, output); |
3029 | } |
3030 | |
3031 | void tst_QTextStream::int_write_with_locale_data() |
3032 | { |
3033 | QTest::addColumn<QString>(name: "locale" ); |
3034 | QTest::addColumn<int>(name: "numberFlags" ); |
3035 | QTest::addColumn<int>(name: "input" ); |
3036 | QTest::addColumn<QString>(name: "output" ); |
3037 | |
3038 | QTest::newRow(dataTag: "C -123" ) << QString("C" ) << 0 << -123 << QString("-123" ); |
3039 | QTest::newRow(dataTag: "C +123" ) << QString("C" ) << (int)QTextStream::ForceSign << 123 << QString("+123" ); |
3040 | QTest::newRow(dataTag: "C 12345" ) << QString("C" ) << 0 << 12345 << QString("12345" ); |
3041 | |
3042 | QTest::newRow(dataTag: "de_DE -123" ) << QString("de_DE" ) << 0 << -123 << QString("-123" ); |
3043 | QTest::newRow(dataTag: "de_DE +123" ) << QString("de_DE" ) << (int)QTextStream::ForceSign << 123 << QString("+123" ); |
3044 | QTest::newRow(dataTag: "de_DE 12345" ) << QString("de_DE" ) << 0 << 12345 << QString("12.345" ); |
3045 | } |
3046 | |
3047 | void tst_QTextStream::int_write_with_locale() |
3048 | { |
3049 | QFETCH(QString, locale); |
3050 | QFETCH(int, numberFlags); |
3051 | QFETCH(int, input); |
3052 | QFETCH(QString, output); |
3053 | |
3054 | QString result; |
3055 | QTextStream stream(&result); |
3056 | stream.setLocale(locale); |
3057 | if (numberFlags) |
3058 | stream.setNumberFlags(QTextStream::NumberFlags(numberFlags)); |
3059 | stream << input; |
3060 | QCOMPARE(result, output); |
3061 | } |
3062 | |
3063 | void tst_QTextStream::textModeOnEmptyRead() |
3064 | { |
3065 | const QString filename(tempDir.path() + QLatin1String("/textmodetest.txt" )); |
3066 | |
3067 | QFile file(filename); |
3068 | QVERIFY2(file.open(QIODevice::ReadWrite | QIODevice::Text), qPrintable(file.errorString())); |
3069 | QTextStream stream(&file); |
3070 | QVERIFY(file.isTextModeEnabled()); |
3071 | QString emptyLine = stream.readLine(); // Text mode flag cleared here |
3072 | QVERIFY(file.isTextModeEnabled()); |
3073 | } |
3074 | |
3075 | |
3076 | // ------------------------------------------------------------------------------ |
3077 | |
3078 | QTEST_MAIN(tst_QTextStream) |
3079 | #include "tst_qtextstream.moc" |
3080 | |
3081 | |