My custom label's text is uneven when rotated
09:20 27 Nov 2025

I've created a custom qlabel using pyqt, however the text is slightly uneven when rotated. I've attached a picture of this vs an unrotated label. I've tried fixing it with setRenderHint Antialiasing, TextAntialiasing, and SmoothPixmapTransform - but it doesn't seem to make a difference. If there was a way to properly align the text onto one level, that could possibly help?

Custom Label Issue Example

class Label(QtWidgets.QLabel):
    def __init__(self, parent=None, element=None):
        super().__init__(parent)

        self.element = element

        if self.element is not None:
            self.configuration = self._parse_element()

        self._text = self.configuration.attrib.get("Text", "")
        self._position_x, self._position_y = tuple(
            map(int, self.configuration.attrib.get("Position", "177,5").split(","))
        )
        self._width, self._height = tuple(
            map(int, self.configuration.attrib.get("Size", "267,27").split(","))
        )
        self._size_ratio = self.configuration.attrib.get("SizeRatio", "0.0")
        self._font = FontManager(
            self.configuration.attrib.get("Font", "Dialog#1#16")
        ).get_font()
        self._rotation = self.configuration.attrib.get("Rotation", "0.0")
        self._scale_x = self.configuration.attrib.get("ScaleX", "1.0")
        self._scale_y = self.configuration.attrib.get("ScaleY", "1.0")

        self._setup_visuals()

    def _parse_element(self):
        for child in self.element:
            if child.tag == "Configuration":
                return child
        return None

    def _setup_visuals(self):
        self.setStyleSheet("""
                           background-color: none;
                           border: none;
                           margin: 0px;
                """)

        self.setText(self._text)

        fm = QtGui.QFontMetrics(self._font)
        text_width = fm.horizontalAdvance(self._text)
        text_height = fm.height()

        if float(self._size_ratio) > 0:
            self._height = int(self._width / float(self._size_ratio))

        self.move(self._position_x, self._position_y)
        self.resize(max(self._width, text_width), max(self._height, text_height))

    @typing_extensions.override
    def paintEvent(self, event):
        painter = QtGui.QPainter(self)
        painter.setRenderHint(QtGui.QPainter.RenderHint.Antialiasing)
        painter.setRenderHint(QtGui.QPainter.RenderHint.TextAntialiasing)
        painter.setRenderHint(QtGui.QPainter.RenderHint.SmoothPixmapTransform)

        painter.setFont(self._font)

        painter.translate(0, 0)
        painter.rotate(degrees(float(self._rotation)))
        painter.scale(float(self._scale_x), float(self._scale_y))

        painter.drawText(0, 0, self.width(), self.height(), QtCore.Qt.AlignmentFlag.AlignLeft | QtCore.Qt.AlignmentFlag.AlignTop, self._text)

    @typing_extensions.override
    def sizeHint(self):
        fm = self.fontMetrics()

        w = fm.horizontalAdvance(self.text())
        h = fm.height()

        a = float(self._rotation)

        r_w = abs(w * cos(a)) + abs(h * sin(a))
        r_h = abs(w * sin(a)) + abs(h * cos(a))

        return QtCore.QSize(int(r_w), int(r_h))

python pyqt qwidget pyqt6