Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. QTextEdit and "carriage-return" / "\r" character
Forum Update on Monday, May 27th 2025

QTextEdit and "carriage-return" / "\r" character

Scheduled Pinned Locked Moved Solved General and Desktop
8 Posts 3 Posters 16.9k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • JonBJ Offline
    JonBJ Offline
    JonB
    wrote on last edited by JonB
    #1

    I am using a (multi-line, scrollable) QTextEdit widget to display the grabbed output from a QProcess in real-time.

    One process deliberately embeds a \r (carriage-return) characters in its output --- it's outputting a "progress" something like:

    10%\r20%\r30% ...
    

    This is a common thing for command-line programs to do: in a terminal this avoids occupying multiple lines because the \r jumps back to the start of the current line and overwrites what's there.

    When I blindly send this raw output --- along with everything else --- to QTextEdit::append() the user sees multiple lines instead, making the output look voluminous.

    [EDIT: Hmm, it's a bit confusing. What I actually seem to see is an extra blank line between items, like:

    10
    
    20
    
    30
    

    ]

    • I take it that QTextEdit is not going to handle \r by returning to the start of a line, right?
    • If I want the "nice" behaviour, I would have to do shenanigans along the lines of parsing the output, locating the \rs, and then not just simply appending but rather actually replacing the previous last line which was added, right?
    • Assuming that would be required, it's more code than it's worth. The best might be to blindly remove any \rs before sending to QTextEdit: I wouldn't get the "overwrite" behaviour, I'd get one great long line, but that might be preferable to multiple lines for the user in the output, right?
    aha_1980A 1 Reply Last reply
    0
    • JonBJ JonB

      I am using a (multi-line, scrollable) QTextEdit widget to display the grabbed output from a QProcess in real-time.

      One process deliberately embeds a \r (carriage-return) characters in its output --- it's outputting a "progress" something like:

      10%\r20%\r30% ...
      

      This is a common thing for command-line programs to do: in a terminal this avoids occupying multiple lines because the \r jumps back to the start of the current line and overwrites what's there.

      When I blindly send this raw output --- along with everything else --- to QTextEdit::append() the user sees multiple lines instead, making the output look voluminous.

      [EDIT: Hmm, it's a bit confusing. What I actually seem to see is an extra blank line between items, like:

      10
      
      20
      
      30
      

      ]

      • I take it that QTextEdit is not going to handle \r by returning to the start of a line, right?
      • If I want the "nice" behaviour, I would have to do shenanigans along the lines of parsing the output, locating the \rs, and then not just simply appending but rather actually replacing the previous last line which was added, right?
      • Assuming that would be required, it's more code than it's worth. The best might be to blindly remove any \rs before sending to QTextEdit: I wouldn't get the "overwrite" behaviour, I'd get one great long line, but that might be preferable to multiple lines for the user in the output, right?
      aha_1980A Offline
      aha_1980A Offline
      aha_1980
      Lifetime Qt Champion
      wrote on last edited by aha_1980
      #2

      @JNBarchan i think you get an empty line as \r is translated to \n in QTextEdit. append() itself adds another line break.

      the easiest way would be QString::trimmed() before appending.

      if you like to simulate carriage return, you would need to replace the last line instead appending if your line contains \r (you would remove the \r nevertheless). not sure how fluent that would look, though.

      Qt has to stay free or it will die.

      JonBJ 1 Reply Last reply
      4
      • aha_1980A aha_1980

        @JNBarchan i think you get an empty line as \r is translated to \n in QTextEdit. append() itself adds another line break.

        the easiest way would be QString::trimmed() before appending.

        if you like to simulate carriage return, you would need to replace the last line instead appending if your line contains \r (you would remove the \r nevertheless). not sure how fluent that would look, though.

        JonBJ Offline
        JonBJ Offline
        JonB
        wrote on last edited by JonB
        #3

        @aha_1980

        append() itself adds another line break.

        Hmm, where's that documented?** Because I'm receiving "chunks" of output from the subprocess, I want to add exactly what I get from there without extra newlines etc. Is there any different between QTextEdit.append(newStuff) versus QTextEdit.setText(QTextEdit().getText() + newStuff) in this "another line break" respect?

        ** EDIT: OK, I'm seeing the documentation for QTextEdit.append() is talking about "paragraphs" and things. I had not intended that: I just want the quickest way to append some new text to whatever is there exactly. I can now see that QTextEdit.setPlainText(QTextEdit().toPlainText() + newStuff) is getting rid of unwanted blank lines (that's good, though it looks "inefficient"?).

        the easiest way would be QString::trimmed() before appending.

        Does me no good. Because I get "chunks of output" as a single string (byte array actually), the \rs are embedded all over the place in the middle of stuff. That's why I'd have to scan the string to do my work. At the moment I've just put in str.replace("\r", ""), and now at least I'm not getting the blank lines.

        if you like to simulate carriage return, you would need to replace the last line instead appending if your line contains \r (you would remove the \r nevertheless). not sure how fluent that would look, though.

        Yes, and that would mean looking at my existing content to determine where "the last line" starts, and recognising multiple lines with \r in them in what is to be "appended", and I can't be bothered with the whole thing!

        aha_1980A 1 Reply Last reply
        0
        • JonBJ JonB

          @aha_1980

          append() itself adds another line break.

          Hmm, where's that documented?** Because I'm receiving "chunks" of output from the subprocess, I want to add exactly what I get from there without extra newlines etc. Is there any different between QTextEdit.append(newStuff) versus QTextEdit.setText(QTextEdit().getText() + newStuff) in this "another line break" respect?

          ** EDIT: OK, I'm seeing the documentation for QTextEdit.append() is talking about "paragraphs" and things. I had not intended that: I just want the quickest way to append some new text to whatever is there exactly. I can now see that QTextEdit.setPlainText(QTextEdit().toPlainText() + newStuff) is getting rid of unwanted blank lines (that's good, though it looks "inefficient"?).

          the easiest way would be QString::trimmed() before appending.

          Does me no good. Because I get "chunks of output" as a single string (byte array actually), the \rs are embedded all over the place in the middle of stuff. That's why I'd have to scan the string to do my work. At the moment I've just put in str.replace("\r", ""), and now at least I'm not getting the blank lines.

          if you like to simulate carriage return, you would need to replace the last line instead appending if your line contains \r (you would remove the \r nevertheless). not sure how fluent that would look, though.

          Yes, and that would mean looking at my existing content to determine where "the last line" starts, and recognising multiple lines with \r in them in what is to be "appended", and I can't be bothered with the whole thing!

          aha_1980A Offline
          aha_1980A Offline
          aha_1980
          Lifetime Qt Champion
          wrote on last edited by aha_1980
          #4

          @JNBarchan said in QTextEdit and "carriage-return" / "\r" character:

          @aha_1980

          append() itself adds another line break.

          Hmm, where's that documented?

          http://doc.qt.io/qt-5/qtextedit.html#append :
          Appends a new paragraph with text to the end of the text edit.

          Because I'm receiving "chunks" of output from the subprocess, I want to add exactly what I get from there without extra newlines etc.

          Understand.

          Is there any different between QTextEdit.append(newStuff) versus QTextEdit.setText(QTextEdit().getText() + newStuff) in this "another line break" respect? I guess QTextEdit.append(newStuff) would be something like QTextEdit.setText(QTextEdit().getText() + '\n' + newStuff)

          You could try http://doc.qt.io/qt-5/qtextedit.html#insertPlainText . It might be faster than calling setText() all over again. Thats also what QtCreator does in the Application and Compile Output windows.

          the easiest way would be QString::trimmed() before appending.

          Does me no good. Because I get "chunks of output" as a single string (byte array actually), the \rs are embedded all over the place in the middle of stuff.

          Ok, yes in that case trimmed() is not enough.

          That's why I'd have to scan the string to do my work. At the moment I've just put in str.replace("\r", ""), and now at least I'm not getting the blank lines.

          If you want a simple solution, than you could stick with this.

          Qt has to stay free or it will die.

          JonBJ 1 Reply Last reply
          2
          • aha_1980A aha_1980

            @JNBarchan said in QTextEdit and "carriage-return" / "\r" character:

            @aha_1980

            append() itself adds another line break.

            Hmm, where's that documented?

            http://doc.qt.io/qt-5/qtextedit.html#append :
            Appends a new paragraph with text to the end of the text edit.

            Because I'm receiving "chunks" of output from the subprocess, I want to add exactly what I get from there without extra newlines etc.

            Understand.

            Is there any different between QTextEdit.append(newStuff) versus QTextEdit.setText(QTextEdit().getText() + newStuff) in this "another line break" respect? I guess QTextEdit.append(newStuff) would be something like QTextEdit.setText(QTextEdit().getText() + '\n' + newStuff)

            You could try http://doc.qt.io/qt-5/qtextedit.html#insertPlainText . It might be faster than calling setText() all over again. Thats also what QtCreator does in the Application and Compile Output windows.

            the easiest way would be QString::trimmed() before appending.

            Does me no good. Because I get "chunks of output" as a single string (byte array actually), the \rs are embedded all over the place in the middle of stuff.

            Ok, yes in that case trimmed() is not enough.

            That's why I'd have to scan the string to do my work. At the moment I've just put in str.replace("\r", ""), and now at least I'm not getting the blank lines.

            If you want a simple solution, than you could stick with this.

            JonBJ Offline
            JonBJ Offline
            JonB
            wrote on last edited by JonB
            #5

            @aha_1980

            http://doc.qt.io/qt-5/qtextedit.html#append :
            Appends a new paragraph with text to the end of the text edit.

            You could try http://doc.qt.io/qt-5/qtextedit.html#insertPlainText . It might be faster than calling setText() all over again

            Yes, I had put an EDIT into my post as I came to realise these. It turns out most of the "ugliness" was actually due to blank line from each append(). Now with setText() always instead, it doesn't look too bad.

            Qt doesn't offer any "raw" append? In native Windows (and maybe HTML/JS too), when I want to append like this I go something like "caret to end" and then "insert characters". I assume that helps with scroll smoothness/no redraw, whereas setText() is going to rewrite the whole control each time? Since I'm gathering external output, there could be like a megabyte there and I just get one more line at a time to append....

            I've decided now to just leave any \rs in the output as-is. They go to next line, but removing them just results in a very long line anyway, so it's a matter of opinion either way. It leaves my code more generic & simple.

            1 Reply Last reply
            0
            • R Offline
              R Offline
              Rondog
              wrote on last edited by Rondog
              #6

              I have noticed this behavior. The append(...) option will add a line break but insert(...) will not. I would go with inset(...) unless you are processing the text to manually separate all appends calls to separate lines of text. QString::split('/r'); will work nicely to separate into individual lines.

              If you use the insert(...) option you need to make sure the cursor at the end otherwise the new text could appear in the middle of the document. A simple mouse click will move the insert position.

              Reading back all the text, adding new text, then calling setText(...) doesn't sound efficient.

              JonBJ 2 Replies Last reply
              1
              • R Rondog

                I have noticed this behavior. The append(...) option will add a line break but insert(...) will not. I would go with inset(...) unless you are processing the text to manually separate all appends calls to separate lines of text. QString::split('/r'); will work nicely to separate into individual lines.

                If you use the insert(...) option you need to make sure the cursor at the end otherwise the new text could appear in the middle of the document. A simple mouse click will move the insert position.

                Reading back all the text, adding new text, then calling setText(...) doesn't sound efficient.

                JonBJ Offline
                JonBJ Offline
                JonB
                wrote on last edited by
                #7

                @Rondog
                Ah, OK, I simply had not noticed there is a QTextEdit::insertPlainText(). I had seen QTextEdit::setText() & QTextEdit::append(). I'm familiar with having to position the cursor for appending with insert. I see QTextEdit::moveCursor().

                This sounds like I'd expect instead of resetting whole text! Thanks.

                1 Reply Last reply
                0
                • R Rondog

                  I have noticed this behavior. The append(...) option will add a line break but insert(...) will not. I would go with inset(...) unless you are processing the text to manually separate all appends calls to separate lines of text. QString::split('/r'); will work nicely to separate into individual lines.

                  If you use the insert(...) option you need to make sure the cursor at the end otherwise the new text could appear in the middle of the document. A simple mouse click will move the insert position.

                  Reading back all the text, adding new text, then calling setText(...) doesn't sound efficient.

                  JonBJ Offline
                  JonBJ Offline
                  JonB
                  wrote on last edited by JonB
                  #8

                  @Rondog
                  I have now simply set my append code to:

                      # append further text at the end, efficiently
                      self.text.moveCursor(QtGui.QTextCursor.End)
                      self.text.insertPlainText(moreText)
                  

                  This also seems to scroll to the end for me, avoiding the need for me to explicitly call set the vertical scrollbar's position.

                  Sometimes it scrolls to end, but not always. Since I want scroll-to-end (and the widget is read-only, so no visible cursor), I have appended:

                      sb = self.text.verticalScrollBar()
                      sb.setValue(sb.maximum())
                  ``
                  
                  Thanks to all.
                  1 Reply Last reply
                  0

                  • Login

                  • Login or register to search.
                  • First post
                    Last post
                  0
                  • Categories
                  • Recent
                  • Tags
                  • Popular
                  • Users
                  • Groups
                  • Search
                  • Get Qt Extensions
                  • Unsolved