简体   繁体   English

如何使用python逐像素显示图像?

[英]How can I show an image plotting pixel by pixel using python?

I have an image of size 1000x1000(Grayscale).我有一张尺寸为 1000x1000(灰度)的图像。 I want to start with a white canvas and plot the pixel value one by one on that canvas and create a video out of it.我想从一个白色的画布开始,在画布上一个一个地绘制像素值,然后用它创建一个视频。 How can we achieve this?我们怎样才能做到这一点?

There are many ways of doing this.有很多方法可以做到这一点。 I'll just show 2 ways:我只会展示两种方式:

  • using OpenCV and its built-in VideoWriter , and使用OpenCV及其内置的VideoWriter ,以及
  • using PIL/Pillow and ffmpeg externally在外部使用PIL/Pillowffmpeg

You can use OpenCV and its VideoWriter like this:您可以像这样使用OpenCV及其VideoWriter

#!/usr/bin/env python3

import numpy as np
import cv2

# Load image in greyscale
im = cv2.imread('paddington.png', cv2.IMREAD_GRAYSCALE)
h, w = im.shape

# Make empty white RGB canvas same size
# I don't think VideoWriter likes greyscale frames, only 3-channel ones
canvas = np.full((h,w,3), 255, np.uint8)

# Create video writer
fourcc = cv2.VideoWriter_fourcc(*'MJPG')
out = cv2.VideoWriter("output.avi", fourcc, 30.0, im.shape)

cnt = 0
for y in range(h):
   for x in range(w):

      # Copy a grey pixel from image to RGB canvas
      canvas[y,x,:] = im[y,x], im[y,x], im[y,x]

      # Write every 100th frame to video to speed it up
      if cnt % 100 ==  0:
         out.write(canvas)

      # Count frames
      cnt += 1
      
out.release()

在此处输入图像描述


Or, if you prefer - or cannot install OpenCV - you can use PIL/Pillow and ffmpeg like this for the same result:或者,如果您喜欢 - 或无法安装OpenCV - 您可以像这样使用PIL/Pillowffmpeg来获得相同的结果:

#!/usr/bin/env python3
################################################################################
# Run like this:
#
# ./plotPaddington2.py | ffmpeg -y -f rawvideo -pix_fmt gray8 -video_size 400x400 -i - -c:v h264 -pix_fmt yuv420p video.mov
################################################################################

from PIL import Image
import sys

# Load image in greyscale
im = Image.open('paddington.png').convert('L')
h, w = im.size

# Make empty white canvas same size
canvas = Image.new('L', im.size, 'white')

cnt = 0
for y in range(h):
   for x in range(w):

      # Copy a pixel from image to canvas
      canvas.putpixel((x,y), im.getpixel((x,y)))

      # Write every 100th frame to video to speed it up
      if cnt % 100 ==  0:
         sys.stdout.buffer.write(canvas.tobytes())

      # Count frames
      cnt += 1

Then you would pipe the output of this script into ffmpeg (with adjusted size parameters to match your video:然后,您将此脚本的输出通过管道传输到ffmpeg (调整大小参数以匹配您的视频:

./plotPaddington2.py | ffmpeg -y -f rawvideo -pix_fmt gray8 -video_size 400x400 -i - -c:v h264 -pix_fmt yuv420p video.mov

Note that if you have an image of 1000x1000 pixels and you create a new frame of video for each and every pixel, you will get 1,000,000 frames of video.请注意,如果您有一个 1000x1000 像素的图像,并且为每个像素创建一个新的视频帧,您将获得 1,000,000 帧视频。 If you show 30 frames/second, which is pretty normal for video, your video will take 9 hours to complete... so I plotted every 100th frame:如果你显示 30 帧/秒,这对于视频来说是很正常的,你的视频将需要 9 个小时才能完成......所以我每 100 帧绘制一次:

hours = WIDTH * HEIGHT / (30 fps * 3600 seconds/hr) = 9.2 hrs

This is pseudocode, but might help:这是伪代码,但可能会有所帮助:

# assume x is 2d array with image of interest
_x = np.zeros_like(x)  # temp emptyarray
for i in range(x.shape[0]):
   for j in range(x.shape[1]):
      _x[i,j] = x[i,j]   # copy data (fill the temp array gradually)
      ...  # pass _x to plotting library

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM