PIL का उपयोग करके छवि पर पाठ जोड़ें


94

मेरे पास एक एप्लिकेशन है जो एक छवि को लोड करता है और जब उपयोगकर्ता इसे क्लिक करता है, तो इस छवि (उपयोग jquery) के लिए एक पाठ क्षेत्र दिखाई देता है , जहां उपयोगकर्ता छवि पर कुछ पाठ लिख सकता है। जिसे Image पर जोड़ा जाना चाहिए।

इस पर कुछ शोध करने के बाद, मुझे लगा कि PIL(पायथन इमेजिंग लाइब्रेरी) मुझे ऐसा करने में मदद कर सकती है। इसलिए मैंने कुछ उदाहरणों की कोशिश की कि यह कैसे काम करता है और मैं एक छवि पर पाठ लिखने में कामयाब रहा। लेकिन मुझे लगता है कि जब मैं इसका उपयोग कर रहा हूँ Python Shellऔर वेब वातावरण में कुछ अंतर है। मेरा मतलब है कि textarea पर पाठ px में बहुत बड़ा है। जब मैं पिलर को टेक्स्टारिया के रूप में उपयोग करता है, तो मैं उसी आकार के पाठ को कैसे प्राप्त कर सकता हूं?

पाठ मल्टीलाइन है। मैं इसे छवि में भी बहुस्तरीय कैसे बना सकता हूं, उपयोग करके PIL?

क्या पीआईएल का उपयोग करने से बेहतर तरीका है? मुझे पूरी तरह यकीन नहीं है, अगर यह सबसे अच्छा कार्यान्वयन है।

एचटीएमएल:

<img src="images/test.jpg"/>

इसकी छवि संपादित की जा रही है

var count = 0;
$('textarea').autogrow();
$('img').click(function(){
    count = count + 1;
    if (count > 1){
        $(this).after('<textarea />');
        $('textarea').focus();
    }   
});

textarea जोड़ने के लिए jquery। इसके अलावा पाठ क्षेत्र की स्थिति है: पूर्ण और निश्चित आकार।

क्या मुझे इसे एक फॉर्म के अंदर रखना चाहिए ताकि मुझे छवि पर टेक्सारिया के निर्देशांक मिल सकें? मैं छवि पर पाठ लिखना चाहता हूं जब उपयोगकर्ता क्लिक करता है और इसे छवि पर सहेजता है।


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

1
मुझे इसकी आवश्यकता है एक परियोजना के लिए मैं चाहता हूं कि छवि को बचाया जाए। Pil एक इमेज पर टेक्स्ट ड्रा कर सकते हैं ImageDraw का उपयोग करके, यह नहीं जानते कि क्या कोई और तरीका है।
एपोस्टोलोस

यह उपयोगी होगा, यदि आप अपने द्वारा उपयोग किए जा रहे पायथन कोड प्रदान कर सकते हैं?
lalit

अभी तक django में लागू नहीं किया गया है। मैंने यह देखने की कोशिश की कि पीआईएल इंटरैक्टिव पाइथन कंसोल में कैसे काम करता है। देखना चाहते हैं कि यह पहले काम करता है या नहीं और फिर इसे जिंजो में ट्रांसफर कर दें।
एपोस्टोलोस

आपके कोड में $ प्रतीक क्या है?
मुगें

जवाबों:


173

मुझे लगता है कि उपलब्ध ImageFont मॉड्यूल PILपाठ फ़ॉन्ट आकार समस्या को हल करने में सहायक होना चाहिए। बस जाँचें कि फ़ॉन्ट प्रकार और आकार आपके लिए उपयुक्त है और फ़ॉन्ट मान बदलने के लिए निम्न फ़ंक्शन का उपयोग करें।

# font = ImageFont.truetype(<font-file>, <font-size>)
# font-file should be present in provided path.
font = ImageFont.truetype("sans-serif.ttf", 16)

तो आपका कोड कुछ इसी तरह दिखाई देगा:

from PIL import Image
from PIL import ImageFont
from PIL import ImageDraw 

img = Image.open("sample_in.jpg")
draw = ImageDraw.Draw(img)
# font = ImageFont.truetype(<font-file>, <font-size>)
font = ImageFont.truetype("sans-serif.ttf", 16)
# draw.text((x, y),"Sample Text",(r,g,b))
draw.text((0, 0),"Sample Text",(255,255,255),font=font)
img.save('sample-out.jpg')

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

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


1
यह मेरा प्रारंभिक विचार है। तो क्या मुझे अपने फोंट को काम करने के लिए अपने वेबसर्वर में एक विशिष्ट फ़ोल्डर में होना चाहिए? मुझे लगता है कि हाँ। रैपिंग टेक्स्ट? क्या कोई मानक तरीका है या मुझे एक को लागू करना चाहिए?
एपोस्टोलोस

आप अपने वेब सर्वर में कहीं भी फ़ॉन्ट फ़ाइल रख सकते हैं। बस सुनिश्चित करें कि आपके द्वारा प्रदान किया गया पथ सही है।
litit

7
@lalit मैंने एक विंडोज मशीन पर आपके कोड की कोशिश की और मुझे फ़ॉन्ट के लिए एक त्रुटि मिली self.font = core.getfont(file, size, index, encoding) IOError: cannot open resource। मैं फ़ॉन्ट फ़ाइल को पथ कैसे प्रदान कर सकता हूं?
LWZ

3
@LWZ, उपरोक्त कोड को चलाने के लिए, बस यह सुनिश्चित करें कि फ़ॉन्ट फ़ाइल वर्तमान निर्देशिका में है जिसमें आप ऊपर दिए गए कोड को निष्पादित कर रहे हैं। यदि आप इसे अपने प्रोग्राम में उपयोग कर रहे हैं, तो अपनी फ़ाइल के लिए पूर्ण पथ निर्दिष्ट करें जैसे 'C: \ Windows \ Fonts \ sans-serif.ttf'। अन्य चीज़ जो आपको यहाँ सुनिश्चित करने की आवश्यकता है, वह है फ़ाइल को उपयुक्त रीड परमिशन देना।
lalit

3
font = ImageFont.truetype ("./ arial.ttf", 30); draw.textsize (संदेश, फ़ॉन्ट = फ़ॉन्ट);
WeizhongTu

16

आप अपनी परियोजना की जड़ में एक निर्देशिका "फोंट" बना सकते हैं और वहां अपने फोंट (sans_serif.ttf) फ़ाइल डाल सकते हैं। तो आप इस तरह से कुछ बना सकते हैं:

fonts_path = os.path.join(os.path.dirname(os.path.dirname(__file__)), 'fonts')
font = ImageFont.truetype(os.path.join(fonts_path, 'sans_serif.ttf'), 24)

15

और भी कम से कम उदाहरण (चित्र में "हैलो दुनिया!" और काले रंग में डिफ़ॉल्ट फ़ॉन्ट के साथ)

...
from PIL import ImageDraw
...
ImageDraw.Draw(
    image  # Image
).text(
    (0, 0),  # Coordinates
    'Hello world!',  # Text
    (0, 0, 0)  # Color
)

7

सबसे पहले, आपको एक फ़ॉन्ट प्रकार डाउनलोड करना होगा ... उदाहरण के लिए: https://www.wfonts.com/font/microsoft-sans-serif

उसके बाद, पाठ को आकर्षित करने के लिए इस कोड का उपयोग करें:

from PIL import Image
from PIL import ImageFont
from PIL import ImageDraw 
img = Image.open("filename.jpg")
draw = ImageDraw.Draw(img)
font = ImageFont.truetype(r'filepath\..\sans-serif.ttf', 16)
draw.text((0, 0),"Draw This Text",(0,0,0),font=font) # this will draw text with Blackcolor and 16 size

img.save('sample-out.jpg')

5

पिलो के साथ, आप इमेजड्रॉ मॉड्यूल का उपयोग करके एक छवि पर भी आकर्षित कर सकते हैं। आप रेखाएँ, बिंदु, दीर्घवृत्त, आयताकार, आर्क्स, बिटमैप्स, कॉर्ड्स, पिसलीस, बहुभुज, आकृतियाँ और पाठ आकर्षित कर सकते हैं।

from PIL import Image, ImageDraw
blank_image = Image.new('RGBA', (400, 300), 'white')
img_draw = ImageDraw.Draw(blank_image)
img_draw.rectangle((70, 50, 270, 200), outline='red', fill='blue')
img_draw.text((70, 250), 'Hello World', fill='green')
blank_image.save('drawn_image.jpg')

हम नई () पद्धति से एक इमेज ऑब्जेक्ट बनाते हैं। यह एक छवि वस्तु देता है जिसमें कोई भरी हुई छवि नहीं है। फिर हम सहेजने से पहले छवि पर एक आयत और कुछ पाठ जोड़ते हैं।


3

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

In [28]: im = Image.new(mode='RGB',size=(240,240))                                                            
In [29]: font = ImageFont.truetype('arial')
In [30]: draw = ImageDraw.Draw(im)
In [31]: t1 = 'hello world!'
In [32]: t2 = 'hello \nworld!'
In [33]: font.getsize(t1), font.getsize(t2) # the height is the same
Out[33]: ((52, 10), (60, 10)) 
In [35]: draw.textsize(t1, font), draw.textsize(t2, font)  # handles multi-lined text
Out[35]: ((52, 10), (27, 24)) 

-9

छवि फ़ाइल पर पाठ जोड़ने के लिए, बस नीचे दिए गए कोड को कॉपी / पेस्ट करें

<?php
$source = "images/cer.jpg";
$image = imagecreatefromjpeg($source);
$output = "images/certificate".rand(1,200).".jpg";
$white = imagecolorallocate($image,255,255,255);
$black = imagecolorallocate($image,7,94,94);
$font_size = 30;
$rotation = 0;
$origin_x = 250;
$origin_y = 450;
$font = __DIR__ ."/font/Roboto-Italic.ttf";
$text = "Dummy";
$text1 = imagettftext($image,$font_size,$rotation,$origin_x,$origin_y,$black,$font,$text);
     imagejpeg($image,$output,99);
?> <img src="<?php echo $output; ?>"> <a href="<?php echo $output;    ?>" download="<?php echo $output; ?>">Download Certificate</a>
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.