summaryrefslogtreecommitdiffstats
path: root/src/gui/text/qtextlayout.cpp
Commit message (Collapse)AuthorAgeFilesLines
* Mark low-level text classes as security criticalEskil Abrahamsen Blomfeldt2025-03-111-0/+1
| | | | | | | | | | | | These files process raw end user provided data and apply structure to it, through layout and Unicode algorithms. Extra care should be taken when reviewing changes to these files. Pick-to: 6.8 6.9 Change-Id: Iba86aec1a185bbbcd40aa2b8d4d0d839bb99ba0d Reviewed-by: Eirik Aavitsland <[email protected]>
* Replace QPair/qMakePair with std::pair in qtbase/guiIsak Fyksen2025-01-091-2/+2
| | | | | | | | Task-number: QTBUG-115841 Pick-to: 6.9 Change-Id: Iebd96760ff7b3d7674816553312ba8dc3229c86a Reviewed-by: Marc Mutz <[email protected]> Reviewed-by: Volker Hilsheimer <[email protected]>
* Don't include bearing of mid-string characters in max widthEskil Abrahamsen Blomfeldt2024-12-201-1/+8
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | When calculating the maximum width of a text layout, we would add the text width of each substring *after* we had added the negative right bearing of the last character to it. But the bearing of the last character in a wrapped substring does not actually add to the maximum width unless it is the last character of the *whole* string. Prior to 250117086ff15bba79df8f0e15ee66192edc9ea9 this was not noticed, because the last glyph in the substring would typically be a space and the space does not have any bearings (when doing wrapping on individual characters it could still happen). After the change, the previous glyph for which we get the right bearing will be the last non-whitespace glyph. If this happened to have a negative right bearing, we would add this to the max width and end up with a larger max width than we should. This caused a test failure in tst_qquicktext. This test prefers the text width without the bearing (i.e. the *advance* of the substring) unless the line is manually wrapped or it is the last line of the layout. Pick-to: 6.8 6.9 Change-Id: Iba1a5ad48d575683672400f0572dfa683a0f2d9c Reviewed-by: Lars Knoll <[email protected]>
* Include right bearing in width of layouts wrapping on spacesEskil Abrahamsen Blomfeldt2024-12-111-4/+16
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When we're calculating the width of the layout, we include the right bearing of the last character in the text line if it is negative (i.e. it exceeds the advance width). We do this by storing the last glyph that has been verified to fit in the line, so that we can retrieve its right bearing when we find a break. However, when we were wrapping on spaces this previous glyph would always be a space, and the right bearing would subsequently be 0. But then the trailing spaces would be trimmed and the right bearing of the actual last glyph would not be recorded and never added to the text width. This caused a failure in tst_qquicktext on Windows with both DirectWrite and Freetype: This was purely unlucky, because the metrics of the Tahoma font happened to be such that the right bearing on the 'k' was enough to cause a line to overflow. Since we didn't account for it when setting the width, we ended up with unexpected line breaks, causing the test to fail. This did not happen with GDI, since it rounded the right bearing of the character down to 0 (which was actually visible in the layout, in that the k was painted a fraction of a pixel outside the text layout's width). In addition, QTBUG-130313 was causing us to pick a different font when resolving the non-existent font requested by the test, so therefore the bug was not found immediately when moving to DirectWrite as the default but only when QTBUG-130313 was fixed. We fix this by 1. When adding a chunk of whitespace, we record the previous non-whitespace glyph that has been verified to fit. 2. When adding a chunk of non-whitespace, we only record the previous glyph verified to fit *if* it is not whitespace. Otherwise we keep whatever we recorded before adding the spaces. Pick-to: 6.8 6.9 Fixes: QTBUG-132075 Change-Id: I8d9a2f3197068f5f93520d217a6bb89633644e95 Reviewed-by: Lars Knoll <[email protected]>
* Don't count overflowing inline image height to previous lineEskil Abrahamsen Blomfeldt2024-11-181-3/+4
| | | | | | | | | | | | | | | | | | | | | | In the line break algorithm, we try filling characters and objects onto a text line until we see an overflow. We then keep the state *before* the overflow as the current line and move to the next. However, for inline images we would store its height to the current state before checking if it overflowed. So if the inline image did cause an overflow it would be counted towards the height of the preceding line in addition to the line where it actually ended up. [ChangeLog][Text] Fixed an issue which could cause the height of a word-wrapped text line to grow if the immediate line after it began with an inline image. Pick-to: 5.15 6.5 6.8 Fixes: QTBUG-130980 Change-Id: I68494b49059e5e35349cbde77aefc64abeb69697 Reviewed-by: Lars Knoll <[email protected]>
* QTextLayout: keep strong reference on font engine in a layout loopVladimir Belyavsky2024-04-161-17/+12
| | | | | | | | | | | | | | | | | | | This is speculative fix for the crashes in QTextLine::layout_helper() we're observing on users side. The possible reason is in that fontEngine and previousGlyphFontEngine, which are stored in LBH, became invalid during the layout cycle (destroyed by trimming font cache?). To prevent this we need to handle font engine's ref-counter gracefully, so just wrap them into QExplicitlySharedDataPointer. As a drive-by change, use in-class initialization for LBH members. Task-number: QTBUG-117500 Pick-to: 5.15 6.2 6.5 6.7 Change-Id: I6987a2b5618bb4ba8762f2ef01b4ce0dd60cb232 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Fix infinite loop in QTextLayout with setNumColumns()Eskil Abrahamsen Blomfeldt2024-01-291-1/+1
| | | | | | | | | | | | | | | | | | | | | | If the line width is negative, then we might exit the layout loop before consuming any text, and thus the loop will never finish. This is a side effect of a change for maximumWidth: 991c056438b311566bc4ea543af0f33dfd5dffbb. 49a63d375972079ae3000c8b7d512d58d4de32bb fixed this issue for QTextLayout::setFixedSize(), but I forgot to do the same in the overload of QTextLayout::setNumColumns() which includes an alignment width and therefore sets the line width in addition to the column count. Basically, we just make sure the line width is never negative so that the width > line.width condition also means the width > 0. Pick-to: 6.5 6.6 6.7 Fixes: QTBUG-115459 Change-Id: If904bfc64cd74e819a0864db55fa9555073d0781 Reviewed-by: Vladimir Belyavsky <[email protected]> Reviewed-by: Lars Knoll <[email protected]>
* Fix clipped text when combining multiple writing systemsEskil Abrahamsen Blomfeldt2024-01-251-171/+193
| | | | | | | | | | | | | | | | | | | When a QTextLine consists of multiple different scripts and the fonts had negative bearing, the background for a script item could overdraw the previous item's text, causing it to look clipped. This was because the background and text was drawn in a single pass, and moving the background drawing into its own pre-pass fixes the issue. [ChangeLog][QtGui] Fixed an issue where drawing text from different writing systems in the same line and including a background could cause parts of the text to be clipped. Pick-to: 6.5 6.6 6.7 Fixes: QTBUG-121040 Change-Id: I3f79e6d33c09a2a92853bc8752dbe11a0bea2dd0 Reviewed-by: Lars Knoll <[email protected]>
* Tidy up qtextlayoutAnton Kudryavtsev2023-10-251-7/+3
| | | | | | | | | - remove unused variable - port index-based loop to range-based for - use const method more to avoid implicit detach Change-Id: I223f6c221d0c6277e94efd2e7b7be0f8d8456c60 Reviewed-by: Mårten Nordheim <[email protected]>
* Fix specific overflow in qtextlayoutAllan Sandfeld Jensen2023-05-081-3/+6
| | | | | | | | | | Adds qAddOverflow and qMulOverflow definitions to QFixed Fixes: QTBUG-113337 Pick-to: 6.5 6.5.1 6.2 5.15 Change-Id: I13579306defceaccdc0fbb1ec0e9b77c6f8d1af9 Reviewed-by: Eirik Aavitsland <[email protected]> Reviewed-by: Thiago Macieira <[email protected]>
* Doc: Remove stray slashVolker Hilsheimer2023-03-281-1/+1
| | | | | | | Pick-to: 6.5 6.2 Change-Id: Ic5e08437e8a5a937ae4f3ea1aa6ca73fd7780c98 Reviewed-by: <[email protected]> Reviewed-by: Andreas Eliasson <[email protected]>
* QTextLayout/text cursor: use the same height as the selectionChristian Ehrlicher2023-03-201-1/+1
| | | | | | | | | | The height of the selection was adjusted for high-dpi screens by a fix for QTBUG-98372. But the height of the cursor was forgotten. This is only visible with a very high device pixel ratio. Pick-to: 6.5 Change-Id: I3ae9a2df0a160b50593931828cdd69c0a8d4b5c4 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Text: fix Soft hyphen rendering in QTextLayout::glyphRuns()Vladimir Belyavsky2023-02-221-8/+14
| | | | | | | | | | | | | | | | | | | | | | When calculating the position offset of QGlyphRuns, either when fetching substrings or when applying fallback fonts, we would include the advances of non-printable glyphs, such as the soft hyphen. This was an oversight, and the other code which calculates the advance (like in QFontEngine::getGlyphPositions()) does this correctly. We apply the same logic as there and only include the advance if the dontPrint flag is unset. [ChangeLog][QtGui][Text] Fixed an issue where spaces would sometimes be shown in soft hyphen positions in a string. Fixes: QTBUG-46990 Fixes: QTBUG-62620 Fixes: QTBUG-67038 Fixes: QTBUG-102483 Pick-to: 5.15 6.2 6.4 6.5 Change-Id: I4e583fb74f7a51424f14917d7cc0894beefec48b Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Turn elidedlabel example into a code snippetVolker Hilsheimer2023-02-091-0/+4
| | | | | | | | | | | | The example is 90% boiler plate for subclassing QFrame and providing a bit of GUI to change the size of the label using sliders. The interesting bit is a block of 25 lines of code, so turn those into a snippet and add that to the QTextLayout overview documentation. Fixes: QTBUG-111011 Pick-to: 6.5 Change-Id: I6e97b2ea47b553c8d998ad185cfac006721ef7ee Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Doc: Document further GUI API as new in 6.5Kai Köhne2023-01-121-0/+1
| | | | | | Pick-to: 6.5 Change-Id: I83402aec120a2f6a78b245029b94d3519f94d7f3 Reviewed-by: Laszlo Agocs <[email protected]>
* Fix infinite layout loop with negative line widthEskil Abrahamsen Blomfeldt2023-01-091-4/+1
| | | | | | | | | | | | | | | | | | | | Setting a negative line width does not make much sense, but in earlier Qt versions, this work the same as if the line width was 0 (just give you the minimal layout given wrapping constraints). But since 991c056438b311566bc4ea543af0f33dfd5dffbb, we check if current width > line width at an earlier point, and because 0 > -1, we would exit immediately before adding any characters to the text line. To restore the behavior in earlier versions, we set the minimum possible line width to 0. Pick-to: 6.5 Fixes: QTBUG-109474 Change-Id: Iceadd5135681f61b30de8221853834983941c5a4 Reviewed-by: Lars Knoll <[email protected]> Reviewed-by: hjk <[email protected]>
* Don't return empty glyph runs from QTextLineEskil Abrahamsen Blomfeldt2022-12-051-13/+17
| | | | | | | | | | | | The last (or only) QGlyphRun would be ignored if it did not contain any glyphs, but we did not have the same conditions for substrings represented by different font engines. This was an oversight and we should be consistent. Pick-to: 6.4 Task-number: QTBUG-108799 Change-Id: Idfa187f6198247d5cc94804a4e55d5de3ccd739e Reviewed-by: Tor Arne Vestbø <[email protected]>
* QTextLayout: fix maximumWidth() for a text containing line separatorVladimir Belyavsky2022-11-191-5/+11
| | | | | | | | | | | | | | | | | This is improved version of previous fix 013c346a8dcbd618febb07884c64c740daf9754d that was reverted because it broke some tests for Quick Text. The problem was that it did not work correctly in the case the text was wrapped to a fixed width. To deal with this we'll accumulate current line full width (as if it hadn't been wrapped) in layout data (layoutData->currentMaxWidth). Then when the next line is explicitly wrapped by line or paragraph separator, this accumulated width will be used to adjust layout's maximum width. Change-Id: Iad7119d9808e1db15fe1fbc5db049c3db928529f Fixes: QTBUG-89557 Fixes: QTBUG-104986 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* QTextLayout: Reconsider cursor drawing on TextObjectTang Haixiang2022-11-111-10/+10
| | | | | | | | | | | | | | | | | | | | | | | | Revert: e99a883bd382ca950192bd66cafb2a1de6394ce7 Revert: 33238ea2c63b372ee8795eaafbfc5a859a778f8d These two commits made the drawing of the cursor incomprehensible, but their purpose was to fix the problem of abnormal cursor drawing when QScriptAnalysis::Object is present. Because objects require some special handling, they can be specially aligned or floated. Anyway, the alignment is already reflected by ascent and descent, and when drawing, y = position.y() + (sl.y + sl.base() - base).toReal(); works fine. So roll them back now. We just need to specially consider the case where the QScriptItem is a QScriptAnalysis::Object, keeping the base and descent the same as the row. Task-number: QTBUG-92468 Task-number: QTBUG-86823 Task-number: QTBUG-96288 Pick-to: 6.2 6.4 Change-Id: I6d9a0e00fbc3823e0cc8e0e8bd061da5782d1f8a Reviewed-by: Shawn Rutledge <[email protected]>
* Port from container::count() and length() to size() - V5Marc Mutz2022-11-031-4/+4
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This is a semantic patch using ClangTidyTransformator as in qtbase/df9d882d41b741fef7c5beeddb0abe9d904443d8, but extended to handle typedefs and accesses through pointers, too: const std::string o = "object"; auto hasTypeIgnoringPointer = [](auto type) { return anyOf(hasType(type), hasType(pointsTo(type))); }; auto derivedFromAnyOfClasses = [&](ArrayRef<StringRef> classes) { auto exprOfDeclaredType = [&](auto decl) { return expr(hasTypeIgnoringPointer(hasUnqualifiedDesugaredType(recordType(hasDeclaration(decl))))).bind(o); }; return exprOfDeclaredType(cxxRecordDecl(isSameOrDerivedFrom(hasAnyName(classes)))); }; auto renameMethod = [&] (ArrayRef<StringRef> classes, StringRef from, StringRef to) { return makeRule(cxxMemberCallExpr(on(derivedFromAnyOfClasses(classes)), callee(cxxMethodDecl(hasName(from), parameterCountIs(0)))), changeTo(cat(access(o, cat(to)), "()")), cat("use '", to, "' instead of '", from, "'")); }; renameMethod(<classes>, "count", "size"); renameMethod(<classes>, "length", "size"); except that the on() matcher has been replaced by one that doesn't ignoreParens(). a.k.a qt-port-to-std-compatible-api V5 with config Scope: 'Container'. Added two NOLINTNEXTLINEs in tst_qbitarray and tst_qcontiguouscache, to avoid porting calls that explicitly test count(). Change-Id: Icfb8808c2ff4a30187e9935a51cad26987451c22 Reviewed-by: Ivan Solovev <[email protected]> Reviewed-by: Qt CI Bot <[email protected]>
* QTextLayout: fix maximumWidth() for a text containing spacesVladimir Belyavsky2022-10-061-5/+1
| | | | | | | | | | | When laying out a text and calculating maxWidth, we must _always_ take into account the accumulated width of spaces (lbh.spaceData.textWidth) regardless of wrapMode, other text content, spaces position, etc. Fixes: QTBUG-106947 Change-Id: I2ac9af92ed7dd07c1e040bfcf83949a358d1c9c9 Reviewed-by: Qt CI Bot <[email protected]> Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Port from container.count()/length() to size()Marc Mutz2022-10-041-13/+13
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This is semantic patch using ClangTidyTransformator: auto QtContainerClass = expr(hasType(namedDecl(hasAnyName(<classes>)))).bind(o) makeRule(cxxMemberCallExpr(on(QtContainerClass), callee(cxxMethodDecl(hasAnyName({"count", "length"), parameterCountIs(0))))), changeTo(cat(access(o, cat("size"), "()"))), cat("use 'size()' instead of 'count()/length()'")) a.k.a qt-port-to-std-compatible-api with config Scope: 'Container'. <classes> are: // sequential: "QByteArray", "QList", "QQueue", "QStack", "QString", "QVarLengthArray", "QVector", // associative: "QHash", "QMultiHash", "QMap", "QMultiMap", "QSet", // Qt has no QMultiSet Change-Id: Ibe8837be96e8d30d1846881ecd65180c1bc459af Reviewed-by: Qt CI Bot <[email protected]> Reviewed-by: Volker Hilsheimer <[email protected]>
* Introduce QGlyphRun::stringIndexes()Eskil Abrahamsen Blomfeldt2022-09-291-13/+147
| | | | | | | | | | | | | | | | | | | | | | | | | | | This introduces a way to trace each entry in the glyph index array to a specific index in the original text passed to QTextLayout, as well as a convenience function to access the original string from the QGlyphRun. The index information is stored in the logClusters array internally in Qt, but it contains the inverse information: For each character in the output string, it contains an index into the glyph array. In order to get the string indexes for each glyph, which makes a lot more sense in the context of the QGlyphRun API, we need to do a little search to construct the data. To avoid adding unnecessary allocations, we make the new APIs opt-in. If you do not specify anything, you will only get the glyph indexes and glyph positions as before. However, you can now specify exactly which parts of the layout to extract using an optional flags parameter. This also adds a manual test which can be very handy to visualize QTextLayouts and how they are split into QGlyphRuns. Fixes: QTBUG-103932 Change-Id: Ie4288fff338b9482aba0aba29fc7e1e59fa60900 Reviewed-by: Lars Knoll <[email protected]>
* Revert "QTextLayout: fix maximumWidth() for a text containing line separator"Eskil Abrahamsen Blomfeldt2022-09-231-8/+1
| | | | | | | | | | | | | | | | This reverts commit 013c346a8dcbd618febb07884c64c740daf9754d. It was determined to cause a regression in Qt Quick: QTBUG-106899. In order to unblock integrations, we need to revert the change. It can be re-committed later when the problem has been analyzed and addressed. Pick-to: 6.2 6.4 Fixes: QTBUG-106899 Task-number: QTBUG-89557 Task-number: QTBUG-104986 Change-Id: I04054587f68ab39fdb038b02fc69ebfa3dc7d197 Reviewed-by: Volker Hilsheimer <[email protected]>
* QTextLayout: fix maximumWidth() for a text containing line separatorVladimir Belyavsky2022-09-201-1/+8
| | | | | | | | | | | | | | When laying out, we need to increase layout's maximum width _only_ if the previous line was not explicitly wrapped by a line or paragraph separator, or if the current line's width is greater than the previously accumulated layout's maximum width. Fixes: QTBUG-89557 Fixes: QTBUG-104986 Pick-to: 6.2 6.4 Change-Id: Ib7cc4b9dda8f20166dcbd5cfd3b56424bb33d14a Reviewed-by: Konstantin Ritt <[email protected]> Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Apply Q_CONSTINIT where beneficialSona Kurazyan2022-09-011-2/+2
| | | | | | | | | | Applied Q_CONSTINIT to variables with static storage duration, but skipped the POD types with core constant initializers. Task-number: QTBUG-100486 Change-Id: Iaabf824e9cb0f29a405a149912200d4e4b3573c1 Reviewed-by: Thiago Macieira <[email protected]> Reviewed-by: Mårten Nordheim <[email protected]>
* Pass QFixed by valueMarc Mutz2022-07-081-2/+2
| | | | | | | | | It's a glorified int, so pass it by value instead of cref. Pick-to: 6.4 Change-Id: I1c7a37614cd0d2dac63d2d549563600d401d6dad Reviewed-by: Sérgio Martins <[email protected]> Reviewed-by: Lars Knoll <[email protected]>
* Ensure consistent cursor width under fractional scalingEirik Aavitsland2022-06-281-1/+14
| | | | | | | | | | | | | | Under fractional scaling, an N units wide rectangle can in general cover either M or M+1 pixels, depending on placement. For a tall thin recangle like the cursor, this difference becomes very visible as the cursor moves from position to position. Avoid by instead painting the cursor as a cosmetic line in such cases, since that keeps its width independently of the current transformation. Fixes: QTBUG-95319 Pick-to: 6.4 6.3 6.2 5.15 Change-Id: I31a31f89fe7eac3037694946aa452a9f2bd6e5be Reviewed-by: Morten Johan Sørvig <[email protected]>
* Enable text layout drawing on coordinates outside QFIXED_MAXEirik Aavitsland2022-05-241-5/+12
| | | | | | | | | | | | | | | In an earlier commit, painting on such coordinates was rejected, since it would overflow the internal calculations using QFixed. Instead, avoid the overflow by translating the painter to avoid the huge coordinate values. Also reduce the max value somewhat, so that pos stays well away from QFIXED_MAX, to avoid overflows in the other QFixed variables that have values offset from pos. Fixes: QTBUG-103745 Pick-to: 6.3 6.2 Change-Id: Iebdec32bed57fe8e65551c7d278da9fd6c041b37 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Use SPDX license identifiersLucie Gérard2022-05-161-38/+2
| | | | | | | | | | | | | Replace the current license disclaimer in files by a SPDX-License-Identifier. Files that have to be modified by hand are modified. License files are organized under LICENSES directory. Task-number: QTBUG-67283 Change-Id: Id880c92784c40f3bbde861c0d93f58151c18b9f1 Reviewed-by: Qt CI Bot <[email protected]> Reviewed-by: Lars Knoll <[email protected]> Reviewed-by: Jörg Bornemann <[email protected]>
* QtGui: stop using QLatin1Char constructor for creating char literalsSona Kurazyan2022-04-131-1/+1
| | | | | | | | | Required for porting away from QLatin1Char/QLatin1String in scope of QTBUG-98434. Change-Id: I308d86cefcbfd126929b68f9a853d420840c965f Reviewed-by: Qt CI Bot <[email protected]> Reviewed-by: Marc Mutz <[email protected]>
* Fix gaps between lines of selectionEskil Abrahamsen Blomfeldt2021-11-291-0/+2
| | | | | | | | | | | | | | | | | | | | | | When a font has fractional metrics, we could get visible gaps between lines in a multi-line selection, if the bottom of the rect was not aligned to the pixel grid. In Qt 5, this was primarily an issue on macOS, but since making vertical metrics consistent in f761ad3cd9ad1252f24b76ae413298dc7bed8af3, we could also get this on other platforms, causing a regression on these platforms. The fix is to align the rect to the pixel grid. [ChangeLog][Text] Fixed an issue where there would sometimes be visible gaps in selections spanning multiple lines. Pick-to: 6.2 Fixes: QTBUG-98372 Change-Id: I03cb1465602b6d78c60a0c764d920f7f092418a8 Reviewed-by: Konstantin Ritt <[email protected]> Reviewed-by: Volker Hilsheimer <[email protected]> Reviewed-by: Qt CI Bot <[email protected]>
* Add const to read only local variablesOliver Eftevaag2021-11-011-1/+1
| | | | | | Pick-to: 6.2 Change-Id: Ideb34a5009277b919a8a3834e53af4ff550dfc6e Reviewed-by: Mitch Curtis <[email protected]>
* Fix cursor positioning on bidi boundariesVolker Hilsheimer2021-10-181-43/+74
| | | | | | | | | | | | | | | | | When the cursor is positioned between to script items that have different writing directions, prioritise the script item that has the same direction as the paragraph (i.e. the QTextEngine) when deciding where and how to display the cursor. If visual cursor movement is enabled, the behavior is unchanged. As a drive-by, clean up coding style and avoid shadowing of function- local variables. Task-number: QTBUG-88529 Pick-to: 6.2 Change-Id: I15227b10b1469d9caf1235b00e4d6f9f64a8b510 Reviewed-by: Lars Knoll <[email protected]> Reviewed-by: Qt CI Bot <[email protected]>
* Fix cursor placement at left and right ends of bidi textVolker Hilsheimer2021-10-181-26/+9
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | In a text line that has a change of direction at either end of the text, the cursor needs to be positioned where the next character is inserted, or where backspace deletes the previous character. In bidi text, this is ambiguous as illustrated by this example: abcشزذ Depending on whether this string was typed in a left-to-right document or in a right-to-left document, it could be first latin, then arabic; or it could be first arabic, then latin. If a general left-to-right context, cursor position 0 should be in front of the 'a', and cursor position 6 should be at the end of the arabic text, in the visual middle of the line. Cursor position 3 can be either after the 'c' if the next character typed would be latin, or at the visual end of the line if the next character will be arabic. Qt calculated the cursor position past the right end of the text as 3 (which is not wrong, but 3 has two visual positions), and placed the cursor at the visual end of the line (favoring the right-to-left alternative). Backspace would then delete the 'c', writing a new latin character would insert a 'd' next to the 'c', writing a new arabic character would insert it also in the middle - none of these operations happen at the visual end of the line, where the cursor was blinking. To fix this, we take into account the general layout of the text, which is typically based on the document, or the user's locale setting and UI translation, and calculate the cursor position accordingly: if we are past the visual end of the document on either side, then the cursor position is either 0 or the last character of the text, depending on the direction of the QTextEngine used. This way, the cursor ends up in the middle of the document when we click beyond the end of the line, which is where characters are removed and inserted. Typing a 'd' at this point will make the cursor jump to the end, where the d is added. There are still corner cases: clicking on the right-most arabic character calculates the cursor position as 3, which is then ambiguous, as it can be either at the visual end of the string, or next to the 'c'. َQt makes the inconsistent choice to place the cursor at the visual end, showing the left-to-right indicator, but pressing a 'd' adds the 'd' after the 'c' in the middle of the text. Fixes: QTBUG-88529 Pick-to: 6.2 Change-Id: Idccd4c4deead2bce0e858189f9aef414857eb8af Reviewed-by: Lars Knoll <[email protected]>
* gui: Fix typos in documentationJonas Kvinge2021-10-121-2/+2
| | | | | | Pick-to: 5.15 6.2 Change-Id: I533f5a55cd0cd60a76990b552d7dab51a301ac1c Reviewed-by: Giuseppe D'Angelo <[email protected]>
* gui: Fix typos in source code commentsJonas Kvinge2021-10-121-1/+1
| | | | | | Pick-to: 5.15 6.2 Change-Id: Ie53e5542a8f93856470982939ecd8ec90b323d69 Reviewed-by: Eirik Aavitsland <[email protected]>
* Fix QTextEdit cursor rectangle vertical positioningZhang Hao2021-09-181-2/+5
| | | | | | | | | | | | | | | When there are characters with different pointsize in QScriptLine, the value of si.descent is less than sl.descent, which will cause the y value of the cursor rectangle to be too large. If si.descent is less than sl.descent, the height of the cursor rectangle is equal to base plus si.descent. Amends e99a883bd382ca950192bd66cafb2a1de6394ce7 Fixes: QTBUG-96288 Done-with: Tor Arne Vestbø <[email protected]> Pick-to: 6.1 6.2 Change-Id: I4a8566b32cfa75d8ca1a584f5e8e577c5c9caf0d Reviewed-by: Volker Hilsheimer <[email protected]>
* Fix QTextFormat::FullWidthSelection for right-to-left text layoutsOliver Eftevaag2021-07-101-4/+11
| | | | | | | | | | | | | | | Using the QTextFormat::FullWidthSelection property to select a line would previously not take into account right-to-left text layouts. With this patch, the whole line should now be drawn correctly for both left-to-right, and right-to-left layouts. Pick-to: 6.2 6.1 5.15 Fixes: QTBUG-91125 Change-Id: Ide7b340cd7b4060e7c00e55e0011a86ffdfb5eb4 Done-with: Volker Hilsheimer <[email protected]> Reviewed-by: Dmitry Shachnev <[email protected]> Reviewed-by: Volker Hilsheimer <[email protected]>
* Avoid overflow in text layoutEirik Aavitsland2021-06-171-1/+2
| | | | | | | | | | Fixes oss-fuzz issue 34597. Fixes: QTBUG-94197 Pick-to: 6.2 6.1 5.15 Change-Id: Icabcd5a87b809b6a5ae0f1a696ec3b5dd906886b Reviewed-by: Eirik Aavitsland <[email protected]> Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Remove Qt6 switches from QtGuiAllan Sandfeld Jensen2021-05-051-14/+0
| | | | | | | Removing now dead code Change-Id: I021539da6517fdb8443f8ae9431fc172b7910cfc Reviewed-by: Friedemann Kleint <[email protected]>
* Draw the cursor considering the descent is 0Tang Haixiang2021-04-201-3/+3
| | | | | | | | | | | | | | When the descent of the item is 0, ascent is the height of the item, base(base = si.ascent)> sl.base. At this time, sl.descent is not considered. The calculated y value may be <0. Fixes: QTBUG-86823 Fixes: QTBUG-92468 Pick-to: 5.15 6.0 6.1 Change-Id: I9cf088dec9162595e52ff72aa90ec3153a30fb72 Reviewed-by: Shawn Rutledge <[email protected]> Reviewed-by: Lars Knoll <[email protected]>
* Assert that engine isn't nullptr before dereferencingVolker Hilsheimer2021-04-191-0/+1
| | | | | | | | | | | The engine pointer is guaranteed to be initialized in line 1838, so we can assert that the correct value is passed into the function to fix static analyzer warning 1d9b8ce922ee0891fb0d477dc17fdb8d. Change-Id: I773bbaa579afec0d7a79d4393ee66fd26ba9629b Reviewed-by: Konstantin Ritt <[email protected]> Reviewed-by: Jonas Karlsson <[email protected]> Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Add new enum value VisualTabCharacter into QCharZhang Hao2021-04-151-1/+1
| | | | | | | | | | | | | | With this enumeration value, users can get the width of the current font TAB character more conveniently In addition, added some documentation about where users may use this enumeration. Fixes: QTBUG-92205 Done-with: Volker Hilsheimer <[email protected]> Done-with: Tor Arne Vestbø <[email protected]> Change-Id: I9794b7553e9299e351f9182de02866d07a1393fc Reviewed-by: Tor Arne Vestbø <[email protected]>
* Avoid overflow in text layoutEirik Aavitsland2021-01-281-0/+4
| | | | | | | | | Fixes oss-fuzz issue 29313. Pick-to: 6.0 5.15 Change-Id: Idbabd162fa9e0dbce687981bdbcc75be37189a61 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]> Reviewed-by: Robert Löhning <[email protected]>
* Avoid overflowing QFixed in text layoutEirik Aavitsland2020-12-101-0/+3
| | | | | | | Pick-to: 6.0 5.15 5.12 Fixes: QTBUG-89172 Change-Id: Icb78c8eeb1dbe4c5d4c6476beebafc0115a91e8c Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>
* Fix documentation warningsVolker Hilsheimer2020-10-241-4/+2
| | | | | | | | | Declare hidden friends like qdoc expects them, and other signature fixes Document function parameters Remove documentation for removed APIs. Change-Id: I44c1caeed0d40be04612129d074acc30b75f5259 Reviewed-by: Allan Sandfeld Jensen <[email protected]>
* Doc: Fix documentation warnings for Qt GUITopi Reinio2020-08-281-0/+4
| | | | | | | | | | | | * Drop deprecation warnings for now-dropped items * Use the 'qt6' define and a new \nothing doc macro to conditionally document items on Qt 6 * Add a custom module header for docs that pulls in also Vulkan headers * Add \internal command for internal classes/functions * Move QtGUI-related code snippets from widgets to gui docs Change-Id: Ieb386b96631a49568d09059906d307c45c01d93a Reviewed-by: Paul Wicking <[email protected]>
* Remove "internal" parameter in QTextLine::draw()Jonas Karlsson2020-08-281-5/+10
| | | | | | | | | | The method is split up into a private and public version, where the parameter is moved into the private method. Fixes: QTBUG-84210 Change-Id: I79e9e02c9b4cc25d31db066e5a9567fdb9bc9fd0 Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]> Reviewed-by: Konstantin Ritt <[email protected]>
* Allow arbitrary baseline shift in QTextCharacterFormatJordi Pujol Foyo2020-08-261-5/+15
| | | | | | | | | | | | | | | Added 6 new methods in QTextFormat and QTextDocument to allow setting/getting specific % positioning for baseline and super/ subscript. Modified QTextLayout to honor those new settings. [ChangeLog][QtGui][QTextLayout,QTextFormat,QTextDocument] Allow text layout modification based on baseline offset and super/subscript % height positioning Fixes: QTBUG-18260 Change-Id: I0796f18224aac8df6baf8359c35022fd98fe64ef Reviewed-by: Qt CI Bot <[email protected]> Reviewed-by: Eskil Abrahamsen Blomfeldt <[email protected]>