Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. How to replace some characters from selected text of QPlainTextEdit
Qt 6.12 LTS is out! See what's new in the release blog

How to replace some characters from selected text of QPlainTextEdit

Scheduled Pinned Locked Moved Solved General and Desktop
18 Posts 4 Posters 4.2k Views 2 Watching
  • 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.
  • KroMignonK KroMignon

    @Emon-Haque said in How to replace some characters from selected text of QPlainTextEdit:

    I've added last 3 line at the end of the function BUT it still doesn't select the first --

    Hmm strange, you could try to use movePosition():

    cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
    

    EDIT: I am stupid, sorry, but you use a copy constructor to get the cursor:

    auto cursor = editor->textCursor();
    

    Do you have change it to get a reference?

    auto &cursor = editor->textCursor();
    

    Or update the cursor of the editor at the end:

    auto cursor = editor->textCursor();
    ...
    cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
    edit->setTextCursor(cursor);
    
    ? Offline
    ? Offline
    A Former User
    wrote on last edited by A Former User
    #6

    @KroMignon, if I do auto &cursor = editor->textCursor(); I get this

    error: non-const lvalue reference to type 'QTextCursor' cannot bind to a temporary of type 'QTextCursor'.
    

    instead of those 3 lines if I add these 2 lines at the end:

    cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
    edit->setTextCursor(cursor);
    

    it removes the selection and moves cursor to left from the end of selection. The following works:

    cursor.setPosition(start);
    if(numberOfLines > 1){
        for(int i = 0; i < numberOfLines; ++i)
        {
            cursor.insertText("--");
            cursor.movePosition(QTextCursor::NextBlock);
        }
        cursor.movePosition(QTextCursor::Up, QTextCursor::KeepAnchor, numberOfLines);
    }
    else
    {
        cursor.insertText("--");
        cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
        cursor.movePosition(QTextCursor::Right, QTextCursor::KeepAnchor, len + 2);
        // len = cursor.selectedText().length()
    }
    editor->setTextCursor(cursor);
    

    don't know whether there's any better approach.

    For the cursor blinking I've to add QPlainTextEdit::dropEvent(event); in drop event BUT if I add that, It inserts file name in the editor.

    Gojir4G 1 Reply Last reply
    0
    • Gojir4G Gojir4

      @Emon-Haque Note that you need to call editor->setTextCursor(cursor) to make changes effective on the text edit.

      ? Offline
      ? Offline
      A Former User
      wrote on last edited by
      #7

      @Gojir4, that's necessary, thanks.

      1 Reply Last reply
      0
      • ? A Former User

        @KroMignon, if I do auto &cursor = editor->textCursor(); I get this

        error: non-const lvalue reference to type 'QTextCursor' cannot bind to a temporary of type 'QTextCursor'.
        

        instead of those 3 lines if I add these 2 lines at the end:

        cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
        edit->setTextCursor(cursor);
        

        it removes the selection and moves cursor to left from the end of selection. The following works:

        cursor.setPosition(start);
        if(numberOfLines > 1){
            for(int i = 0; i < numberOfLines; ++i)
            {
                cursor.insertText("--");
                cursor.movePosition(QTextCursor::NextBlock);
            }
            cursor.movePosition(QTextCursor::Up, QTextCursor::KeepAnchor, numberOfLines);
        }
        else
        {
            cursor.insertText("--");
            cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
            cursor.movePosition(QTextCursor::Right, QTextCursor::KeepAnchor, len + 2);
            // len = cursor.selectedText().length()
        }
        editor->setTextCursor(cursor);
        

        don't know whether there's any better approach.

        For the cursor blinking I've to add QPlainTextEdit::dropEvent(event); in drop event BUT if I add that, It inserts file name in the editor.

        Gojir4G Offline
        Gojir4G Offline
        Gojir4
        wrote on last edited by
        #8

        For the cursor blinking I've to add QPlainTextEdit::dropEvent(event); in drop event BUT if I add that, It inserts file name in the editor.

        I think you need to call event->acceptProposedAction()when you accept the drop action. But I'm not sure this is related to you issue.

        ? 1 Reply Last reply
        0
        • ? Offline
          ? Offline
          A Former User
          wrote on last edited by A Former User
          #9

          With a lot of Left, Right, Up, Down, Anchor etc., so far I've achieved this:

          x2.gif

          so I can comment in and out an inline selection whole day BUT for multiline, still couldn't figure out why does it keep selecting the next line! Here's what I have right now:

          void QueryView::commentLines()
          {
              auto cursor = editor->textCursor();
              if(!cursor.hasSelection()) return;
          
              auto text = cursor.selectedText();
              int start = cursor.selectionStart();
              int end = cursor.selectionEnd();
              cursor.setPosition(start);
              int startLine = cursor.blockNumber();
              cursor.setPosition(end);
              int endLine = cursor.blockNumber();
              int numberOfLines = endLine - startLine + 1;
              cursor.setPosition(start);
          
              if(text.startsWith("--")){
                  if(numberOfLines > 1){
                      for(int i = 0; i < numberOfLines; ++i){
                          while (cursor.position() < end) {
                              cursor.movePosition(QTextCursor::NextWord, QTextCursor::KeepAnchor);
                              if(cursor.selectedText().contains("--"))
                                  cursor.insertText(cursor.selectedText().replace("--", ""));
                          }
                          cursor.movePosition(QTextCursor::NextBlock);
                      }
                      cursor.setPosition(start, QTextCursor::MoveAnchor);
                      cursor.movePosition(QTextCursor::Down, QTextCursor::KeepAnchor, numberOfLines);
                  }
                  else{
                      int count = 0;
                      while (cursor.position() < end) {
                          cursor.movePosition(QTextCursor::NextWord, QTextCursor::KeepAnchor);
                          if(cursor.selectedText().contains("--"))
                          {
                              cursor.insertText(cursor.selectedText().replace("--", ""));
                              count += 2;
                          }
                      }
                      cursor.setPosition(start, QTextCursor::MoveAnchor);
                      cursor.setPosition(end - count, QTextCursor::KeepAnchor);
                  }
              }
              else{
                  if(numberOfLines > 1){
                      for(int i = 0; i < numberOfLines; ++i)
                      {
                          cursor.insertText("--");
                          cursor.movePosition(QTextCursor::NextBlock);
                      }
                      cursor.movePosition(QTextCursor::Up, QTextCursor::KeepAnchor, numberOfLines);
                  }
                  else
                  {
                      cursor.insertText("--");
                      cursor.movePosition(QTextCursor::Left, QTextCursor::MoveAnchor, 2);
                      cursor.movePosition(QTextCursor::Right, QTextCursor::KeepAnchor, text.length() + 2);
                  }
              }
              editor->setTextCursor(cursor);
          }
          

          The file name is at the top because of calling QPlainTextEdit::dropEvent(event); in dropEvent.

          1 Reply Last reply
          0
          • Gojir4G Gojir4

            For the cursor blinking I've to add QPlainTextEdit::dropEvent(event); in drop event BUT if I add that, It inserts file name in the editor.

            I think you need to call event->acceptProposedAction()when you accept the drop action. But I'm not sure this is related to you issue.

            ? Offline
            ? Offline
            A Former User
            wrote on last edited by
            #10

            @Gojir4, tried that BUT doesn't work.

            Gojir4G 1 Reply Last reply
            0
            • ? A Former User

              @Gojir4, tried that BUT doesn't work.

              Gojir4G Offline
              Gojir4G Offline
              Gojir4
              wrote on last edited by
              #11

              @Emon-Haque Here is what I have for a code editor, similar to what you are doing. It works well on my side:

              #ifndef QT_NO_DRAGANDDROP
              void MainWindow::dragEnterEvent(QDragEnterEvent *e)
              {
                  if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
              
                      for(const QUrl &url : e->mimeData()->urls()){
                          if(url.isLocalFile()){
                              QFileInfo fi(url.toLocalFile());
                              if(fi.exists() && (fi.suffix().startsWith("js"))){
                                  e->acceptProposedAction();
                                  return;
                              }
                          }
                      }
                  }
              }
              void MainWindow::dropEvent(QDropEvent *e)
              {
                  if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
                      e->acceptProposedAction();
                      QStringList files;
                      for(const QUrl &url : e->mimeData()->urls()){
                          QFileInfo fi(url.toLocalFile());
                          if(fi.exists() && (fi.suffix().startsWith("js"))){
                              files << fi.absoluteFilePath();
                          }
                      }
                      if(!files.isEmpty()){
                          // Open files
                          m_wCodeEditorMdi->openJsFiles(files);
                      }
                  }
              }
              
              void MainWindow::dragMoveEvent(QDragMoveEvent *e)
              {
                  e->acceptProposedAction();
              }
              
              void MainWindow::dragLeaveEvent(QDragLeaveEvent *e)
              {
                  e->accept();
              }
              #endif
              

              Hope this helps

              ? 2 Replies Last reply
              0
              • Gojir4G Gojir4

                @Emon-Haque Here is what I have for a code editor, similar to what you are doing. It works well on my side:

                #ifndef QT_NO_DRAGANDDROP
                void MainWindow::dragEnterEvent(QDragEnterEvent *e)
                {
                    if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
                
                        for(const QUrl &url : e->mimeData()->urls()){
                            if(url.isLocalFile()){
                                QFileInfo fi(url.toLocalFile());
                                if(fi.exists() && (fi.suffix().startsWith("js"))){
                                    e->acceptProposedAction();
                                    return;
                                }
                            }
                        }
                    }
                }
                void MainWindow::dropEvent(QDropEvent *e)
                {
                    if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
                        e->acceptProposedAction();
                        QStringList files;
                        for(const QUrl &url : e->mimeData()->urls()){
                            QFileInfo fi(url.toLocalFile());
                            if(fi.exists() && (fi.suffix().startsWith("js"))){
                                files << fi.absoluteFilePath();
                            }
                        }
                        if(!files.isEmpty()){
                            // Open files
                            m_wCodeEditorMdi->openJsFiles(files);
                        }
                    }
                }
                
                void MainWindow::dragMoveEvent(QDragMoveEvent *e)
                {
                    e->acceptProposedAction();
                }
                
                void MainWindow::dragLeaveEvent(QDragLeaveEvent *e)
                {
                    e->accept();
                }
                #endif
                

                Hope this helps

                ? Offline
                ? Offline
                A Former User
                wrote on last edited by A Former User
                #12

                @Gojir4, I've these:

                void CodeEditor::dragEnterEvent(QDragEnterEvent *event)
                { 
                    if(event->mimeData()->text().contains('\n')){
                        event->ignore();
                        return;
                    }
                    event->acceptProposedAction();
                    //QPlainTextEdit::dragEnterEvent(event);
                }
                void CodeEditor::dropEvent(QDropEvent *event)
                {
                    event->acceptProposedAction();
                    //QPlainTextEdit::dropEvent(event);
                    QFile file (event->mimeData()->text().remove("file:///"));
                    file.open(QIODevice::ReadOnly);
                    QTextStream in(&file);
                    insertPlainText(in.readAll());
                    file.close();
                }
                

                if i don't uncomment QPlainTextEdit::dropEvent(event); inside dropEvent, cursor doesn't blink and stuck at the end. If I click somewhere else cursor doesn't apparently move BUT I can type where I clicked.

                Gojir4G 1 Reply Last reply
                0
                • ? A Former User

                  @Gojir4, I've these:

                  void CodeEditor::dragEnterEvent(QDragEnterEvent *event)
                  { 
                      if(event->mimeData()->text().contains('\n')){
                          event->ignore();
                          return;
                      }
                      event->acceptProposedAction();
                      //QPlainTextEdit::dragEnterEvent(event);
                  }
                  void CodeEditor::dropEvent(QDropEvent *event)
                  {
                      event->acceptProposedAction();
                      //QPlainTextEdit::dropEvent(event);
                      QFile file (event->mimeData()->text().remove("file:///"));
                      file.open(QIODevice::ReadOnly);
                      QTextStream in(&file);
                      insertPlainText(in.readAll());
                      file.close();
                  }
                  

                  if i don't uncomment QPlainTextEdit::dropEvent(event); inside dropEvent, cursor doesn't blink and stuck at the end. If I click somewhere else cursor doesn't apparently move BUT I can type where I clicked.

                  Gojir4G Offline
                  Gojir4G Offline
                  Gojir4
                  wrote on last edited by
                  #13

                  @Emon-Haque I suspect that the drag&drop event is in a unfinished state and the cursor stop blinking. calling e->accept() in dragLeaveEvent should terminate the drag&drop action and restore the cursor blinking

                  ? 1 Reply Last reply
                  0
                  • Gojir4G Gojir4

                    @Emon-Haque I suspect that the drag&drop event is in a unfinished state and the cursor stop blinking. calling e->accept() in dragLeaveEvent should terminate the drag&drop action and restore the cursor blinking

                    ? Offline
                    ? Offline
                    A Former User
                    wrote on last edited by
                    #14

                    @Gojir4, exactly, now with dragMove and dragleave with your content. it blinks. Thanks. For frag and drop, I always have to implement all 4 of those?

                    Gojir4G 1 Reply Last reply
                    0
                    • ? A Former User

                      @Gojir4, exactly, now with dragMove and dragleave with your content. it blinks. Thanks. For frag and drop, I always have to implement all 4 of those?

                      Gojir4G Offline
                      Gojir4G Offline
                      Gojir4
                      wrote on last edited by
                      #15

                      @Emon-Haque Honestly I don't know. I started recently using drag and drop. the doc says

                      For more sophisticated applications, reimplementing dragMoveEvent() and dragLeaveEvent() will let you make certain parts of your widgets sensitive to drop events, and give you more control over drag and drop in your application.

                      I'm not really understanding what it means. But yeah maybe my solution is over-complicated

                      1 Reply Last reply
                      0
                      • ? Offline
                        ? Offline
                        A Former User
                        wrote on last edited by A Former User
                        #16

                        Here's a hacky solution. In the multiline uncomment section if I do this I can comment / uncomment whole day:

                        if(numberOfLines > 1){
                            for(int i = 0; i < numberOfLines; ++i){
                                while (cursor.position() < end) {
                                    cursor.movePosition(QTextCursor::NextWord, QTextCursor::KeepAnchor);
                                    if(cursor.selectedText().contains("--"))
                                        cursor.insertText(cursor.selectedText().replace("--", ""));
                                }
                                cursor.movePosition(QTextCursor::NextBlock);
                            }
                            cursor.setPosition(start, QTextCursor::MoveAnchor);
                            cursor.movePosition(QTextCursor::Down, QTextCursor::KeepAnchor, numberOfLines - 2);
                            cursor.movePosition(QTextCursor::EndOfLine, QTextCursor::KeepAnchor);
                        }
                        

                        For now I'll move forward with that as I'm new to Qt Widget app and, hopefully, will keep exploring more.

                        1 Reply Last reply
                        1
                        • Gojir4G Gojir4

                          @Emon-Haque Here is what I have for a code editor, similar to what you are doing. It works well on my side:

                          #ifndef QT_NO_DRAGANDDROP
                          void MainWindow::dragEnterEvent(QDragEnterEvent *e)
                          {
                              if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
                          
                                  for(const QUrl &url : e->mimeData()->urls()){
                                      if(url.isLocalFile()){
                                          QFileInfo fi(url.toLocalFile());
                                          if(fi.exists() && (fi.suffix().startsWith("js"))){
                                              e->acceptProposedAction();
                                              return;
                                          }
                                      }
                                  }
                              }
                          }
                          void MainWindow::dropEvent(QDropEvent *e)
                          {
                              if(e->mimeData()->hasUrls() && e->mimeData()->hasFormat("text/uri-list")){
                                  e->acceptProposedAction();
                                  QStringList files;
                                  for(const QUrl &url : e->mimeData()->urls()){
                                      QFileInfo fi(url.toLocalFile());
                                      if(fi.exists() && (fi.suffix().startsWith("js"))){
                                          files << fi.absoluteFilePath();
                                      }
                                  }
                                  if(!files.isEmpty()){
                                      // Open files
                                      m_wCodeEditorMdi->openJsFiles(files);
                                  }
                              }
                          }
                          
                          void MainWindow::dragMoveEvent(QDragMoveEvent *e)
                          {
                              e->acceptProposedAction();
                          }
                          
                          void MainWindow::dragLeaveEvent(QDragLeaveEvent *e)
                          {
                              e->accept();
                          }
                          #endif
                          

                          Hope this helps

                          ? Offline
                          ? Offline
                          A Former User
                          wrote on last edited by A Former User
                          #17

                          @Gojir4, I wanted to accept this as answer, BUT wrongly I've selected mine. How to remove the currently accepted and set yours as accepted?

                          JonBJ 1 Reply Last reply
                          0
                          • ? A Former User

                            @Gojir4, I wanted to accept this as answer, BUT wrongly I've selected mine. How to remove the currently accepted and set yours as accepted?

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

                            @Emon-Haque I think you just do so from the vertical "..." at the right-hand side of the new answer you want to accept.

                            1 Reply Last reply
                            1

                            • Login

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