0

PyQt メーリング リストの Benno Dielmann からの次の質問は、2008 年以来未回答のままです。

[..] QTableView セルの内容を描画するための paint() を実装する QStyledItemDelegate サブクラスがあります。これらのセルの 1 つにフォーカスがある場合、フォーカス四角形を描画するにはどうすればよいですか? 私はこれを試しました:

class MyDelegate(QStyledItemDelegate):  
    ...
    def paint(self, painter, option, index):
        ...
        painter.save()
        if option.state & QStyle.State_HasFocus:
           self.parent().style().drawPrimitive(QStyle.PE_FrameFocusRect, option, painter)
        ...
        painter.restore()

しかし、これは単に何もしません。エラーもフォーカス フレームもありません。カスタムペイントされたセルの1つにフォーカスがある場合、QStyleシステムに通常のフォーカスフレームをペイントさせたいだけです。QStyle のドキュメントでは、QStyleOptionFocusRect を作成し、initFrom() を使用するように指示されています。しかし、initFrom() には、この場合にない QWidget が必要です。

私はそれを理解していません。

カスタム デリゲートによって描画された QTableView セルでフォーカス フレームを取得する通常の方法は何ですか?[..]

4

1 に答える 1

1

私は同じ問題に遭遇しました。多くの欲求不満の後、非推奨の QStyledItem クラスに答えが埋もれていることがわかりました。そのコードに基づく PyQt/PySide ソリューションは次のとおりです。

class MyDelegate(QtGui.QStyledItemDelegate):
    ...
    def drawFocus(self, painter, option, rect, widget=None):
        if (option.state & QtGui.QStyle.State_HasFocus) == 0 or not rect.isValid():
            return
        o = QtGui.QStyleOptionFocusRect()
        # no operator= in python, so we have to do this manually
        o.state = option.state
        o.direction = option.direction
        o.rect = option.rect
        o.fontMetrics = option.fontMetrics
        o.palette = option.palette

        o.state |= QtGui.QStyle.State_KeyboardFocusChange
        o.state |= QtGui.QStyle.State_Item
        cg = QtGui.QPalette.Normal if (option.state & QtGui.QStyle.State_Enabled) else QtGui.QPalette.Disabled
        o.backgroundColor = option.palette.color(cg, QtGui.QPalette.Highlight if (option.state & QtGui.QStyle.State_Selected) else QtGui.QPalette.Window)
        style = widget.style() if widget else QtGui.QApplication.style()
        style.drawPrimitive(QtGui.QStyle.PE_FrameFocusRect, o, painter, widget)

    def paint(self, painter, option, index):
        painter.save()
        # ... draw your delegate here, or call your widget's render method ...
        painter.restore()

        painter.save()
        # omit the last argument if you're not drawing a widget
        self.drawFocus(painter, option, option.rect, widget)
        painter.restore()
于 2014-12-31T16:34:45.290 に答える