我最近花了一些时间研究如何在 PyQt 中使用 QDataStream 和 QTreeWidget。我从来没有找到具体的例子来做这件事,而且 QDataStream 的 pyqt 文档一般来说似乎非常稀缺。所以我想我会在这里发布一个问题作为面包屑路径,以防其他人需要提示。如果有人想跳进去试一试,我会稍等一下,我会用我自己的努力稍后发回。

问题是:在 PyQt 中,如何使用 QDataStream 将 QTreeWidgetItems 作为 native QT 对象保存到文件中,然后读回文件以完全按照保存的方式恢复树结构?

埃里克

最佳答案

one of my other answers 到一个类似的问题,我写了一个简单的演示,序列化为 xml。

相同的代码可以很容易地适用于 QDataStream。我并不是真的推荐它作为解决方案(可能有几十种不同的方法来实现同一件事),但它至少提供了一个工作示例:

import sip
sip.setapi('QString', 2)

from xml.etree import cElementTree as etree
from PyQt4 import QtGui, QtCore

class Window(QtGui.QWidget):
    def __init__(self, xml):
        QtGui.QWidget.__init__(self)
        self.tree = QtGui.QTreeWidget(self)
        self.tree.header().hide()
        self.button = QtGui.QPushButton('Export', self)
        self.button.clicked[()].connect(self.exportTree)
        layout = QtGui.QVBoxLayout(self)
        layout.addWidget(self.tree)
        layout.addWidget(self.button)
        self._array = QtCore.QByteArray()
        self._buffer = QtCore.QBuffer(self._array, self)
        self._buffer.open(QtCore.QIODevice.ReadWrite)
        self._datastream = QtCore.QDataStream(self._buffer)
        self.importTree(xml)

    def importTree(self, xml):
        def build(item, root):
            for element in root.getchildren():
                child = QtGui.QTreeWidgetItem(item)
                data = element.attrib['data'].encode('ascii')
                self._array.swap(self._array.fromBase64(data))
                self._buffer.reset()
                self._datastream >> child
                build(child, element)
            item.setExpanded(True)
        root = etree.fromstring(xml)
        build(self.tree.invisibleRootItem(), root)

    def exportTree(self):
        def build(item, root):
            for row in range(item.childCount()):
                child = item.child(row)
                self._array.clear()
                self._buffer.reset()
                self._datastream << child
                data = self._array.toBase64().data().decode('ascii')
                element = etree.SubElement(root, 'node', data=data)
                build(child, element)
        root = etree.Element('root')
        build(self.tree.invisibleRootItem(), root)
        from xml.dom import minidom
        print(minidom.parseString(etree.tostring(root)).toprettyxml())

if __name__ == '__main__':

    import sys
    app = QtGui.QApplication(sys.argv)
    window = Window("""\
<?xml version="1.0" ?>
<root>
    <node data="AAAAAQAAAAEAAAAJAAAAQwAB/////wAA
                AAAAAAAAAAEAAAAKAAAAAAYAUgBlAGQ=">
        <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAP//
                    //8AAAAAAAEAAAAKAAAAAAgAQwB5AGEAbg==">
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAICA
                        AAAAAAAAAAEAAAAKAAAAAAoARwByAGUAZQBu"/>
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAAAA
                        //8AAAAAAAEAAAAKAAAAAAgAQgBsAHUAZQ=="/>
        </node>
        <node data="AAAAAQAAAAEAAAAJAAAAQwAB/////6Wl
                    AAAAAAAAAAEAAAAKAAAAAAwATwByAGEAbgBnAGU=">
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//+AgAAA
                        gIAAAAAAAAEAAAAKAAAAAAwAUAB1AHIAcABsAGU="/>
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAICA
                        AAAAAAAAAAEAAAAKAAAAAAoARwByAGUAZQBu"/>
        </node>
    </node>
    <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAP//
                //8AAAAAAAEAAAAKAAAAAAgAQwB5AGEAbg==">
        <node data="AAAAAQAAAAEAAAAJAAAAQwAB/////6Wl
                    AAAAAAAAAAEAAAAKAAAAAAwATwByAGEAbgBnAGU=">
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAP//
                        //8AAAAAAAEAAAAKAAAAAAgAQwB5AGEAbg=="/>
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//+AgAAA
                        gIAAAAAAAAEAAAAKAAAAAAwAUAB1AHIAcABsAGU="/>
        </node>
        <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAICA
                    AAAAAAAAAAEAAAAKAAAAAAoARwByAGUAZQBu">
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB//8AAAAA
                        //8AAAAAAAEAAAAKAAAAAAgAQgBsAHUAZQ=="/>
            <node data="AAAAAQAAAAEAAAAJAAAAQwAB/////wAA
                        AAAAAAAAAAEAAAAKAAAAAAYAUgBlAGQ="/>
        </node>
    </node>
</root>
        """)
    window.setGeometry(800, 300, 300, 300)
    window.show()
    sys.exit(app.exec_())

关于python - PyQt:使用 QDataStream 保存原生 QTreeWidgets,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/21653108/

10-09 07:51