2012-11-06 14 views
6

मुझे आश्चर्य है कि क्या कोई व्यक्ति आकार के स्केलट्रांसफॉर्म को लागू करते समय WPF आकार प्रतिपादन के डिफ़ॉल्ट व्यवहार को ओवरराइड करने में कामयाब रहा है। डिफ़ॉल्ट व्यवहार स्ट्रोक समेत पूरे आकार ड्राइंग को बदलता है, लेकिन मैं केवल ज्यामिति को स्केल करना चाहता हूं। कठिनाई यह है कि मेरे आकार अलग-अलग स्तरों पर लागू रेंडर ट्रांसफॉर्म के साथ दृश्य पदानुक्रम में रहते हैं (एक 2 डी दृश्य ग्राफ की तरह - लेकिन एक WPF दृश्य पेड़), यह मैं नहीं बदल सकता (!)। मैंने अलग-अलग स्थानों में पढ़ा है कि रेंडर ट्रांसफॉर्म के लिए ट्रांसफॉर्म को रद्द करने और इसे इसके बजाय ज्यामिति पर रखने के लिए कस्टम आकार बनाना संभव हो सकता है।स्ट्रोक को प्रभावित किए बिना WPF आकार ज्यामिति स्केलिंग

public sealed class MyPath : Shape 
{ 
    // This class has a Data property of type Geometry just like the normal Path class 

    protected override Geometry DefiningGeometry 
    { 
     get 
     { 
      Geometry data = Data; 

      if (data == null) 
      { 
       data = Geometry.Empty; 
      } 

      return data; 
     } 
    } 

    protected override void OnRender(DrawingContext drawingContext) 
    { 
     Transform tr = RenderedGeometry.Transform; 
     Geometry geomToDraw = RenderedGeometry.Clone(); 
     geomToDraw.Transform = new MatrixTransform(tr.Value * tr.Value); 
     Matrix trInv = tr.Value; trInv.Invert(); 
     drawingContext.PushTransform(new MatrixTransform(trInv)); 
     drawingContext.DrawGeometry(Brushes.Transparent, new Pen() { Brush = Brushes.Black, Thickness = 1 }, geomToDraw); 
    } 
} 

के रूप में स्पष्ट रूप से स्पष्ट है, मैं काफी यह करने के लिए नया हूँ और इसके बाद के संस्करण कोड शायद पूरी तरह से में गड़बड़ है: इस समय मैं कुछ इस तरह की है। मैं अंतिम परिणामस्वरूप ज्यामिति परिवर्तन को बदलने के बिना मैट्रिक्स को ज्यामिति में स्थानांतरित करने की कोशिश कर रहा था, इसलिए tr.Value * tr.Value और trInv। लेकिन यह काम नहीं करता है क्योंकि मैं इसे चाहता हूं। मुझे पता है कि इस ट्रांसफर ट्रांसफॉर्म तकनीक सिद्धांत में काम करती है क्योंकि मैंने इसे लगातार ट्रांसफॉर्म के साथ करने की कोशिश की है (ज्यामिति सेट करने के लिए परीक्षण। 4 के साथ स्केल एक्स को ट्रांसफॉर्म करें और 0.25 के साथ स्केल एक्स में ट्रांसफॉर्म को दबाकर ठीक काम किया लेकिन परिणामी आकार ड्राइंग लागू नहीं लग रहा था खिंचाव = भरें, जो मैं भरोसा करता हूं)। तो ऐसा कुछ होना चाहिए जो मैं रेंडर ट्रांसफॉर्म के साथ लापता हूं।

परीक्षण परिदृश्य है कि काम नहीं कर रहा है:

  • मैं एक प्रस्तुत करना पैमाने XAML में scaleX = 4 और scaleY = 1 के साथ बदलना लागू होते हैं।
  • बिल्ट-इन पथ वर्ग पूरे चित्र को स्केल करता है ताकि y दिशा में x दिशा में 4 गुना चौड़ा स्ट्रोक हो।
  • मैं चाहता हूं कि माईपाथ केवल ज्यामिति को स्केल करे, न कि स्ट्रोक। < - यह काम नहीं कर रहा है!
    • क्या होता है: ज्यामिति सही ढंग से स्केल हो जाती है, स्ट्रोक को x दिशा में 4 से बढ़ाया जाता है और y दिशा में 4 से थोड़ा कम होता है। गलत क्या है? मुझे एहसास है कि मुझे पूरी तरह से रेंडरगेमेट्री के साथ काम नहीं करना चाहिए। ट्रांसफॉर्म लेकिन मुझे इसके बजाय क्या उपयोग करना चाहिए? मुझे रेंडर ट्रांसफॉर्म और खिंचाव = आकार पर भरने की आवश्यकता है। मेरे रेंडर ट्रांसफॉर्म पदानुक्रम में तराजू, घूर्णन और अनुवाद का मिश्रण हो सकता है, इसलिए समाधान किसी भी ट्रांसफॉर्म को संभालने के लिए पर्याप्त सामान्य होना चाहिए, न केवल अक्ष-संरेखित स्केलिंग।

नोट: मैं जानता हूँ कि यह बुरा है OnRender में ज्यामिति बनाने के लिए लेकिन मैं इसे समय बिताने यह सफाई से पहले काम करना आरंभ करना चाहते हैं।

Invariant stroke thickness of Path regardless of the scale

समस्या जैसा कि पहले कहा कि मैं ध्यान में रूपांतरण प्रस्तुत करना लेने के लिए की क्या ज़रूरत है और मैं कैसे है कि समाधान के लिए अनुकूल करने के लिए के बारे में सुनिश्चित नहीं कर रहा हूँ:

वैसे, मैं इस पोस्ट को पढ़ने के उनके साथ काम करो।

उत्तर

3

यदि मैं सही ढंग से प्रश्न को समझता हूं तो आप कलम पर रेंडर रूपांतरण के प्रभाव को रद्द करना चाहते हैं लेकिन ज्यामिति पर नहीं।

यह उस आइटम के सापेक्ष नियंत्रण के परिवर्तन को प्राप्त करके पूरा किया जा सकता है, जिससे आप कलम पर प्रभाव को रद्द करने के लिए इसके विपरीत का उपयोग करके परिवर्तन को रद्द करना चाहते हैं। (इसलिए उदाहरण के लिए यदि आपके पास पदानुक्रम पी 1/पी 2/पी 3/यूआरशैप है, और पी 1, पी 2, पी 3 सभी उन पर बदल गए हैं और आप चाहते हैं कि वे सभी आपकी कलम को प्रभावित न करें, तो आपको पी 1 रिश्तेदार के परिवर्तन को प्राप्त करने की आवश्यकता होगी UrShape करने के लिए)।फिर आप ट्रांसफॉर्म को केवल अपने आकार में पुनः लागू कर सकते हैं।

var brush = new SolidColorBrush(Colors.Red); 
var pen = new Pen(brush, 5); 
//Instead of the direct parent you could walk up the visual tree to the root from where you want to cancel the transform 

var rootTransform = (MatrixTransform)this.TransformToAncestor((Visual)this.Parent); 

var inverserRootTransform = (MatrixTransform)rootTransform.Inverse; 

//We cancel out the transformation from the parent 
drawingContext.PushTransform(inverserRootTransform); 

var renderGeometry = this.Geometry.Clone(); 
// We apply the parent transform to the shape only, and group it with the original transform that was present on the shape 
// we do this to honor any transformation that was set on the shape. 
renderGeometry.Transform = new TransformGroup() 
{ 
    Children = 
    { 
     rootTransform, 
     this.Geometry.Transform 
    } 
}; 

//We draw the shape, the pen size will have the correct size since we canceled out the transform from the parent 
// but the shape now has the transformation directly on it. 
drawingContext.DrawGeometry(brush, pen, renderGeometry); 
drawingContext.Pop(); 
संबंधित मुद्दे

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