2016-01-30 16 views
5

Có cách nào với Python (có thể với OpenCV hoặc PIL) để liên tục lấy khung của tất cả hoặc một phần màn hình, ít nhất là 15 khung hình/giây trở lên không? Tôi đã nhìn thấy nó được thực hiện trong các ngôn ngữ khác, do đó, trong lý thuyết nó nên có thể.Ghi lại dữ liệu video từ màn hình bằng Python

Tôi không cần phải lưu dữ liệu hình ảnh vào tệp. Tôi thực sự chỉ muốn nó xuất ra một mảng chứa dữ liệu RGB thô (như trong một mảng numpy hay cái gì đó) vì tôi sẽ lấy nó và gửi nó đến màn hình LED lớn (có thể sau khi định cỡ lại nó).

+0

http://stackoverflow.com/a/24213099/1832058 – furas

Trả lời

6

Bạn sẽ cần phải sử dụng ImageGrab từ thư viện Pillow (PIL) và chuyển đổi ảnh chụp thành mảng có nhiều mảng. Khi bạn có mảng, bạn có thể làm những gì bạn hài lòng với nó bằng cách sử dụng opencv. Tôi chuyển đổi chụp sang màu xám và sử dụng imshow() như một cuộc biểu tình.

Dưới đây là một mã nhanh chóng để giúp bạn bắt đầu:

from PIL import ImageGrab 
import numpy as np 
import cv2 

img = ImageGrab.grab(bbox=(100,10,400,780)) #bbox specifies specific region (bbox= x,y,width,height *starts top-left) 
img_np = np.array(img) #this is the array obtained from conversion 
frame = cv2.cvtColor(img_np, cv2.COLOR_BGR2GRAY) 
cv2.imshow("test", frame) 
cv2.waitKey(0) 
cv2.destroyAllWindows() 

bạn có thể cắm một mảng đó với tần số bạn hài lòng để giữ chụp khung. Sau đó bạn chỉ giải mã các khung hình. đừng quên để thêm trước khi vòng lặp:

fourcc = cv2.VideoWriter_fourcc(*'XVID') 
vid = cv2.VideoWriter('output.avi', fourcc, 6, (640,480)) 

và bên trong vòng lặp bạn có thể thêm:

vid.write(frame) #the edited frame or the original img_np as you please 

CẬP NHẬT
cuối cùng kết quả nhìn một cái gì đó như thế này (Nếu bạn muốn đạt được một luồng các khung hình được lưu trữ. Lưu trữ dưới dạng video chỉ là minh họa về việc sử dụng opencv trên màn hình được chụp):

from PIL import ImageGrab 
import numpy as np 
import cv2 
while(True): 
    img = ImageGrab.grab(bbox=(100,10,400,780)) #bbox specifies specific region (bbox= x,y,width,height) 
    img_np = np.array(img) 
    frame = cv2.cvtColor(img_np, cv2.COLOR_BGR2GRAY) 
    cv2.imshow("test", frame) 
    cv2.waitKey(0) 
cv2.destroyAllWindows() 

Hy vọng rằng sẽ giúp

+0

Không chắc chắn những gì bạn có nghĩa là bởi: "bạn có thể cắm một mảng đó với tần số Bạn hãy để tiếp tục chụp khung "... mảng ở đâu? Và tôi không cần phải làm đầu ra video ở tất cả ... Có cách nào để xác định nơi trên màn hình để lấy? –

+0

Tôi muốn nói thêm một thời gian để xem luồng của screencaptures. Tôi sẽ chỉnh sửa mã ngay bây giờ. để chỉ định tham số bbox sử dụng vùng cụ thể. Một phút tôi sẽ thực hiện cập nhật – ibininja

+0

Tôi đã thực hiện các thay đổi khác. Hy vọng rằng sẽ giúp – ibininja

13

Có một giải pháp khác với mss cung cấp tốc độ khung hình tốt hơn nhiều. (Thử nghiệm trên một Macbook Pro với hệ điều hành MacOS Sierra)

import numpy as np 
import cv2 
from mss import mss 
from PIL import Image 

mon = {'top': 160, 'left': 160, 'width': 200, 'height': 200} 

sct = mss() 

while 1: 
    sct.get_pixels(mon) 
    img = Image.frombytes('RGB', (sct.width, sct.height), sct.image) 
    cv2.imshow('test', np.array(img)) 
    if cv2.waitKey(25) & 0xFF == ord('q'): 
     cv2.destroyAllWindows() 
     break 
+0

Tôi nhận được ** ValueError: không đủ dữ liệu hình ảnh ** khi sử dụng Image.frombytes – ypicard

+0

với i7 2600k, tôi chỉ nhận được 8fps khi quay màn hình 1440p. – NullVoxPopuli

Các vấn đề liên quan