2009-09-07 15 views
5

ठीक है, मैं एक बहुत बुनियादी QStandardItemModel, कुछ संख्या के साथ भरा है काम नहीं करता। मैं इसे QTableView में प्रदर्शित करने में कामयाब रहा, यह ठीक है। यह sourcemodel स्थापित करने के लिए की जरूरत है, और इस नई परत वास्तविक एक पर कुछ परिवर्तनों करना चाहिए - मैं एक नया मॉडल (QAbstractItemModel या QAbstractProxyModel में से किसी उपवर्ग) है, जो एक मौजूदा मॉडल की एक परत के कुछ प्रकार है बनाया।क्यूटी में, मॉडल चेनिंग के रूप में की उम्मीद

मेरी समस्या यह है कि शीर्ष परत में, "परत मॉडल" data(const QModelIndex & index, int role) सदस्य फ़ंक्शन कभी नहीं कहा जाता है, हालांकि मैं भूमिका पैरामीटर द्वारा प्रदर्शन विधियों को बदलना चाहता हूं।

यहां एक नमूना कोड है, जो दर्शाता है कि मूल मॉडल का data(index,role) हमेशा कॉल किया जाता है, जबकि परत मॉडल का data(index,role) कभी नहीं होता है। क्यूं कर? QTableView ऑब्जेक्ट शीर्ष परत के data(index,role) को "छोड़" कैसे सकता है?

#include <QtGui/QApplication> 
#include <QtGui> 
#include <QStandardItemModel> 

class MyModel : public QStandardItemModel 
{ 
public: 
    MyModel(const int r, const int c, QObject* parent = 0) : QStandardItemModel(r,c,parent) {} 
    QVariant data (const QModelIndex & index, int role = Qt::DisplayRole) const { 
     qDebug() << "mymodel data"; 
     return this->itemFromIndex(index)->data(role); 
    } 
}; 

class MyProxyModel : public QAbstractProxyModel 
{ 
public: 

    MyProxyModel(QObject* parent = 0) : QAbstractProxyModel(parent) {} 
    QModelIndex index (int row, int column, const QModelIndex & parent = QModelIndex()) const { 
     return this->sourceModel()->index(row,column,parent); 
    } 
    QModelIndex parent (const QModelIndex & index) const { 
     return this->sourceModel()->parent(index); 
    } 
    QModelIndex mapFromSource (const QModelIndex & sourceIndex) const 
    { 
     return sourceIndex; 
    } 
    QModelIndex mapToSource (const QModelIndex & proxyIndex) const 
    { 
     return proxyIndex; 
    } 
    QVariant data (const QModelIndex & index, int role = Qt::DisplayRole) const { 
     qDebug() << "myproxymodel data"; 
     return this->sourceModel()->data(index,role); 
    } 

    int rowCount (const QModelIndex & parent = QModelIndex()) const { 
     return this->sourceModel()->rowCount(parent); 
    } 
    int columnCount (const QModelIndex & parent = QModelIndex()) const { 
     return this->sourceModel()->columnCount(parent); 
    } 
}; 

int main(int argc, char *argv[]) 
{ 
    QApplication app(argc,argv); 
    MyModel model(8, 2); 
    MyProxyModel mymodel; 
    mymodel.setSourceModel(&model); 

    QTableView tableView; 
    tableView.setModel(&mymodel); 

    tableView.horizontalHeader()->setStretchLastSection(true); 
    for (int row = 0; row < 8; ++row) { 
     for (int column = 0; column < 2; ++column) { 
      QModelIndex index = model.index(row, column, QModelIndex()); 
      model.setData(index, QVariant((row+1) * (column+1))); 
     } 

    } 
    tableView.show(); 
    return app.exec(); 
} 

उत्तर

6

क्योंकि QTableView डेटा, शायद कुछ इस तरह पुनः प्राप्त करने के मॉडल सूचकांक का उपयोग करता है।

QModelIndex index = model->index(row, column, parentIndex); 
index.data(Qt::DisplayRole); 

और तुम स्रोत मॉडल के मॉडल सूचकांक के बजाय एक सूचकांक के आपके प्रॉक्सी मॉडल के लिए लौट रहे हैं: आपके प्रॉक्सी मॉडल के लिए एक सूचकांक में मॉडल सूचकांक कन्वर्ट करने के लिए

QModelIndex index (int row, int column, const QModelIndex & parent = QModelIndex()) const { 
    return this->sourceModel()->index(row,column,parent); 
} 

कोशिश

QModelIndex index (int row, int column, const QModelIndex & parent = QModelIndex()) const { 
    return this->createIndex(row,column,row); 
} 

स्रोत और स्रोत कार्यों से मैप करने के लिए नक्शे के पुनर्लेखन के लिए मत भूलना।


समाधान

class MyTableProxyModel : public QAbstractProxyModel 
{ 
    Q_OBJECT 
public: 
    MyTableProxyModel (QObject* parent = 0) 
     : QAbstractProxyModel(parent) { 
    } 

    QModelIndex index(int row, int column, const QModelIndex& parent=QModelIndex()) const { 
     return createIndex(row,column,row); 
    } 

    QModelIndex parent(const QModelIndex &index) const { 
     //Works only for non-tree models 
     return QModelIndex(); 
    } 

    QModelIndex mapFromSource(const QModelIndex &source) const { 
     return index(source.row(), source.column(), source.parent()); 
    } 

    QModelIndex mapToSource(const QModelIndex &proxy) const { 
     return (sourceModel()&&proxy.isValid()) 
      ? sourceModel()->index(proxy.row(), proxy.column(), proxy.parent()) 
      : QModelIndex(); 
    } 

    QVariant data(const QModelIndex &index, int role=Qt::DisplayRole) const { 
     qDebug() << "myproxymodel data"; 
     return mapToSource(index).data(role); 
    } 

    int rowCount (const QModelIndex & parent = QModelIndex()) const { 
     return sourceModel() ? sourceModel()->rowCount(parent) : 0; 
    } 

    int columnCount (const QModelIndex & parent = QModelIndex()) const { 
     return sourceModel() ? sourceModel()->columnCount(parent) : 0; 
    } 
}; 
+0

ठीक है, मैं देख रहा हूँ। मेरे पास 2 प्रश्न हैं: - मैं प्रॉक्सी इंडेक्स बनाने के बिना अपना लक्ष्य कैसे प्राप्त कर सकता हूं? मैं प्रॉक्सी मॉडल में अनुक्रमित बनाने से बचने के लिए, क्योंकि वहाँ किसी भी छानने/छंटाई नहीं होगा, आदि चाहते हैं, और है कि मूल मॉडल के अनुक्रमित की एक पूरी दोहराव होगा। - मैं नहीं दिख रहा है कि कैसे 'QSortFilterProxyModel' मुझे बाहर कर सकते हैं। मुझे 'डेटा (..)' फ़ंक्शन को कोड करना होगा, और उपर्युक्त के कारण, मुझे 'इंडेक्स (...)' कोड भी कोड चाहिए। 'QSortFilterProxyModel' क्या है' QAbstractProxyModel' मेरे दृष्टिकोण में नहीं है? –

+1

आपको प्रॉक्सी मॉडल को इंगित करने वाली नई अनुक्रमणिका बनाने की आवश्यकता है। QSortFilterProxyMode आपके लिए प्रॉक्सी इंडेक्स बनाता है। – TimW

+0

बहुत बहुत धन्यवाद, mapToSource और mapFromSource मेरे लिए शैतान की आंखें थीं! यह एक आकर्षण की तरह काम करता है! –

संबंधित मुद्दे