2012-02-01 10 views
8

में व्यूस्टेट और नियंत्रण मैंने कुछ दिन पहले व्यूस्टेट के बारे में एक प्रश्न पोस्ट किया था और कुछ परीक्षण चलाने के बाद मैं कुछ निष्कर्ष/परिणामों पर आया हूं। इन परिणामों के आधार पर मेरे पास कुछ प्रश्न हैं कि कोई कैसे कुछ चीजें करेगा।एएसपी.नेट

  1. usercontrolA एक पृष्ठ का OnInit से भरी हुई है, तो उसकी viewstate OnLoad में उपलब्ध हो जाएगा:

    यहाँ है कि मैं भाग गया मेरी परीक्षण के परिणाम हैं। अन्य सभी नियंत्रण जो usercontrolA OnInit से लोड होता है, उनके व्यूस्टेट को उनके OnLoad में तैयार किया जाएगा।

  2. यदि उपयोगकर्ताcontrolA को पृष्ठ के OnLoad से लोड किया गया है, तो उसका व्यूस्टेट OnPreRender में उपलब्ध होगा। अन्य सभी नियंत्रण जो usercontrolA OnLoad से लोड होता है, उनके व्यूस्टेट को उनके OnPreRender में उपलब्ध होगा।
  3. यदि उपयोगकर्ताcontrolA किसी ईवेंट से लोड होता है (उदाहरण: बटन क्लिक करें। OnLoad के बाद ईवेंट आग और OnPreRender से पहले), तो उसका व्यूस्टेट उपलब्ध नहीं होगा। उपयोगकर्ता नियंत्रण लोड के सभी अन्य नियंत्रणों में उनके व्यूस्टेट उपलब्ध नहीं होंगे।

तो एक परिपूर्ण दुनिया में आप हमेशा स्थिति # 1 का उपयोग करके सभी नियंत्रण लोड करेंगे, ताकि उनका व्यूस्टेट उनके OnLoad पर उपलब्ध हो। दुर्भाग्यवश जब आपको किसी बटन से नियंत्रण लोड करने की आवश्यकता होती है या OnLoad से, OnPreRender चरण से पहले अपने व्यूस्टेट को प्राप्त करने के लिए नियंत्रण का कोई तरीका नहीं है?

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

कोई भी सुझाव और/या लिंक की सराहना की जाती है।

उत्तर

3

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

class Default : Page { 
    enum LoadedControl { Textbox, Label, GridView } 

    override OnInit() { 
     if (IsPostback) { 
     var c = Viewstate["LoadedControl"] as LoadedControl; 
     if (c != null) LoadDynamicControl(c); 
     } 
    } 

    void Button_Click() { 
    var c = (LoadedControl)Enum.Parse(typeof(LoadedControl), ddl.SelectedValue); 
    LoadDynamicControl(c); 
    } 

    void LoadDynamicControl(LoadedControl c) { 
    switch (c) { 
     case LoadedControl.Textbox: 
      this.ph.Controls.Add(new Textbox()); 
      break; 
     ... 
    } 

    ViewState["LoadedControl"] = c; 
    } 
} 

थोड़ा और अधिक दिलचस्प बिट, हालांकि, कि अनुसार पकड़ने-अप करने के लिए घटनाओं है - यह वास्तव में कोई फर्क नहीं करना चाहिए। गतिशील रूप से एक नियंत्रण लोड करने के लिए callstack तरह दिखता है:

Control.Controls.Add(Control) 
    Control.AddedControl(Control) 
     Control.LoadViewStateRecursive(object) 
      Control.LoadViewState(object) 

एक उदाहरण के रूप ले रहा है Label, यह LoadViewState ओवरराइड करता है और यह Text संपत्ति सीधे ViewState से है खींचती है। टेक्स्टबॉक्स समान है। तो, मेरे पढ़ने के द्वारा, किसी भी बिंदु पर जोड़ने के लिए ठीक होना चाहिए, और फिर व्यूस्टेट तक पहुंचें। यह मेरे अनुभव के साथ जिव प्रतीत नहीं होता है, हालांकि, आगे की जांच वारंट लगती है।

+0

हाय, यह मेरे मुद्दों में से एक था क्यों मैं व्यूस्टेट का उपयोग करने की कोशिश कर रहा था। मुझे किसी भी तरह से चिह्नित करने की ज़रूरत है कि पिछले पोस्टबैक पर ऑनक्लिक हैंडलर द्वारा लोड होने के बाद मेरे नियंत्रण को अगले पोस्टबैक पर लोड किया जाना चाहिए। मैं उस पृष्ठ से व्यूस्टेट का उपयोग करने के बारे में सोच रहा था जिसमें मूल्य होंगे। मेरे परीक्षणों में ऐसा लगता है कि यह जाने का रास्ता हो सकता है। – BlueChameleon

4

मुझे नहीं लगता कि मैं कुछ भी जोड़ सकता हूं जो इस आलेख को कवर नहीं करता है।

विशेष रूप से लाइफ साइकिल घटनाक्रम अनुभाग पर देखें।

http://msdn.microsoft.com/en-us/library/ie/ms178472.aspx

1

मैं हैरान लेकिन अपने परिणामों के बारे में दिलचस्पी रखता हूँ। जब मैं गतिशील नियंत्रण के साथ काम करता हूं तो मैं उन्हें हमेशा Page_Init में जोड़ता हूं। कुछ और काम नहीं करता है। लेकिन आप सही हैं - यदि आप बटन क्लिक के जवाब में उन्हें जोड़ रहे हैं तो आप इसे कैसे करते हैं।

मुझे मिला एकमात्र तरीका Request.Form("__EVENTTARGET") संग्रह PageInit पर संग्रह कर रहा है। इसमें नियंत्रण की नियंत्रण आईडी शामिल है जिसने पोस्टबैक को ट्रिगर किया है, उदाहरण के लिए बटन क्लिक करें। यह निश्चित रूप से नामकरण कंटेनरों द्वारा योग्यता प्राप्त की जाएगी। एक बार जब आप इस विधि से 'ईवेंट' की पहचान कर लेंगे तो आप अपने इच्छित नियंत्रण जोड़ सकते हैं।

यह निश्चित रूप से थोड़ा सा हैकी है, लेकिन इन चीजों को करने का यही एकमात्र तरीका है। यह वास्तव में कारगर है।

यह दिलचस्प है कि ViewStatePreRender पर उपलब्ध है यदि आप Page_Load पर नियंत्रण जोड़ते हैं। लेकिन जैसा कि उपर्युक्त लिंक आपको मदद करने में बहुत देर हो गया है। नियंत्रण चक्र लोड चक्र के दौरान बहाल किया जाता है। यदि यह वहां नहीं है तो आपका नियंत्रण स्थिति या गतिशील नियंत्रण गायब होने जा रहा है।

+0

मुझे लगता है कि वह व्यूस्टेट उपलब्ध होने और पोस्टबैक के बीच बने रहने के बीच अंतर करने में असफल रहा है। पेजस्टलोड के दौरान पिछले पोस्टबैक से व्यूस्टेट लोड किया गया है, जिसका अर्थ है कि यदि आप किसी पृष्ठ के दौरान नियंत्रण बनाते हैं। लोड हैंडलर, तो इसका व्यूस्टेट स्वचालित रूप से जारी रहेगा। – pseudocoder

0

क्या आपने LoadComplete ईवेंट का उपयोग करने का प्रयास किया था?

इस घटना का उपयोग ऐसे कार्यों के लिए करें जिनके लिए पृष्ठ पर अन्य सभी नियंत्रण लोड हो जाएं।

यहPageLoad और सभी घटनाओं (ButtonClick, आदि) के बाद निकाल दिया जाता है, तो अपने UserControls ButtonClick घटनाओं में लोड किए गए हैं कर रहे हैं, और LoadComplete में अपने ViewState पहले से ही आरंभ नहीं हो जाता।

+0

आपकी प्रतिक्रिया के लिए धन्यवाद लेकिन मुझे यकीन नहीं है कि मैं निम्नलिखित हूं। उपयोगकर्ता नियंत्रकों में से एक को अपने व्यूस्टेट से मूल्य प्राप्त करने की आवश्यकता है। लोडकंपलेट पेज स्तर पर है। – BlueChameleon

+0

यदि आप एक ऐसी घटना चाहते हैं जहां आप जानते हैं कि घटनाओं पर क्लिक किस प्रकार हुआ है, तो लोडकंपलेट पहला है। – Leon