2014-09-08 6 views
5

मैंने QAbstractItemModel subclassing द्वारा आलसी आबादी वाले वृक्षदृश्य को लागू किया है।QSortFilterProxyModel और आलसी आबादी वाले पेड़दृश्य

https://gist.github.com/gnufied/db9c4d805e2bb24d8c23

(मैं संदेश सेवा से गंदगी के रूप में कोड इनलाइन चिपकाने नहीं कर रहा हूँ, इसलिए)

यह मूल रूप से तालिका में संग्रहीत श्रेणीबद्ध डेटा का एक पेड़ प्रतिनिधित्व है: कार्यान्वयन की तरह कुछ लग रहा है। अब, मैं चाहता हूं कि उपयोगकर्ता स्तंभों के आधार पर पंक्तियों को सॉर्ट करने में सक्षम हों। कॉलम कहां हैं, "गिनती" या "संदर्भ गणना"। ये मान मूल रूप से पूर्णांक हैं।

अपने स्वयं के कार्यों पर कार्यान्वयन, जब तक कि मैं QSortFilterProxyModel में फेंक नहीं देता और मुझे दृश्य में बहुत सारी खाली पंक्तियां मिलती हैं। मुश्किल समस्या यह है कि यह तब होता है जब मेरे पास बहुत सारी पंक्तियां होती हैं (जैसे हजारों या तो)।

छँटाई प्रॉक्सी लागू करने के लिए कोड है:

rootItem = RBKit::SqlConnectionPool::getInstance()->rootOfSnapshot(snapShotVersion); 
model = new RBKit::HeapDataModel(rootItem, this); 
proxyModel = new SortObjectProxyModel(this); 
proxyModel->setSourceModel(model); 
ui->treeView->setModel(proxyModel); 
ui->treeView->setSortingEnabled(true); 

मैं QSortFilterProxyModel वर्ग और उपवर्ग कार्यान्वयन subclassed है वास्तव में सरल है:

https://gist.github.com/gnufied/115f1a4fae3538534511

प्रलेखन कहता है -

" इस जटिल प्रॉक्सिंग तंत्र को अधिक जटिल व्यवहार के साथ स्रोत मॉडल के लिए ओवरराइड करने की आवश्यकता हो सकती है; एफ या उदाहरण, यदि स्रोत मॉडल कस्टम है IChildren() कार्यान्वयन प्रदान करता है, तो आपको प्रॉक्सी मॉडल में भी एक प्रदान करना चाहिए। "

लेकिन उससे परे, मुझे यकीन नहीं है - मुझे क्या याद आ रहा है।

उत्तर

4

तो, मुझे लगता है कि मुझे समाधान मिला है और फिक्स प्रॉक्सी मॉडल सबक्लास में fetchMore को फिर से कार्यान्वित करने लग रहा है, क्योंकि स्रोत मॉडल द्वारा रिपोर्ट की गई पंक्तियों को सम्मिलित नहीं किया गया है, जहां पंक्तियां वास्तव में मौजूद हैं, जहां पंक्तियां वास्तव में मौजूद हैं (दृश्यों में पंक्तियों का स्वामित्व है प्रॉक्सी मॉडल द्वारा), इसलिए ऐसा लगता है कि यह मेरे लिए तय किया गया है:

#include "sortobjectproxymodel.h" 

SortObjectProxyModel::SortObjectProxyModel(QObject *parent) : 
    QSortFilterProxyModel(parent) 
{ 
} 

bool SortObjectProxyModel::hasChildren(const QModelIndex &parent) const 
{ 
    const QModelIndex sourceIndex = mapToSource(parent); 
    return sourceModel()->hasChildren(sourceIndex); 
} 

int SortObjectProxyModel::rowCount(const QModelIndex &parent) const 
{ 
    const QModelIndex sourceIndex = mapToSource(parent); 
    return sourceModel()->rowCount(sourceIndex); 
} 

bool SortObjectProxyModel::canFetchMore(const QModelIndex &parent) const 
{ 
    if(!parent.isValid()) 
     return true; 
    else { 
     const QModelIndex sourceIndex = mapToSource(parent); 
     return sourceModel()->canFetchMore(sourceIndex); 
    } 
} 

void SortObjectProxyModel::fetchMore(const QModelIndex &parent) 
{ 
    if (parent.isValid() && parent.column() == 0) { 
     int row = parent.row(); 
     int startRow = row + 1 ; 
     const QModelIndex sourceIndex = mapToSource(parent); 
     RBKit::HeapItem *item = static_cast<RBKit::HeapItem *>(sourceIndex.internalPointer()); 
     if (!item->childrenFetched) { 
      qDebug() << "Insert New Rows at :" << startRow << " ending at : " << startRow + item->childrenCount(); 
      beginInsertRows(parent, startRow, startRow + item->childrenCount()); 
      item->fetchChildren(); 
      endInsertRows(); 
     } 
    } 
} 
1

मेरे विरोध में आपको शीर्ष परत पर सॉर्ट करने के लिए QSortFilterProxyModel उपclass करने की आवश्यकता नहीं है। यदि आपके विचार के लिए sortingEnabled == true है तो दृश्य प्रॉक्सी मॉडल पर सॉर्टिंग करेगा, जो मॉडल को स्वयं को सॉर्ट करने के लिए वांछनीय नहीं है। आपको proxyModel->sort(desiredColumn) पर कॉल करने की आवश्यकता है और यह आपके डेटा को बदलने के बिना दृश्य में क्रमबद्ध model प्रदर्शित करेगा। डिफ़ॉल्ट रूप से QSortFilterProxyModel में dynamicSortFilter संपत्ति है, जो डेटा परिवर्तन या पंक्ति डालने या निकालने पर प्रॉक्सी मॉडल को फिर से क्रमबद्ध करने का कारण बनती है। मुझे उत्सर्जित डेटा दिखाई नहीं दे रहा है आपके HeapDataModel में कहीं भी सिग्नल सिग्नल, तो शायद गतिशील रूप से क्रमबद्ध पंक्तियां प्राप्त करने के लिए यह संकेत हो सकता है। यदि आपको सबिटैम्स को सॉर्ट करने की आवश्यकता है तो यह थोड़ा अधिक जटिल हो जाता है और फिर आपको QSortFilterProxyModel उप-वर्गों की आवश्यकता होगी। ये मॉडल-व्यू अबास्ट्रक्शन सीखना मुश्किल होता है लेकिन एक बार जब आप इसे प्राप्त कर लेते हैं तो आप तेजी से चमत्कार कर सकते हैं।

rootItem = RBKit::SqlConnectionPool::getInstance()->rootOfSnapshot(snapShotVersion); 
model = new RBKit::HeapDataModel(rootItem, this); 
proxyModel = new SortObjectProxyModel(this); 
proxyModel->setSourceModel(model); 
proxyModel->sort(column); 
ui->treeView->setModel(proxyModel); 
2

जवाब देने के लिए धन्यवाद। इस बिंदु पर मुझे वास्तव में उन पंक्तियों का सहारा लेने की परवाह नहीं है जो आलसी लोड किए गए थे (जब एक नोड का विस्तार किया गया था), इसलिए मैं आगे बढ़ गया और sortingEnabled अक्षम कर दिया और अक्षम dynamicSortFilter भी।

rootItem = RBKit::SqlConnectionPool::getInstance()->rootOfSnapshot(snapShotVersion); 
model = new RBKit::HeapDataModel(rootItem, this); 
proxyModel = new SortObjectProxyModel(this); 
proxyModel->setSourceModel(model); 
proxyModel->sort(2, Qt::DescendingOrder); 
proxyModel->setDynamicSortFilter(false); 
ui->treeView->setModel(proxyModel); 

कि अभी भी खाली पंक्तियों के साथ छोड़ देता है:

नए कोड की तरह दिखता है।

+0

क्या आप अपरिवर्तित सामग्री देखते हैं यदि आप अपने मॉडल को पेड़ पर सेट करते हैं तो सीधे प्रॉक्सी मॉडल के बिना देखें? –

+0

हाँ, बिना 'proxyModel' के बीच मैं बिना किसी समस्या के निरर्थक सामग्री को ठीक से देखता हूं! –

+0

बीटीडब्ल्यू - मैंने शीर्ष और निचली पंक्ति अनुक्रमणिका के साथ 'endInsertRows' के अंत में 'डेटा चेंज' ईवेंट उत्सर्जित करने का प्रयास किया है। इससे समस्या ठीक नहीं होती है। इसके बाद मैंने कोशिश की - 'layoutChanged' ईवेंट उत्सर्जित करता है जो समस्या को हल करता है लेकिन यह एप्लिकेशन को यादृच्छिक रूप से क्रैश करता है। –

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