2013-02-06 34 views
9

का उपयोग करता है, मैं एक WPF मार्कअप एक्सटेंशन क्लास बनाने की कोशिश कर रहा हूं जो मेरे टेक्स्ट अनुवाद वर्ग से अनुवादित पाठ प्रदान करता है। अनुवाद सामग्री बहुत अच्छी काम करती है, लेकिन अनुवादित पाठ को वापस करने के लिए टेक्स्ट कुंजी के साथ एक स्थिर विधि कॉल की आवश्यकता होती है। इस तरह:मार्कअप एक्सटेंशन जो डेटाबाइंडिंग मान

ImportLabel.Text = Translator.Translate("import files"); 
// will be "Dateien importieren" in de or "Import files" in en 

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

ImportLabel.Text = Translator.Translate("import n files", FileCount); 
// will be "Import 7 files" or "Import 1 file" 

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

Translator.Translate("minutes", numberOfMinutes) 
// will be "minute" if it's 1, and "minutes" for anything else 

अब एक WPF में आवेदन, बहुत सारे एक्सएएमएल कोड हैं और इसमें बहुत से शाब्दिक ग्रंथ हैं। नट्स के बिना उन्हें अनुवाद करने में सक्षम होने के लिए, मुझे एक मार्कअप एक्सटेंशन की आवश्यकता है जिसे मैं अपनी टेक्स्ट कुंजी पास कर सकता हूं और वह रनटाइम पर अनुवादित पाठ वापस कर देगा। यह हिस्सा काफी आसान है। MarkupExtension से विरासत में प्राप्त क्लास बनाएं, एक कन्स्ट्रक्टर जोड़ें जो टेक्स्ट कुंजी को तर्क के रूप में स्वीकार करता है, इसे एक निजी फ़ील्ड में संग्रहीत करता है, और इसकी ProvideValue विधि संग्रहीत कुंजी के लिए एक अनुवाद टेक्स्ट लौटा देता है।

मेरी असली समस्या यह है: मैं अपने मार्कअप एक्सटेंशन को इस तरह से गिनती मूल्य कैसे स्वीकार कर सकता हूं कि यह डेटा-बाउंड है और अनुवाद टेक्स्ट तदनुसार अपडेट होगा जब गणना मूल्य बदलता है?

यह इस तरह इस्तेमाल किया जाना चाहिए:

<TextBlock Text="{t:Translate 'import files', {Binding FileCount}}"/> 

जब भी FileCount परिवर्तन के बंधन मूल्य, TextBlock और परिवर्तन को प्रतिबिंबित करने के लिए एक नया पाठ मान प्राप्त करना चाहिए अभी भी एक अच्छा शब्दों प्रदान करते हैं।

मुझे वहां एक समान दिखने वाला समाधान मिला है: http://blogs.microsoft.co.il/blogs/tomershamam/archive/2007/10/30/wpf-localization-on-the-fly-language-selection.aspx लेकिन जितना कठिन मैं इसे पालन करने का प्रयास करता हूं, मैं समझ नहीं पा रहा हूं कि यह क्या करता है या यह क्यों काम करता है। सब कुछ डब्ल्यूपीएफ के अंदर होता है, प्रदान किया गया कोड केवल इसे सही दिशा में धक्का देता है लेकिन यह अस्पष्ट है कि कैसे। मैं कुछ भी उपयोगी करने के लिए इसका अनुकूलन नहीं कर सकता।

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

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

+0

मुझे लगता है कि इस परिदृश्य के लिए 'IValueConverter'' MarkupExtension' से बेहतर काम करेगा –

+0

यह कैसा दिखता है? ''? टाइप करने के लिए थोड़ा पीछे। क्या होगा यदि मैं रनटाइम पर भाषा शब्दकोश बदलने योग्य बनाना चाहता था, तो उसे बाध्यकारी भी चाहिए? – ygoe

उत्तर

15

कभी नहीं, मुझे अंत में पता चला कि संदर्भित कोड कैसे काम करता है और समाधान के साथ आ सकता है। रिकॉर्ड के लिए यहां एक संक्षिप्त स्पष्टीकरण दिया गया है।

<TextBlock Text="{t:Translate 'import files', {Binding FileCount}}"/> 

यह एक वर्ग TranslateExtension, MarkupExtension से विरासत में मिली एक निर्माता दो पैरामीटर, एक स्ट्रिंग और एक बाध्यकारी को स्वीकार करने के साथ, की आवश्यकता है। उदाहरण में दोनों मानों को स्टोर करें। कक्षाएं 'ProvideValue विधि तब बाध्यकारी का उपयोग करती है, इसमें एक कस्टम कनवर्टर इंस्टेंस जोड़ता है और बाध्यकारी से परिणाम देता है। प्रावधान वैल्यू, जो एक बाध्यकारी एक्सप्रेशन उदाहरण आईआईआरसी है।

public class TranslateExtension : MarkupExtension 
{ 
    public TranslateExtension(string key, Binding countBinding) 
    { 
     // Save arguments to properties 
    } 
    public override object ProvideValue(IServiceProvider serviceProvider) 
    { 
     countBinding.Converter = new TranslateConverter(key); 
     return countBinding.ProvideValue(serviceProvider); 
    } 
} 

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

जब भी गणना मूल्य बदलता है (यह बाध्यकारी के माध्यम से आता है), डब्ल्यूपीएफ इसके मूल्य को फिर से अनुरोध करेगा। ऐसा लगता है कि कनवर्टर के माध्यम से बाध्यकारी के स्रोत से, सतह पर जहां यह प्रदर्शित होता है। कनवर्टर का उपयोग करके, हमें बाध्यकारी के बारे में चिंता करने की ज़रूरत नहीं है, क्योंकि कनवर्टर को बाइंडिंग का वर्तमान मान विधि विधि के रूप में मिलता है और कुछ और वापस करने की उम्मीद है। गणना मूल्य (int) में, अनुवादित पाठ (स्ट्रिंग) बाहर। यह मेरा कोड है।

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

यह वही कनवर्टर की तरह लग सकता है:।

class TranslateConverter : IValueConverter 
{ 
    private string key; 
    public TranslateConverter(string key) 
    { 
     this.key = key; 
    } 
    public object Convert(object value, ...) 
    { 
     return Translator.Translate(key, (int) value); 
    } 
} 

जादू है कि। समाधान प्राप्त करने के लिए त्रुटि हैंडलिंग और अधिक सुविधाएं जोड़ें।

+0

यह ** ** ** मूल बाध्यकारी पहले से कनवर्टर होने पर तोड़ देगा। एक बेहतर [समाधान] है (https://stackoverflow.com/a/48090008/332528) – torvin