2009-12-25 10 views
5

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

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

मैं इसे PDF-EasyPDF पर्ल मॉड्यूल के अतिरिक्त के रूप में कर रहा हूं, लेकिन भाषा वह हिस्सा नहीं है जिसके लिए मुझे सहायता चाहिए।

उत्तर

5

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

विचित्र रूप से पर्याप्त, मैंने कुछ परीक्षण कोड में यह सटीक कार्य करने के लिए कहा था जो मैं काम कर रहा हूं जो पीडीएफ उत्पन्न करता है। यहां बताया गया है मैंने किया:

private void DrawEllipse(PdfGraphics g, double xrad, double yrad) 
    { 
     const double magic = 0.551784; 
     double xmagic = xrad * magic; 
     double ymagic = yrad * magic; 
     g.MoveTo(-xrad, 0); 
     g.CurveTo(-xrad, ymagic, -xmagic, yrad, 0, yrad); 
     g.CurveTo(xmagic, yrad, xrad, ymagic, xrad, 0); 
     g.CurveTo(xrad, -ymagic, xmagic, -yrad, 0, -yrad); 
     g.CurveTo(-xmagic, -yrad, -xrad, -ymagic, -xrad, 0); 
    } 

    private void DrawCircle(PdfGraphics g, double radius) 
    { 
     DrawEllipse(g, radius, radius); 
    } 

मान लें कि PdfGraphics एक वर्ग है कि पीडीएफ आदेशों बाहर निसृत है, इसलिए g.MoveTo(x, y) सामग्री धारा में में "एक्स व म" हो जाएगा। मैंने डॉन Lancaster's fabulous explanation (पीडीएफ, स्वाभाविक रूप से) से अपना गणित और मेरा जादू संख्या लिया। यह मानता है कि सर्कल या अंडाकार उत्पत्ति पर खींचा जाएगा। इसे कहीं और स्थानांतरित करने के लिए, पहले अनुवाद को ट्रांसफॉर्म करें या वांछित मूल में जोड़ने को घटाने के लिए कोड को संशोधित करें। यह कोड लगभग 1/1250 (लगभग .08%) और 1/2500 (लगभग .04%) के औसत की सबसे खराब केस त्रुटि देता है।

4

plinth's answer वही चीज़ है जो मुझे अंत में मिली। बहुत सारे मुश्किल गणित हैं जो एक जादू निरंतर को कम करते हैं और कार्य को चार अलग-अलग बेज़ीर घटता में विभाजित करते हैं। मुझे इसे कच्चे पीडीएफ कमांड में करने की ज़रूरत है, लेकिन प्रक्रिया एक जैसी है।

  • पहले वक्र की शुरुआत में जाएं। यह सर्कल का केंद्र त्रिज्या का केंद्र है जो आपको पसंद है।

  • वक्र के अंत ($x3 और $y3 इस कोड में मान) के अंत में चित्रित करें। सबस्क्रिप्ट बेज़ीयर वक्र नियंत्रण बिंदु लेबल से आती हैं जो अधिकांश लोग उपयोग करते हैं।

  • नियंत्रण बिंदुओं को चित्रित करें। यही वह जगह है जहां $magic मूल्य दिखाता है।

  • जब आप एक सेगमेंट के साथ समाप्त होते हैं, तो अगला करें। केवल अतिरिक्त जोड़ों और घटकों के साथ कार्टेशियन निर्देशांक में अच्छी तरह से काम करने के अलावा चार खंडों के बारे में विशेष विशेष कुछ भी नहीं है।

  • यदि आप भरना चाहते हैं, तो आप जिस पथ को अभी बनाया है उसके अंदर पेंट करने के लिए f के साथ समाप्त करें।

वहाँ

कुछ रिफैक्टरिंग कि मैं कर सकता है, लेकिन रूप में मैं इस के साथ काम कर रहा था बहुत देखने के लिए कि मैं सही कोड के अलग-अलग ब्लॉक होने से संकेत हो रही थी आसान था है।

sub make_magic_circle 
    { 
    my($pdf, # PDF::EasyPDF object 
     $center, 
     $r # radius 
     ) = @_; 

    my($xc, $yc) = $center->xy; 

    my $magic = $r * 0.552; 
    my($x0p, $y0p) = ($xc - $r, $yc); 
    $pdf->{stream} .= "$x0p $y0p m\n"; 

    { 
    ($x0p, $y0p) = ($xc - $r, $yc); 
    my($x1, $y1) = ($x0p,    $y0p + $magic); 
    my($x2, $y2) = ($x0p + $r - $magic, $y0p + $r ); 
    my($x3, $y3) = ($x0p + $r,   $y0p + $r ); 
    $pdf->{stream} .= "$x1 $y1 $x2 $y2 $x3 $y3 c\n"; 
    } 

    { 
    ($x0p, $y0p) = ($xc, $yc + $r); 
    my($x1, $y1) = ($x0p + $magic, $y0p    ); 
    my($x2, $y2) = ($x0p + $r,  $y0p - $r + $magic); 
    my($x3, $y3) = ($x0p + $r,  $y0p - $r   ); 
    $pdf->{stream} .= "$x1 $y1 $x2 $y2 $x3 $y3 c\n"; 
    } 

    { 
    ($x0p, $y0p) = ($xc + $r, $yc); 
    my($x1, $y1) = ($x0p,    $y0p - $magic); 
    my($x2, $y2) = ($x0p - $r + $magic, $y0p - $r ); 
    my($x3, $y3) = ($x0p - $r,   $y0p - $r ); 
    $pdf->{stream} .= "$x1 $y1 $x2 $y2 $x3 $y3 c\n"; 
    } 

    { 
    ($x0p, $y0p) = ($xc, $yc - $r); 
    my($x1, $y1) = ($x0p - $magic,    $y0p); 
    my($x2, $y2) = ($x0p - $r, $y0p + $r - $magic ); 
    my($x3, $y3) = ($x0p - $r,   $y0p + $r ); 
    $pdf->{stream} .= "$x1 $y1 $x2 $y2 $x3 $y3 c\n"; 
    } 

    $pdf->{stream} .= "f\n"; 
    } 
1

इन दोनों अन्य यहाँ जवाब एकदम सही हैं, लेकिन मैं सिर्फ एक ठोस भरा चक्र (इस प्रकार के विशेष मामले के लिए एक छोटा सा हैक जोड़ना चाहते हैं नहीं: इस सबरूटीन मैं PDF::EasyPDF को जोड़ने किया गया है स्ट्रोक)

बस रेखा की मोटाई के साथ शून्य लंबाई वाली रेखा खींचें, लेकिन "लाइन टोपी" को rounded पर सेट करें।

यह स्पष्ट रूप से लंबवृत्त, आर्क, सेगमेंट और कई अन्य संबंधित आकारों के लिए एक अच्छा समाधान नहीं है ... लेकिन यह एक अच्छी चाल है।

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