2011-11-24 19 views
10

में एक टेक्स्टबॉक्स के साथ एक ट्रीव्यू फ़िल्टर करें मेरे पास एक सी # Winform में एक TreeView है। मैं एक खोज बॉक्स के माध्यम से एक खोज कार्यक्षमता जोड़ने में सक्षम होना चाहूंगा। मूल रूप से उपयोगकर्ता अक्षरों में टाइप करता है (मैं _TextChanged ईवेंट पर अनुमान लगा रहा हूं), मैं केवल उन नोड्स दिखाता हूं जिनमें इनपुट किए गए अक्षरों के साथ बालकोड होते हैं ...एक सी # Winforms ऐप

मेरे ट्री व्यू में कुल 15000 से अधिक के लिए 53 पैरेंट नोड्स शामिल हैं नोड्स तो मुझे थोड़ा सा प्रदर्शन करने की ज़रूरत है। मैं एक csv से मेरी TreeView है कि मैं एक DataTable में लोड और फिर प्रश्नों बनाने जुड़े बच्चे नोड्स के साथ जनक नोड्स पाने के लिए पर ...

अद्यतन

मैं एक विचार है निर्माण। अंतिम उद्देश्य यह है कि जब कोई उपयोगकर्ता किसी बच्चे नोड पर डबलक्लिक करता है तो उसे सूची में जोड़ा जाता है।

मैंने पहली बार इस खोज फ़ंक्शन को एक साधारण सूची दृश्य में कार्यान्वित किया था जहां मैंने अपने डेटा को श्रेणियों में अलग नहीं किया था।

मेरा विचार है कि एक बार उपयोगकर्ता चीजों में टाइप शुरू होता है, मैं अपने ट्री दृश्य को बंद करने और सूची दृश्य के बजाय दिखाने है ...

मैं कोशिश करते हैं और लागू करने और देखते हैं कि यह प्रदर्शन बुद्धिमान देता हूँ .. इस विचार पर किसी भी आलोचकों का स्वागत है।

+0

15000 - पाठ नोड्स बहुत ज्यादा अगर आप एक आधुनिक पीसी पर चल रहे हैं नहीं है। आप पेड़ को भी फ़िल्टर कर सकते हैं, मुख्य बिंदु प्रदर्शन समस्याओं से बचने के लिए एक स्मार्ट रणनीति है। मैं एक का वर्णन करने की कोशिश करूंगा। सूची के साथ समाधान तकनीकी रूप से ठीक है, लेकिन मुझे लगता है कि अपेक्षित और सर्वोत्तम उपयोगकर्ता अनुभव नहीं है। –

+0

क्या आपने अभी तक ब्रूट फोर्स विधि की कोशिश की है? एक अच्छा ओले foreach (ParentNode.ChildNodes में TreeNode नोड)? –

उत्तर

8

आखिरकार मैंने यही किया, यह मेरी आवश्यकताओं के अनुरूप है। मैं पहले अपने TreeView की एक प्रति बना देता हूं और फ़ील्ड ट्री कैश में स्टोर करता हूं। मैं फिर फ़ील्ड को साफ़ करता हूं। मैं फिर कैश के माध्यम से खोज करता हूं और फ़ील्ड में मेरे खोज पैरामीटर वाले किसी भी नोड को जोड़ता हूं। यहां ध्यान दें कि एक बार जब आप खोज लेंगे, तो आपके पास अब दिखाई देने वाले पैरेंट नोड्स नहीं होंगे। आप बस सभी अंत नोड्स प्राप्त करते हैं। मैं ऐसा किया क्योंकि अगर नहीं मैं 2 विकल्प था:

  • सभी माता-पिता बच्चे से मेल खाने वाले युक्त नोड्स का विस्तार करें, लेकिन फिर यह धीमा था और एक माता पिता 50 बच्चों जो नेत्रहीन महान नहीं है हो सकता है।
  • पैरेंट नोड्स का विस्तार न करें, लेकिन फिर आप केवल श्रेणियां प्राप्त करें, न कि उन बच्चों के नोड्स जिन्हें आप खोज रहे हैं।

    void fieldFilterTxtBx_TextChanged(object sender, EventArgs e) 
    { 
        //blocks repainting tree till all objects loaded 
        this.fieldsTree.BeginUpdate(); 
        this.fieldsTree.Nodes.Clear(); 
        if (this.fieldFilterTxtBx.Text != string.Empty) 
        { 
         foreach (TreeNode _parentNode in _fieldsTreeCache.Nodes) 
         { 
          foreach (TreeNode _childNode in _parentNode.Nodes) 
          { 
           if (_childNode.Text.StartsWith(this.fieldFilterTxtBx.Text)) 
           { 
            this.fieldsTree.Nodes.Add((TreeNode)_childNode.Clone()); 
           } 
          } 
         } 
        } 
        else 
        { 
         foreach (TreeNode _node in this._fieldsTreeCache.Nodes) 
         { 
          fieldsTree.Nodes.Add((TreeNode)_node.Clone()); 
         } 
        } 
        //enables redrawing tree after all objects have been added 
        this.fieldsTree.EndUpdate(); 
    } 
    
+0

मैंने इस दृष्टिकोण को भी अपनाया है, मेरे मामले के लिए बहुत अच्छा काम करता है। –

+5

_treeTablesCache कैसे बनाया गया था? – Thunder

+0

अगर मेरे पास एक नोड है जिसमें एकाधिक नोड्स स्तर हैं? –

0
  1. हर नोड TreeView में Expanded और IsVisible गुण है। एक ही समय में दिखाई देने वाली वस्तुओं की संख्या सीमित है (TreeView.VisibleCount)। इस जानकारी के आधार पर आप नाटकीय रूप से जांच के लिए नोड्स की संख्या को कम कर सकते हैं।

  2. नोड और उसके बच्चे नोड्स स्कैन करते समय आप रिकर्सन को रोक सकते हैं क्योंकि आपको पहले से ही एक नाराज नोड के अंदर मिल जाता है, इस प्रकार आप पहले ही जानते हैं कि इसमें कम से कम एक बच्चा है और वैसे भी दिखाई देगा।

  3. असीमित रूप से फ़िल्टरिंग निष्पादित करें। (उदाहरण के लिए new Task() का उपयोग करें) कम से कम वर्ण टाइप किए जाने के बाद पहला कार्य प्रारंभ करें (मान लें 3)। प्रत्येक अगले टाइप किए गए चार को चल रहे कार्य को रद्द करना होगा और नया शुरू करना होगा।

2

यहां एक छोटा सरल उदाहरण (MSDN से कोड के साथ) है TreeView नोड प्रदर्शित करता है को फिल्टर करने की है कि एक बहुत ही सरल तरीका है।

वृक्ष दृश्य में Winforms आप केवल TreeNode जोड़ या निकाल सकते हैं।

नोड्स की खोज अभी भी बेहतर हो सकती है यदि नोड्स को उनके डेटा के साथ एक शब्दकोश (एक अनूठी कुंजी के साथ) में संग्रहीत किया जाता है।

using System.Collections; 
using System.Windows.Forms; 

namespace FilterWinFormsTreeview 
{ 
    // The basic Customer class. 
    public class Customer : System.Object 
    { 
    private string custName = ""; 
    protected ArrayList custOrders = new ArrayList(); 

    public Customer(string customername) { 
     this.custName = customername; 
    } 

    public string CustomerName { 
     get { return this.custName; } 
     set { this.custName = value; } 
    } 

    public ArrayList CustomerOrders { 
     get { return this.custOrders; } 
    } 
    } 

    // End Customer class 

    // The basic customer Order class. 
    public class Order : System.Object 
    { 
    private string ordID = ""; 

    public Order(string orderid) { 
     this.ordID = orderid; 
    } 

    public string OrderID { 
     get { return this.ordID; } 
     set { this.ordID = value; } 
    } 
    } 

    // End Order class 

    public static class TreeViewHelper 
    { 
    // Create a new ArrayList to hold the Customer objects. 
    private static ArrayList customerArray = new ArrayList(); 

    public static void FilterTreeView(TreeView treeView1, string orderText) { 
     if (string.IsNullOrEmpty(orderText)) { 
     FillMyTreeView(treeView1); 
     } else { 
     // Display a wait cursor while the TreeNodes are being created. 
     Cursor.Current = Cursors.WaitCursor; 

     // Suppress repainting the TreeView until all the objects have been created. 
     treeView1.BeginUpdate(); 

     foreach (TreeNode customerNode in treeView1.Nodes) { 
      var customer = customerNode.Tag as Customer; 
      if (customer != null) { 
      customerNode.Nodes.Clear(); 
      // Add a child treenode for each Order object in the current Customer object. 
      foreach (Order order in customer.CustomerOrders) { 
       if (order.OrderID.Contains(orderText)) { 
       var orderNode = new TreeNode(customer.CustomerName + "." + order.OrderID); 
       customerNode.Nodes.Add(orderNode); 
       } 
      } 
      } 
     } 

     // Reset the cursor to the default for all controls. 
     Cursor.Current = Cursors.Default; 

     // Begin repainting the TreeView. 
     treeView1.EndUpdate(); 
     } 
    } 

    public static void FillMyTreeView(TreeView treeView1) { 
     // Add customers to the ArrayList of Customer objects. 
     if (customerArray.Count <= 0) { 
     for (int x = 0; x < 1000; x++) { 
      customerArray.Add(new Customer("Customer" + x.ToString())); 
     } 

     // Add orders to each Customer object in the ArrayList. 
     foreach (Customer customer1 in customerArray) { 
      for (int y = 0; y < 15; y++) { 
      customer1.CustomerOrders.Add(new Order("Order" + y.ToString())); 
      } 
     } 
     } 

     // Display a wait cursor while the TreeNodes are being created. 
     Cursor.Current = Cursors.WaitCursor; 

     // Suppress repainting the TreeView until all the objects have been created. 
     treeView1.BeginUpdate(); 

     // Clear the TreeView each time the method is called. 
     treeView1.Nodes.Clear(); 

     // Add a root TreeNode for each Customer object in the ArrayList. 
     foreach (Customer customer2 in customerArray) { 
     var customerNode = new TreeNode(customer2.CustomerName); 
     customerNode.Tag = customer2; 
     treeView1.Nodes.Add(customerNode); 

     // Add a child treenode for each Order object in the current Customer object. 
     foreach (Order order1 in customer2.CustomerOrders) { 
      var orderNode = new TreeNode(customer2.CustomerName + "." + order1.OrderID); 
      customerNode.Nodes.Add(orderNode); 
     } 
     } 

     // Reset the cursor to the default for all controls. 
     Cursor.Current = Cursors.Default; 

     // Begin repainting the TreeView. 
     treeView1.EndUpdate(); 
    } 
    } 
} 
+0

'एमएसडीएन से कोड के साथ, लिंक कहां है? @ punker76 – wpcoder

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