OpenCvSharp-鼠标框选截取感兴趣区域(ROI)-附源代码

这篇具有很好参考价值的文章主要介绍了OpenCvSharp-鼠标框选截取感兴趣区域(ROI)-附源代码。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

 前言:ROI(Region of Interest)是图像处理中的一个重要概念,指的是图像中感兴趣的区域。在这个区域内,我们通常希望执行某种特定的操作、获取特定信息,或者进行进一步的分析。ROI 可以是图像的一个矩形、圆形、多边形或者其他各种形状。

目录

一、核心函数:

委托 MouseCallback

设置鼠标回调函数 Cv2.SetMouseCallback()

绘制矩形 Cv2.Rectangle()

提取子区域 SubMat():

二、操作步骤

三、源代码如下


一、核心函数:

委托 MouseCallback
public delegate void MouseCallback(MouseEventTypes @event, int x, int y, MouseEventFlags flags, IntPtr userdata);

 这个委托类型定义了一个鼠标回调函数的格式,回调函数需要接收五个参数

  • @event:鼠标事件类型,它是一个枚举类型MouseEventTypes,表示鼠标的不同操作,例如按下、抬起、移动等。
  • xy:鼠标操作发生的位置坐标,它们表示鼠标在图像窗口上的位置。
  • flags:鼠标事件的附加标志,它是一个枚举类型MouseEventFlags,用于描述鼠标事件的一些附加信息。
  • userData:这是一个指向用户数据的指针,用于传递额外的数据到回调函数中。
设置鼠标回调函数 Cv2.SetMouseCallback()
Cv2.SetMouseCallback(string winname, MouseCallback onMouse, IntPtr userdata = default(IntPtr))
  • winname:图像窗口的名称,在该窗口上监听鼠标事件。
  • onMouse:表示注册的鼠标回调函数,是一个委托类型MouseCallback,当鼠标事件发生时,将调用该函数。
  • userdata:可选参数,传递给回调函数的额外用户数据,默认为default(IntPtr),如果不需要传递额外数据,可以不提供。
绘制矩形 Cv2.Rectangle()
void Cv2.Rectangle(Mat img, Point pt1, Point pt2, Scalar color, int thickness = 1, LineTypes lineType = LineTypes.Link8, int shift = 0);
  • img: 表示源图像(Mat对象),在其中绘制矩形。
  • pt1: 表示矩形左上角的坐标点(Point对象)。
  • pt2: 表示矩形右下角的坐标点(Point对象)。
  • color: 表示绘制矩形的颜色,以BGR格式表示(Scalar对象)。
  • thickness: 可选参数,指定绘制矩形线条的厚度,默认值为1。
  • lineType: 可选参数,指定绘制矩形线条的类型,默认值为LineTypes.Link8,表示8连通线。
  • shift: 可选参数,指定坐标点的小数部分位数,默认值为0。
提取子区域 SubMat():
Mat SubMat(int y, int height, int x, int width);
  • y: 表示子区域的起始行索引。
  • height: 表示子区域的高度。
  • x: 表示子区域的起始列索引。
  • width: 表示子区域的宽度。

SubMat方法返回一个新的Mat对象,该对象表示从原始图像中提取出的子区域。子区域实际上是从原始图像中截取出的矩形区域。

二、操作步骤

 1.创建窗体程序、设置两个按钮

opencvsharp roi,OpenCvSharp入门教程及实战,c#,opencv,计算机视觉

  2.Ctrl C + V

三、源代码如下

using OpenCvSharp;
using OpenCvSharp.Extensions;
using System;
using System.Windows.Forms;
using Point = OpenCvSharp.Point;

namespace 绘制roi
{
    public partial class Form1 : System.Windows.Forms.Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        Mat src;// 存储图像的Mat对象

        //选择图像文件
        private void button1_Click(object sender, EventArgs e)
        {
            OpenFileDialog ofd = new OpenFileDialog();
            ofd.Filter = "Image Files(*.jpg;*.png*;*.bmp*)|*.jpg;*.png*;*.bmp";
            if (ofd.ShowDialog() != DialogResult.OK)
                return;
            string imagePath = ofd.FileName;
            src = Cv2.ImRead(imagePath, ImreadModes.AnyColor);
            Cv2.ImShow("src image", src);
        }


        static Mat tempMat; // 用于临时存储原始图像
        static Point sp = new Point(-1, -1); // 起始点坐标
        static Point ep = new Point(-1, -1); // 终点坐标

        private void button2_Click(object sender, EventArgs e)
        {
            if (src == null)
            {
                MessageBox.Show("请先选择图像文件!", "提示", MessageBoxButtons.OK, MessageBoxIcon.Warning);
                return;
            }

            // 创建鼠标回调函数
            MouseCallback draw = new MouseCallback(DrawRectangle);

          
            // 复制图像
            tempMat = new Mat(src.Size(), src.Type());
            Cv2.CopyTo(src, tempMat);

            // 分两步将Mat对象转换为IntPtr,用于传递给回调函数。
            // 将Mat对象src作为参数传递给Alloc方法,以创建一个GCHandle对象,并将其与srcImage关联起来
            System.Runtime.InteropServices.GCHandle handle = System.Runtime.InteropServices.GCHandle.Alloc(src);

            // 再将GCHandle对象转换为IntPtr,即从GCHandle对象中获取对象所在的内存地址。
            IntPtr ptr = System.Runtime.InteropServices.GCHandle.ToIntPtr(handle);

            // 设置鼠标回调函数,将ptr作为额外的用户数据,通过Cv2.SetMouseCallback方法传递给鼠标回调函数DrawRectangle
            Cv2.SetMouseCallback("src image", draw, ptr);
            Cv2.WaitKey();
        }

        // 鼠标回调函数DrawRectangle,它是一个委托类型MouseCallback的实现
        public static void DrawRectangle(MouseEventTypes @event, int x, int y, MouseEventFlags flags, IntPtr userData)
        {
            // 获取图像数据 从userData指针中获取用户数据,并将其转换为GCHandle对象
            System.Runtime.InteropServices.GCHandle handle = System.Runtime.InteropServices.GCHandle.FromIntPtr(userData);
            Mat src = (Mat)handle.Target;

            // 鼠标左键按下事件
            if (@event == MouseEventTypes.LButtonDown)
            {
                sp.X = x;
                sp.Y = y;
                Console.WriteLine("起点坐标 ({0},{1})", sp.X, sp.Y);
            }
            // 鼠标左键抬起事件
            else if (@event == MouseEventTypes.LButtonUp)
            {
                ep.X = x;
                ep.Y = y;
                Console.WriteLine("终点坐标 ({0},{1})", ep.X, ep.Y);

                // 绘制矩形
                if (ep.X > sp.X && ep.Y > sp.Y)
                {
                    // Cv2.Rectangle方法用于在图像(Mat对象)上绘制矩形 
                    //  Cv2.Rectangle(Mat img, Point pt1, Point pt2, Scalar color, int thickness = 1, LineTypes lineType = LineTypes.Link8, int shift = 0);
                    Cv2.Rectangle(src, sp, ep, new Scalar(0, 0, 255), 2, LineTypes.AntiAlias, 0);

                    // SubMat方法用于从图像(Mat对象)中提取子区域,Mat SubMat(int y, int height, int x, int width);
                    Cv2.ImShow("ROI区域", src.SubMat(sp.Y, ep.Y, sp.X, ep.X));

                    // 显示绘制矩形后的图像
                    Cv2.ImShow("src image", src);

                    // 完成绘制矩形后,sp.X和sp.Y重置为-1。确保下一次绘制矩形时能够正确记录起点坐标
                    sp.X = -1;
                    sp.Y = -1;
                }
            }
            // 鼠标移动事件
            else if (@event == MouseEventTypes.MouseMove && sp.X > 0 && sp.Y > 0)
            {
                ep.X = x;
                ep.Y = y;
                // 绘制矩形并显示临时图像
                if (ep.X > sp.X && ep.Y > sp.Y)
                {
                    // 将临时图像tempMat复制到src中
                    Cv2.CopyTo(tempMat, src);
                    // 在src图像上绘制矩形
                    Cv2.Rectangle(src, sp, ep, new Scalar(0, 0, 255), 2, LineTypes.AntiAlias, 0);
                    Cv2.ImShow("src image", src);
                }
            }
        }
    }
}

结果图:

opencvsharp roi,OpenCvSharp入门教程及实战,c#,opencv,计算机视觉文章来源地址https://www.toymoban.com/news/detail-764147.html

到了这里,关于OpenCvSharp-鼠标框选截取感兴趣区域(ROI)-附源代码的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • OpenCV自学笔记四:感兴趣区域(ROI)、通道操作、获取图像性质

    感兴趣区域(ROI)是指在图像或画面中,我们所关注或感兴趣的特定区域。对于图像处理任务,使用ROI可以提取、操作或分析该区域的特征。 在OpenCV中,可以使用numpy数组的切片操作来定义和提取ROI。以下是一个简单的例子,展示如何使用ROI来提取图像的一部分: 在上述代码

    2024年02月04日
    浏览(29)
  • OpenCV(十四):ROI区域截取

    在OpenCV中,你可以使用Rect对象或cv::Range来截取图像的感兴趣区域(Region of Interest,ROI)。 方法一:使用Rect对象截取图像 Rect_(_Tp _x, _Tp _y, _Tp _width,_Tp _height) Tp:数据类型,C++模板特性,可以用int、double、float等替换。 _x:矩形区域左上角第一个像素的x坐标,也就是第一个像素

    2024年02月10日
    浏览(26)
  • OpenCV截取ROI区域——多种形状(圆形)

    背景:在做一个中国象棋机器人的项目,项目中需要识别象棋棋子上的汉字,计划采用CNN的方式实现这一功能。在制作CNN训练的数据集的时候,需要一个截取象棋中心文字的问题。当我们定位到一个象棋的位置之后,我首先将包裹象棋的一个50*50的矩形取阈截取出来,但是,

    2024年02月16日
    浏览(34)
  • OPENCV C++图像提取,图像处理,roi,阈值分割,连通区域筛选,边缘检测(以箱子边缘框选为例)

    本周有机会接触了一点opnev, 在此做一下记录, 最终以 框选出下图箱子为目的( 图片箱子为相机实拍结果,曝光有点低,会有亿点点暗 ), 本文会拆解步骤并附上图片, 完整的源码在最后.PS: 本文参考了好多大佬分享的理论知识, 在此先感谢大佬的分享~~ 首先是梳理一下流程, 下图是

    2024年02月07日
    浏览(34)
  • OpenCV学习(五)——图像基本操作(访问图像像素值、图像属性、感兴趣区域ROI和图像边框)

    访问像素值并修改 访问图像属性 设置感兴趣区域(ROI) 分割和合并图像 5.1 访问像素值并修改 访问像素值 修改像素值 简单访问每个像素值并修改比较缓慢,一般不使用。 Numpy数组方法 array.item() 和 array.itemset() 被认为更好,但是它们始终返回标量。 更好的像素访问和编辑方

    2024年02月06日
    浏览(35)
  • Baumer工业相机堡盟相机如何使用ROI感兴趣区域功能( PARTIAL SCAN ROI功能的优点和行业应用)(C#)

    Baumer工业相机堡盟相机是一种高性能、高质量的工业相机,可用于各种应用场景,如物体检测、计数和识别、运动分析和图像处理。   Baumer的万兆网相机拥有出色的图像处理性能,可以实时传输高分辨率图像。此外,该相机还具有快速数据传输、低功耗、易于集成以及高度可

    2024年02月05日
    浏览(29)
  • 6. QT环境下使用OPenCV(利用鼠标实现图像的ROI区域选择)

    1. 说明 一张图像显示的内容可能并非所有的都是有用信息,有时需要选定某些区域做出特殊的处理。在OPenCV当中可以在图像上响应鼠标的操作,选取出图像上的特殊区域 — ROI区域。 效果展示: 2. 实现步骤 首先在QtCreator中创建一个新的widget项目,并配置好OPenCV的开发环境,

    2024年02月12日
    浏览(32)
  • 【sgRectSelect】Vue实现拖拽鼠标圈选、划区域、框选组件:矩形区域选中checkbox,并回调相关选中、取消选中的操作

    边框线虚线动画效果请参阅 边框虚线滚动动画特效_虚线滚动效果_你挚爱的强哥的博客-CSDN博客 【代码】边框虚线滚动动画特效。_虚线滚动效果 https://blog.csdn.net/qq_37860634/article/details/130507289   碰撞检测原理请前往  原生JS完成“一对一、一对多”矩形DIV碰撞检测、碰撞检查,

    2024年02月16日
    浏览(35)
  • 【sgRectSelect】自定义组件:Vue实现拖拽鼠标圈选、划区域、框选组件:矩形区域选中checkbox,并回调相关选中、取消选中的操作。

    边框线虚线动画效果请参阅 边框虚线滚动动画特效_虚线滚动效果_你挚爱的强哥的博客-CSDN博客 【代码】边框虚线滚动动画特效。_虚线滚动效果 https://blog.csdn.net/qq_37860634/article/details/130507289   碰撞检测原理请前往  原生JS完成“一对一、一对多”矩形DIV碰撞检测、碰撞检查,

    2024年02月09日
    浏览(61)
  • Opencv 如何获取roi区域

    关于图片处理,经常遇到的一个问题是如何获取roi区域(说白了就是抠图),并对roi区域赋值,比如说赋值成黑色。 首先,关于如何获取roi区域,opencv的Mat类中提供了两种方法。代码如下: 上述两种获取roi的方式是通过重载()运算符实现的,根据上面的描述可以看到通过上面

    2024年02月09日
    浏览(32)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包