OpenCV 中的缩放功能 imshow Windows
Zooming functionality in OpenCV imshow in Windows
在 Ubuntu 中,OpenCV 的 imshow 函数有一个 window 可以使用不同的选项,例如放大、缩小、平移 window 等,如下所示:
但是,Windows 中没有这些功能。我有一个特殊情况,我需要在 Windows 上部署我的 OpenCV 代码,用户需要放大图像的某些部分。
有什么方法可以在 Windows 中 access/add 这些功能吗?
见https://gist.github.com/BartG95/1ce8ba1e9c25ec3698d1
似乎是一个较长的过程,因此您可以改用 matplotlib 的 pyplot 函数(使用 Qt)。你需要先涂上这个内衬(详情见Extracting a region from an image using slicing in Python, OpenCV):
import cv2
import matplotlib.pyplot as plt
image = cv2.imread("~\imagedir\image.jpg")
plt_image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
imgplot = plt.imshow(plt_image)
绕路,PIL:
import cv2
from PIL import Image
img = cv2.imread('lena.jpg')
img2 = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
im_pil = Image.fromarray(img2)
im_pil.show()
基本思想是决定每次鼠标滚轮改变的比例。
获取当前比例(v.s.原始图像)和正确的图像显示区域后,就可以得到缩放图像上矩形的位置和长度。
所以你可以在缩放后的图像上绘制这个矩形。
在我的github中,查看class COpenCVWindowExt是如何实现的,更重要的是,这个项目可以缩放in/out和平移图像仅使用 opencv window.
虽然是c++代码,只需要将imshow()和resize()改成python版本就可以了
效果:
部分代码:
void MouseCall (int event, int x, int y, int flag, void* pUserData)
{
COpenCVWindowExt* pParent = (COpenCVWindowExt*)pUserData;
if (event == EVENT_MOUSEWHEEL)
{
if (getMouseWheelDelta (flag) > 0 && pParent->m_iScaleTimes != pParent->m_iMaxScaleTimes)
pParent->m_iScaleTimes++;
else if (getMouseWheelDelta (flag) < 0 && pParent->m_iScaleTimes != pParent->m_iMinScaleTimes)
pParent->m_iScaleTimes--;
if (pParent->m_iScaleTimes == 0)
pParent->m_dCompensationX = pParent->m_dCompensationY = 0;
//Pixel value = mouse offset (v.s. window's left top position)
//But using x, y is not correct in Wheel Event. So, use pre recorded value
x = pParent->m_iMouseX;
y = pParent->m_iMouseY;
double dPixelX = (pParent->m_iHorzScrollBarPos + x + pParent->m_dCompensationX) / pParent->m_dNewScale;
double dPixelY = (pParent->m_iVertScrollBarPos + y + pParent->m_dCompensationY) / pParent->m_dNewScale;
pParent->m_dNewScale = pParent->m_dInitialScale * pow (pParent->m_dScaleRatio, pParent->m_iScaleTimes);
if (pParent->m_iScaleTimes != 0)
{
int iWidth = pParent->m_matSrc.cols;
int iHeight = pParent->m_matSrc.rows;
pParent->m_iHorzScrollBarRange_Max = int (pParent->m_dNewScale * iWidth - pParent->m_dInitialScale * iWidth) - 1;
pParent->m_iVertScrollBarRange_Max = int (pParent->m_dNewScale * iHeight - pParent->m_dInitialScale * iHeight) - 1;
int iBarPosX = pParent->m_iHorzScrollBarPos = int (dPixelX * pParent->m_dNewScale - x + 0.5);
int iBarPosY = pParent->m_iVertScrollBarPos = int (dPixelY * pParent->m_dNewScale - y + 0.5);
pParent->m_dCompensationX = -iBarPosX + (dPixelX * pParent->m_dNewScale - x);
pParent->m_dCompensationY = -iBarPosY + (dPixelY * pParent->m_dNewScale - y);
}
else
{
pParent->m_iHorzScrollBarPos = 0;
pParent->m_iVertScrollBarPos = 0;
}
pParent->RefreshImage ();
}
else if (event == EVENT_MOUSEMOVE)
{
pParent->m_iMouseX = x;
pParent->m_iMouseY = y;
}
}
@mluerig 和许多其他人指出了解决方案 - 在 cmake 中启用 QT。我在这里分享原因和我的解决方案。
原因:
如果你去the highgui module documentation,我们会发现那些功能,比如缩放,像素值只能用Qt GUI实现。
我的解决方案:
如果您像我一样想要使用 CUDA 支持和其他额外模块,则必须在启用 Qt 的情况下从源代码构建。
如果您对 CUDA 不感兴趣,但想学习一些额外的模块,您可以使用:conda install libopencv opencv py-opencv
可选:(--channel conda-forge)
如果您只想要主要模块:conda install -c conda-forge opencv
任何使用 pip 的安装都不适合我。
在 Ubuntu 中,OpenCV 的 imshow 函数有一个 window 可以使用不同的选项,例如放大、缩小、平移 window 等,如下所示:
但是,Windows 中没有这些功能。我有一个特殊情况,我需要在 Windows 上部署我的 OpenCV 代码,用户需要放大图像的某些部分。
有什么方法可以在 Windows 中 access/add 这些功能吗?
见https://gist.github.com/BartG95/1ce8ba1e9c25ec3698d1
似乎是一个较长的过程,因此您可以改用 matplotlib 的 pyplot 函数(使用 Qt)。你需要先涂上这个内衬(详情见Extracting a region from an image using slicing in Python, OpenCV):
import cv2
import matplotlib.pyplot as plt
image = cv2.imread("~\imagedir\image.jpg")
plt_image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
imgplot = plt.imshow(plt_image)
绕路,PIL:
import cv2
from PIL import Image
img = cv2.imread('lena.jpg')
img2 = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
im_pil = Image.fromarray(img2)
im_pil.show()
基本思想是决定每次鼠标滚轮改变的比例。
获取当前比例(v.s.原始图像)和正确的图像显示区域后,就可以得到缩放图像上矩形的位置和长度。
所以你可以在缩放后的图像上绘制这个矩形。
在我的github中,查看class COpenCVWindowExt是如何实现的,更重要的是,这个项目可以缩放in/out和平移图像仅使用 opencv window.
虽然是c++代码,只需要将imshow()和resize()改成python版本就可以了
效果:
部分代码:
void MouseCall (int event, int x, int y, int flag, void* pUserData)
{
COpenCVWindowExt* pParent = (COpenCVWindowExt*)pUserData;
if (event == EVENT_MOUSEWHEEL)
{
if (getMouseWheelDelta (flag) > 0 && pParent->m_iScaleTimes != pParent->m_iMaxScaleTimes)
pParent->m_iScaleTimes++;
else if (getMouseWheelDelta (flag) < 0 && pParent->m_iScaleTimes != pParent->m_iMinScaleTimes)
pParent->m_iScaleTimes--;
if (pParent->m_iScaleTimes == 0)
pParent->m_dCompensationX = pParent->m_dCompensationY = 0;
//Pixel value = mouse offset (v.s. window's left top position)
//But using x, y is not correct in Wheel Event. So, use pre recorded value
x = pParent->m_iMouseX;
y = pParent->m_iMouseY;
double dPixelX = (pParent->m_iHorzScrollBarPos + x + pParent->m_dCompensationX) / pParent->m_dNewScale;
double dPixelY = (pParent->m_iVertScrollBarPos + y + pParent->m_dCompensationY) / pParent->m_dNewScale;
pParent->m_dNewScale = pParent->m_dInitialScale * pow (pParent->m_dScaleRatio, pParent->m_iScaleTimes);
if (pParent->m_iScaleTimes != 0)
{
int iWidth = pParent->m_matSrc.cols;
int iHeight = pParent->m_matSrc.rows;
pParent->m_iHorzScrollBarRange_Max = int (pParent->m_dNewScale * iWidth - pParent->m_dInitialScale * iWidth) - 1;
pParent->m_iVertScrollBarRange_Max = int (pParent->m_dNewScale * iHeight - pParent->m_dInitialScale * iHeight) - 1;
int iBarPosX = pParent->m_iHorzScrollBarPos = int (dPixelX * pParent->m_dNewScale - x + 0.5);
int iBarPosY = pParent->m_iVertScrollBarPos = int (dPixelY * pParent->m_dNewScale - y + 0.5);
pParent->m_dCompensationX = -iBarPosX + (dPixelX * pParent->m_dNewScale - x);
pParent->m_dCompensationY = -iBarPosY + (dPixelY * pParent->m_dNewScale - y);
}
else
{
pParent->m_iHorzScrollBarPos = 0;
pParent->m_iVertScrollBarPos = 0;
}
pParent->RefreshImage ();
}
else if (event == EVENT_MOUSEMOVE)
{
pParent->m_iMouseX = x;
pParent->m_iMouseY = y;
}
}
@mluerig 和许多其他人指出了解决方案 - 在 cmake 中启用 QT。我在这里分享原因和我的解决方案。
原因:
如果你去the highgui module documentation,我们会发现那些功能,比如缩放,像素值只能用Qt GUI实现。
我的解决方案:
如果您像我一样想要使用 CUDA 支持和其他额外模块,则必须在启用 Qt 的情况下从源代码构建。
如果您对 CUDA 不感兴趣,但想学习一些额外的模块,您可以使用:
conda install libopencv opencv py-opencv
可选:(--channel conda-forge)如果您只想要主要模块:
conda install -c conda-forge opencv
任何使用 pip 的安装都不适合我。