I am writing a custom word processor as a hobby project. I'm using python and pyqt6.
I wrote the following. The purpose is that if I select some text and apply bold formatting (e.g. by hitting "ctrl-b") it will switch the formatting. Specifically, if all selected text is bold, the bold formatting should be removed. Otherwise, it will apply bold formatting.
class OvidFont: def __init__(self, ovid) -> None: self.textEditor = ovid.textEditor def setBoldText(self) -> None: fmt = QTextCharFormat() if self.textEditor.currentCharFormat().fontWeight() != QFont.Weight.Bold: print(" setting bold") # for debugging fmt.setFontWeight(QFont.Weight.Bold) else: print(" setting normal") # for debugging fmt.setFontWeight(QFont.Weight.Normal) self.textEditor.textCursor().mergeCharFormat(fmt)
However, it does not remove bold formatting.
For example, in the sentence "this is a test", if I select "is a" and apply bold formatting, I get "this is a test" where "is a" is appropriate Bold. However, with the selection in place, if I hit "ctrl-b" it still remains bold. If I deselect the first or last character, the bold toggle works as expected. (I've tried inverting the if /else logic, but that also failed).
What did I miss?
Update: I added a working minimal test case at https://gist.github.com/ovid/65936985c6838c0220620cf40ba935fa
## The problem with the #setboldtext function is that it uses
self.texteditor.currentcharformat().fontweight() to check the bold status, which only reflects the formatting of the character at the current cursor position, not the entire selected text format. If your cursor is at the beginning or end of the selection, it may not accurately represent the formatting of the entire selection.
setfontweight().
Updated code:
import sys from PyQt6.QtWidgets import QTextEdit, QToolButton, QApplication, QMainWindow, QToolBar from PyQt6.QtGui import QFont, QShortcut, QKeySequence, QTextCharFormat, QTextCursor class OvidFont: def __init__(self, ovid) -> None: self.textEditor = ovid.textEditor def setBoldText(self): cursor = self.textEditor.textCursor() # If there's a selection, and the cursor is not at the block start and at the beginning of the selection, # move the cursor to the end of the selection if cursor.hasSelection() and not cursor.atBlockStart() and cursor.position() == cursor.selectionStart(): cursor.setPosition(cursor.selectionEnd()) # Check if the text (either selected or where the cursor is) is bold is_bold = cursor.charFormat().fontWeight() == QFont.Weight.Bold # Apply the new weight based on the current state new_weight = QFont.Weight.Normal if is_bold else QFont.Weight.Bold self.textEditor.setFontWeight(new_weight) print(f"Bold set to: {'Normal' if is_bold else 'Bold'}") class Ovid(QMainWindow): def __init__(self): super().__init__() self.initUI() def initUI(self): self.setWindowTitle("Ovid") self.setGeometry(100, 100, 200, 200) self.textEditor = QTextEdit() self.setCentralWidget(self.textEditor) self.fonts = OvidFont(self) self.toolbar = QToolBar("Main Toolbar") self.addToolBar(self.toolbar) bold_button = QToolButton() bold_button.setText("B") bold_button.setFont(QFont("Arial", 16, QFont.Weight.Bold)) bold_button.setToolTip("Bold") bold_button.clicked.connect(self.fonts.setBoldText) self.toolbar.addWidget(bold_button) QShortcut(QKeySequence("Ctrl+B"), self, self.fonts.setBoldText) def main(): app = QApplication(sys.argv) ex = Ovid() ex.show() sys.exit(app.exec()) if __name__ == "__main__": main()
The above is the detailed content of Use PyQt6 to switch character formats. For more information, please follow other related articles on the PHP Chinese website!