Ví dụ bạn đã cố gắng thích ứng là giao diện python mới cho OpenCV 2.0. Đây có lẽ là nguồn gốc của sự nhầm lẫn giữa tên hàm có tiền tố và không có tiền tố (cv.cvSetData()
so với cv.SetData()
).
OpenCV 2.0 tại tàu với hai bộ bindings python:
- Các "old-style" python wrapper, một gói python với
opencv.{cv,highgui,ml}
module
- Các new interface, một phần mở rộng python C (
cv.pyd
), mà kết thúc tốt đẹp tất cả các OpenCV chức năng (bao gồm các mô hình highgui
và ml
.)
Lý do đằng sau thông báo lỗi là gói SWIG mỗi không xử lý chuyển đổi từ một chuỗi python đến một bộ đệm C cũ. Tuy nhiên, trình bao bọc SWIG đi kèm với mô-đun opencv.adaptors
, được thiết kế để hỗ trợ chuyển đổi từ các hình ảnh numpy
và PIL
sang OpenCV.
Sau đây (thử nghiệm) Mã nên giải quyết vấn đề ban đầu của bạn (chuyển đổi từ PIL để OpenCV), sử dụng giao diện SWIG:
# PIL to OpenCV using the SWIG wrapper
from opencv import cv, adaptors, highgui
import PIL
pil_img = PIL.Image.open(filename)
cv_img = adaptors.PIL2Ipl(pil_img)
highgui.cvNamedWindow("pil2ipl")
highgui.cvShowImage("pil2ipl", cv_img)
Tuy nhiên, điều này không giải quyết được thực tế rằng cv.cvSetData()
chức năng sẽ luôn luôn thất bại (với thực thi trình bao bọc SWIG hiện tại). Sau đó bạn có thể sử dụng các wrapper kiểu mới, cho phép bạn sử dụng cv.SetData()
chức năng như bạn mong chờ:
# PIL to OpenCV using the new wrapper
import cv
import PIL
pil_img = PIL.Image.open(filename)
cv_img = cv.CreateImageHeader(pil_img.size, cv.IPL_DEPTH_8U, 3) # RGB image
cv.SetData(cv_img, pil_img.tostring(), pil_img.size[0]*3)
cv.NamedWindow("pil2ipl")
cv.ShowImage("pil2ipl", cv_img)
Một cách tiếp cận thứ ba sẽ được chuyển giao diện OpenCV python của bạn vào ctypes-based wrapper. Nó đi kèm với các chức năng tiện ích để chuyển đổi dữ liệu rõ ràng giữa ví dụ: python strings và C buffer. Một cái nhìn nhanh chóng trên google code search dường như chỉ ra rằng đây là một phương pháp làm việc.
Liên quan đến tham số thứ ba của hàm cvSetData()
, kích thước của bộ đệm hình ảnh, nhưng bước hình ảnh. Bước là số byte trong một hàng của hình ảnh của bạn, là pixel_depth * number_of_channels * image_width
. Tham số pixel_depth
là kích thước tính theo byte của dữ liệu được liên kết với một kênh. Trong ví dụ của bạn, nó sẽ chỉ đơn giản là chiều rộng hình ảnh (chỉ có một kênh, một byte cho mỗi pixel).
Mã bạn nhập vào ở trên có một cái tên không xác định trong đó (cvSetData), vì vậy nó khó biết liệu bạn có thực sự thử nó hay không. –
@ Jonathan: Tôi không gặp lỗi bạn đã đề cập. cvSetData thực sự là một hàm hợp lệ được xác định trong opencv.cv – Arkady
Trạng thái của câu trả lời là gì? –