I am trying to generate a image which produces gif like effect by flushing the response continuously to the browser, I am relatively new to django/python and tried with following code testing for both text and image. The generator for text works fine but in case of image only first version of image is being generated.
I tried searching but can't find anything on this. I am confused how to proceed with this or if this is at all possible with django or If the idea is conceptually wrong.
Image Generator :
def refreshx():
from PIL import Image
from PIL import ImageFont
from PIL import ImageDraw
size = (1000,500)
im = Image.new('RGB', size)
draw = ImageDraw.Draw(im)
red = (255,255,255)
text_pos = (10,30)
draw.text(text_pos, str(datetime.datetime.today()), fill=red)
buffer = StringIO.StringIO()
im.save(buffer, 'PNG')
yield buffer.getvalue()
time.sleep(5)
buffers = StringIO.StringIO()
ims = Image.new('RGB', size)
draws = ImageDraw.Draw(ims)
text_poss = (30,80)
draws.text(text_poss, 'dasdasdsa', fill=red)
print 'been there'
ims.save(buffers, 'PNG')
yield buffers.getvalue()
Text Generator :
def testgenerator():
yield str(datetime.datetime.today())
time.sleep(5)
yield str(datetime.datetime.today())
View Function :
def test(request):
#return HttpResponse(testgenerator());
return HttpResponse(refreshx(), mimetype="image/png")
EDIT :
I learned while researching that there's a concept called gifsocket, I'm looking into it..please suggest if anyone has experience with these
Related
i want to take screenshot and crop only the captcha image, im write this code : http://pastebin.com/Hqau6kRD :
elem = driver.find_element_by_css_selector("#imagecpt")
loc = elem.location
size = elem.size
left = loc['x']
top = loc['y']
width = size['width']
height = size['height']
box = (int(left), int(top), int(left+width), int(top+height))
screenshot = driver.get_screenshot_as_png()
img = Image.open(StringIO.StringIO(screenshot))
area = img.crop(box)
area.save('screenshot.png', 'PNG')
the image saved is complete black, where im wrong ?
Yeah. For Python3 it will be like:
...
from io import BytesIO
...
screenshot = driver.get_screenshot_as_base64()
img = Image.open(BytesIO(base64.b64decode(screenshot))
...
I'm assuming you are using the Image module from PIL library.
Try getting the base64 value, decode it and then pass it as a parameter to the open() method.
...
screenshot = driver.get_screenshot_as_base64()
img = Image.open(StringIO.StringIO(base64.b64decode(screenshot))
...
This block of code is to save the image data read from a byte array to the Image img
val = bytearray(message.msg)
size = re.split(r',', message.messageSize)
img = Image.new("L", (int(size[0]), int(size[1])), 0)
pix = img.load()
counter = 0
for y in range(int(size[1])):
for x in range(int(size[0])):
pix[x, y] = val[counter]
counter = counter + 1
Then if I img.save('test.png', 'PNG') and QPixmap('test.png'), it will display the image normally. But if I use the following method, the image would be twisted.(screenshot and image are attached to the hyperlinks below)
self.imgQ = ImageQt(img) # img is PIL Image type
img.save('test.png', 'PNG') # this will be success
pixMap = QtGui.QPixmap.fromImage(self.imgQ)
self.scene1.clear()
self.scene1.addPixmap(pixMap)
self.scene1.update()
self.viewMessage.fitInView(QRectF(0, 0, int(size[0]), int(size[1])), Qt.KeepAspectRatio)
after I implemented the code above, the image is shown twisted. But if I saved the image, the image looks correct.
[update] even if I use the PNG that I saved, it still twisted.
im = Image.open('hehe.png')
I have uploaded the PNG file here.
Here is my code:
import Image
import sys
import json
if __name__ == '__main__':
args = json.loads(sys.argv[1])
srcPath = args.get('srcPath')
image = Image.open(srcPath)
sizes = {}
for variant_name, dimensions in args.get('sizes').items():
if '%' in dimensions:
sizes[variant_name] = image.size
else:
width = int(dimensions.split('x')[0])
height = int(dimensions.split('x')[1])
widthAndHeight = (width, height)
sizes[variant_name] = widthAndHeight
for key, val in sizes.items():
imageName = key + '.' + srcPath.split('.')[1]
convertedImage = image.resize(val, Image.ANTIALIAS)
image.save(imageName)
print 'done'
And I'm calling it with:
python image.py '{"sizes":{"large":"200x150","orig":"100%x100%"},"srcPath":"/Users/bobcobb/Desktop/avocado.png"}'
If the argument 100%x100% is passed in, then I want to resize to the original size, otherwise, I want to resize to the passed in size. So the above code would generate 2 images (one original, the other 200x150).
Right now, it just saves the image as the original size for both. How can I fix this?
Your problem is that the resized image is assigned to convertedImage, but you save the original image (at the new filename).
So changing this line
image.save(imageName)
into
convertedImage.save(imageName)
solves this problem.
I'm learning Python and Django.
An image is provided by the user using forms.ImageField(). Then I have to process it in order to create two different sized images.
When I submit the form, Django returns the following error:
IOError at /add_event/
cannot identify image file
I call the resize function:
def create_event(owner_id, name, image):
image_thumb = image_resizer(image, name, '_t', 'events', 180, 120)
image_medium = image_resizer(image, name, '_m', 'events', 300, 200)
I get en error when image_resizer is called for the second time:
def image_resizer(image, name, size, app_name, length, height):
im = Image.open(image)
if im.mode != "RGB":
im = im.convert("RGB")
im = create_thumb(im, length, height)
posit = str(MEDIA_ROOT)+'/'+app_name+'/'
image_2 = im
image_name = name + size +'.jpg'
imageurl = posit + image_name
image_2.save(imageurl,'JPEG',quality=80)
url_image='/'+app_name+'/'+image_name
return url_image
Versions:
Django 1.3.1
Python 2.7.1
PIL 1.1.7
I'm trying to find the problem, but i don't know what to do. Thank you in advanced!
EDIT
I solved rewriting the function; now it creates the different images in batch:
I call the resize function:
url_array = image_resizer.resize_batch(image, image_name, [[180,120,'_t'], [300,200,'_m']], '/events/')
so:
image_thumb = url_array[0]
image_medium = url_array[1]
and the resize function:
def resize_batch(image, name, size_array, position):
im = Image.open(image)
if im.mode != "RGB":
im = im.convert("RGB")
url_array = []
for size in size_array:
new_im = create_thumb(im, size[0], size[1])
posit = str(MEDIA_ROOT) + position
image_name = name + size[2] +'.jpg'
imageurl = posit + image_name
new_im.save(imageurl,'JPEG',quality=90)
new_url_array = position + image_name
url_array.append(new_url_array)
return url_array
Thanks to all!
As ilvar asks in the comments, what kind of object is image? I'm going to assume for the purposes of this answer that it's the file property of a Django ImageField that comes from a file uploaded by a remote user.
After a file upload, the object you get in the ImageField.file property is a TemporaryUploadedFile object that might represent a file on disk or in memory, depending on how large the upload was. This object behaves much like a normal Python file object, so after you have read it once (to make the first thumbnail), you have reached the end of the file, so that when you try to read it again (to make the second thumbnail), there's nothing there, hence the IOError. To make a second thumbnail, you need to seek back to the beginning of the file. So you could add the line
image.seek(0)
to the start of your image_resizer function.
But this is unnecessary! You have this problem because you are asking the Python Imaging Library to re-read the image for each new thumbnail you want to create. This is a waste of time: better to read the image just once and then create all the thumbnails you want.
I'm guessing that is a TemporaryUploadedFile ... find this with type(image).
import cStringIO
if isinstance(image, TemporaryUploadedFile):
temp_file = open(image.temporary_file_path(), 'rb+')
content = cStringIO.StringIO(temp_file.read())
image = Image.open(content)
temp_file.close()
I'm not 100% sure of the code above ... comes from 2 classes I've got for image manipulation ... but give it a try.
If is a InMemoryUploadedFile your code should work!
i have a problem when converting some Qimages to thumbnails using PIL.
to be used in a list widget , check the image below
where the image should look like :
please note that i use horizontal flow and the text of item is an empty text
one more thing : this only happens when i put more than 1 image
for i in listOfImages:
picture = Image.open(i)
picture.thumbnail((50,50), Image.ANTIALIAS )
qimage = QtGui.QImage(ImageQt.ImageQt(picture))
icon = QtGui.QIcon(QtGui.QPixmap.fromImage(qimage))
item = QtGui.QListWidgetItem(str(path))
item.setIcon(icon)
self.listWidget.addItem(item)
any idea what is going on ? and why images are being pixlated ?.. any better solutions
EDIT : using
pix = QtGui.QPixmap(path)
pix = pix.scaled(50,50,QtCore.Qt.KeepAspectRatio)
icon = QtGui.QIcon(pix)
will be very problematic (needed 10 seconds to run) while the code above needed 1 second.
thanks
from io import BytesIO
qimage = QtGui.QImage()
fp = BytesIO()
picture.save(fp, "BMP")
qimage.loadFromData(fp.getvalue(), "BMP")
icon ...
I had tried ImageQt, but the performance is not good.
I reference http://doloopwhile.hatenablog.com/entry/20100305/1267782841
Because I use python 3.3, cStringIO is replaced by BytesIO
I've not used PIL with PyQt. Have you tried using a QImageReader?
item = QListWidgetItem(image_path)
imageReader = QImageReader()
imageReader.setFileName(image_path)
size = imageReader.size()
size.scale(50, 50, Qt.KeepAspectRatio)
imageReader.setScaledSize(size)
image = imageReader.read()
pix = QPixmap.fromImage(image)
icon = QIcon(pix)
item.setIcon(icon)
self.listWidget.addItem(item)