2010-07-26 17 views
9

मेरे पास हमेशा WPF DataGrids के साथ लंबे समय तक लोडिंग समय होता है, और मुझे ऑनलाइन कोई समान रिपोर्ट नहीं मिलती है, इसलिए मुझे संदेह था कि मैं कुछ गलत कर रहा था। अब मुझे यकीन है कि, लेआउट जटिलता को जोड़ने से काफी निष्पादन धीमा हो जाता है। एक बहुत ही सरल लेआउट में, डेटाग्रिड तत्काल पॉप्युलेट करता है, जबकि नीचे दिए गए कोड को निष्पादित करने में लगभग 3 सेकंड लगते हैं।अनुचित WPF डेटाग्रिड लोड हो रहा है समय

निम्नलिखित कोड में, 150 पंक्तियों और 11 कॉलम लोड होने में ~ 3 सेकंड लगते हैं, भले ही प्रत्येक सेल किसी भी संपत्ति से बंधे न हो और ऑटोगनेर कॉलम = गलत हो। (मेरे पास दो कोर, 2.6 गीगाहर्ट्ज प्रोसेसर है जिसमें बहुत सी रैम है)।

<Window x:Class="datagridtest.MainWindow" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    Title="MainWindow" Height="350" Width="525"> 
<Border Background="LightSteelBlue" CornerRadius="10" Margin="10"> 
    <ScrollViewer Margin="10" HorizontalScrollBarVisibility="Auto"> 
     <Grid Margin="10,50,0,0"> 
      <Grid.RowDefinitions> 
       <RowDefinition Height="Auto" /> 
       <RowDefinition Height="auto" /> 
       <RowDefinition Height="auto" /> 

      </Grid.RowDefinitions> 
      <Expander IsExpanded="True" Name="expander1" Grid.Row="0"> 
       <Grid> 
        <DataGrid VirtualizingStackPanel.IsVirtualizing="True" AutoGenerateColumns="false" Name="dg" Height="auto" CanUserReorderColumns="False" CanUserResizeColumns="False" CanUserResizeRows="False" CanUserSortColumns="False"> 
         <DataGrid.Columns> 
          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 



          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 


          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 

          <DataGridTextColumn > 
           <DataGridTextColumn.Header > 
            <TextBlock Width="140" HorizontalAlignment="Center" TextAlignment="Center">untitled<LineBreak/>column</TextBlock> 
           </DataGridTextColumn.Header> 
          </DataGridTextColumn> 



         </DataGrid.Columns> 
         </DataGrid> 
       </Grid> 
      </Expander> 

      <Expander IsExpanded="true" Grid.Row="1"> 
       <Grid> 
        <DataGrid AutoGenerateColumns="True" Height="auto" /> 
       </Grid> 
      </Expander> 

      <Expander IsExpanded="true" Grid.Row="2"> 
       <Grid> 
        <DataGrid AutoGenerateColumns="True" Height="auto" /> 
       </Grid> 
      </Expander> 
      <Button Content="Button" Height="23" HorizontalAlignment="Left" Margin="121,-42,0,0" Name="button1" VerticalAlignment="Top" Width="75" Click="button1_Click_2" /> 
     </Grid> 
    </ScrollViewer> 
</Border> 

using System.Collections.ObjectModel; 

namespace datagridtest 
{ 
/// <summary> 
/// Interaction logic for MainWindow.xaml 
/// </summary> 
public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
     InitializeComponent(); 


    } 

    class row 
    { 
     public string Name { get; set; } 
     public double Age { get; set; } 
    } 



    private void button1_Click_2(object sender, RoutedEventArgs e) 
    { 
     ObservableCollection<row> src = new ObservableCollection<row>(); 

     for (int i = 0; i < 150; i++) 
      src.Add(new row { Name = i.ToString(), Age = i/2 }); 

     dg.ItemsSource = src; 
    } 
} 
} 
+0

क्या आप कुछ नमूना कोड पोस्ट कर सकते हैं जो यह दिखाता है? मुझे नहीं लगता कि डब्ल्यूपीएफ डेटा ग्रिड में बनाया गया है। –

+0

धन्यवाद एलन। मुझे लगता है कि मैं टूलकिट से डेटाग्रिड का उपयोग कर रहा हूं। मैंने कोड जोड़ा, और मूल प्रश्न में नई टिप्पणियां। –

+0

@Alan: यह .NET Framework – Goblin

उत्तर

17

जब डेटा ग्रिड की तरह एक ScrollViewer अंदर एम्बेडेड है समस्या केवल तब होता है:

<ScrollViewer> 
    <Datagrid/> 
</ScrollViewer> 

क्योंकि इस विन्यास का कारण बनता है पूरे डेटा ग्रिड एक ही समय में तैयार हो (आकार के ScrollViewer के सक्षम होने के लिए यह समझ में आता है ग्राहक क्षेत्र सही ढंग से)। संक्षेप में, यह डेटाग्रिड के अंतर्निर्मित वर्चुअलाइजेशन व्यवहार को ओवरराइड करता है, जो अपने स्वयं के स्क्रॉलबार लागू करता है ताकि इसकी सभी सामग्री को लेआउट में एक साथ रखा जाना न पड़े।

दूसरे शब्दों में, स्क्रॉल व्यूअर के अंदर डेटाग्रिड एम्बेड करना शायद ही कभी आवश्यक है क्योंकि डेटाग्रिड की अपनी स्वचालित स्क्रॉलिंग है।

+2

इसके अलावा, कभी भी डेटाग्रिड को किसी भी आयाम में ऑटोसोज़ न दें। यदि आप उन्हें अन्य नियंत्रणों के अंदर ढेर करने की योजना बना रहे हैं, तो अपने मैक्सहेइट प्रॉपर्टी को अपनी स्क्रीन के आकार से छोटे से सेट करना एक अच्छा विचार है, क्योंकि डेटा लेयर बहुत बड़ा होने लगता है जब इसका लेआउट बड़ा होता है। –

+0

+1 लाइफसेवर! मैं अस्थायी रूप से एक स्क्रॉलव्यूयर में डाल दिया और इसके बारे में सब भूल गया .. जब मैंने ग्रिड को अद्यतन पर क्रॉल देखा तो चौंक गया। – Gishu

+0

कमाल। धन्यवाद – jkl

3

जैसा कि आप देख सकते हैं कि सभी पंक्तियों लेआउट के लिहाज से बनाया जा रहा है: जब ItemsSource संपत्ति नीचे एक के रूप में एक लेआउट में सेट है

बोतल गर्दन जगह लेता है? आम तौर पर वर्चुअलाइजेशन को बाधा डालना चाहिए और केवल दृश्य पंक्तियां उत्पन्न करना चाहिए। (इसे कॉलम में से एक में टेम्पलेट के साथ परीक्षण करें और इसे कन्स्ट्रक्टर में गिनें)। एक बग है यदि डब्ल्यूपीएफ डाटाग्रिड की सही चौड़ाई निर्धारित नहीं कर सकता है क्योंकि यह आकार को सबसे बड़ा कॉलम करने की कोशिश करता है - इस प्रकार सभी पंक्तियों को सबसे बड़ी चौड़ाई वाले गणना करने के लिए उत्पन्न करना होता है। (- एक गोदी पैनल के बजाय एक ग्रिड में यह जगह - पिछले एक परीक्षण करने के लिए डॉक किया बाएं या दाएं)

इसके अलावा, कोशिश VirtualizingStackPanel.VirtualizationMode = "पुनर्चक्रण" में इसका इस्तेमाल किया टेम्पलेट्स रीसायकल जाने के लिए।

+0

के संस्करण 4.0 में करता है धन्यवाद गोब्लिन! आप सही रास्ते पर थे कि मेरा डेटाग्रिड एक ही समय में सभी पंक्तियों को उत्पन्न करने की कोशिश कर रहा था। लेकिन यह स्क्रॉलव्यू के अंदर डेटाग्रिड को एम्बेड करने के कारण था। वर्चुअलाइजेशन मुद्दा नहीं था (क्योंकि डेटाग्रिड का आकार स्क्रीन आयामों के लिए बाध्य नहीं किया जा रहा था)। –

4

मैं एक UserControl कि एक डेटा ग्रिड निहित के साथ एक समान समस्या थी जब मैं एक नए रूप पर UserControl रखा कभी कभी, या किसी अन्य UserControl यह इंटरफेस (5 सेकंड?) बंद, जबकि यह डेटा ग्रिड redrew होगा। आकार बदलने के साथ ही।

मैं इसे

RowDefinition ऊंचाई = "ऑटो"

और एक ही प्रदर्शन मुद्दा करने के लिए नीचे नज़र रखी है कि अगर मैं एक StackPanel में UserControl डाल भी हुआ। पहले बताए गए आकार बदलने वाले बग के साथ बहुत कुछ लगता है जब पूरे डेटाग्रिड को encapsulating कंटेनर के आकार की गणना करने के लिए popluated की जरूरत है।

<UserControl x:Class="ExampleUserControl" 
      xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
      mc:Ignorable="d" d:DesignHeight="481" d:DesignWidth="773"> 

    <Grid> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="*" /> <!-- 'AUTO' CAUSES EXTREMELY POOR PERFORMANCE --> 
     </Grid.RowDefinitions> 

     <Grid Grid.Row="0"> <!-- CHANGING TO STACKPANEL CAUSES EXTREMELY POOR PERFORMANCE --> 
      <ContentControl Content="{Binding MyDataGridUserControl}" /> 
     </Grid> 
    </Grid> 

</UserControl> 

मैं सिर्फ पता चला कि स्थापित करने maxHeight = "[जो]" ContentControl के लिए भी एक पिछली टिप्पणी के अनुसार काम करता है। यह स्क्रीन से बड़ा हो सकता है।

+1

इस तथ्य को इंगित करने के लिए धन्यवाद कि जब ऊंचाई "ऑटो" पर सेट हो जाती है तो समस्या उत्पन्न होती है। मेरे जवाब में मैंने स्पष्ट रूप से उस पर जोर नहीं दिया था। हालांकि, मैं यह नहीं कहूंगा कि यह एक बग है, सिर्फ एक डिजाइन मुद्दा है। जब कोई डेटा ग्रिड अपने स्वयं के स्क्रॉलबार और "वर्चुअल" क्लाइंट क्षेत्र को संभालता है, तो कई अनुकूलन संभव होते हैं, लेकिन हम उम्मीद नहीं कर सकते कि इन सभी अनुकूलन प्रभावी हो सकते हैं जब वर्चुअल एरिया को पैरेंट कंट्रोल द्वारा नियंत्रित किया जाता है - या हम कर सकते हैं? वैसे भी, डेटा ग्रिड को एक बहुत ही विशिष्ट उपयोग के लिए डिज़ाइन किया गया प्रतीत होता है :(यह बेकार है क्योंकि इससे हमें कुछ यूआई में स्क्रॉलबार के भीतर स्क्रॉलबार मिलते हैं। –

+0

इस तरह की डब्ल्यूपीएफ को एक सीमा लाती है कि हम वहां अपेक्षा नहीं करेंगे होने के लिए। –

+0

इस उत्तर के लिए धन्यवाद - यह वास्तव में मेरा मुद्दा था। डेटा ग्रिड पंक्ति के लिए ऊंचाई = "ऑटो" को हटाने के बाद मेरे पास एक बड़ा प्रदर्शन वृद्धि हुई थी। –

0

मुझे बाध्य डेटा ग्रिड के साथ एक ही समस्या है, और मुझे लगता है कि पहले लोड में यह तेज़ है लेकिन दूसरे पर और अगला यह धीमा है।तो जब मैं कोड में जोड़ें:

DataGrid.ItemsSource = Nothing 

और फिर

TableAdapter.Fill(Mydataset.MyStoredProcedure,....) 
DataGrid.ItemsSource=Mydataset.MyStoredProcedure 

यह बहुत तेजी से बन गया।

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