精华内容
下载资源
问答
  • Opencv计算两直线交点

    千次阅读 2017-10-18 10:11:14
    直线交点

    //一个细微的模块,干脆放在这里备忘

    //顺便,喜迎十九大,233


    计算出点1,2形成直线与点3,4形成直线的交点

    如果有无穷多个或者平行,那么返回2和3的中间点


    下面就是简单粗暴的功能函数

    cv::Point 交点(cv::Point 点1, cv::Point 点2, cv::Point 点3, cv::Point 点4) {
    	//计算点1,2形成直线与点3,4形成直线交点
    	//如果平行或有无穷个交点就取点2和3的中间点
    	int x, y;
    	int X1 = 点1.x - 点2.x, Y1 = 点1.y - 点2.y, X2 = 点3.x - 点4.x, Y2 = 点3.y - 点4.y;
    	//(点1.x-x)/(点1.y-y)=X1/Y1
    	//(点1.x-x)Y1=X1(点1.y-y)
    	//X1*y=(Y1*x+X1*点1.y-Y1*点1.x)
    	//X2*y=(Y2*x+X2*点3.y-Y2*点3.x)
    	if (X1*Y2 == X2*Y1)return cv::Point((点2.x+点3.x)/2,(点2.y+点3.y)/2);
    
    	int A = X1*点1.y - Y1*点1.x,B= X2*点3.y - Y2*点3.x;
    	//X1*y=(Y1*x+A)
    	//X2*y=(Y2*x+B)
    	y = (A*Y2 - B*Y1) / (X1*Y2 - X2*Y1);
    	x = (B*X1-A*X2) / (Y1*X2 - Y2*X1);
    	return cv::Point(x, y);
    }

    以及完整测试:


    #include<opencv2/opencv.hpp>
    using namespace cv;
    cv::Point 交点(cv::Point 点1, cv::Point 点2, cv::Point 点3, cv::Point 点4) {
    	//计算点1,2形成直线与点3,4形成直线交点
    	//如果平行或有无穷个交点就取点2和3的中间点
    	int x, y;
    	int X1 = 点1.x - 点2.x, Y1 = 点1.y - 点2.y, X2 = 点3.x - 点4.x, Y2 = 点3.y - 点4.y;
    	//(点1.x-x)/(点1.y-y)=X1/Y1
    	//(点1.x-x)Y1=X1(点1.y-y)
    	//X1*y=(Y1*x+X1*点1.y-Y1*点1.x)
    	//X2*y=(Y2*x+X2*点3.y-Y2*点3.x)
    	if (X1*Y2 == X2*Y1)return cv::Point((点2.x + 点3.x) / 2, (点2.y + 点3.y) / 2);
    
    	int A = X1*点1.y - Y1*点1.x, B = X2*点3.y - Y2*点3.x;
    	//X1*y=(Y1*x+A)
    	//X2*y=(Y2*x+B)
    	y = (A*Y2 - B*Y1) / (X1*Y2 - X2*Y1);
    	x = (B*X1 - A*X2) / (Y1*X2 - Y2*X1);
    	return cv::Point(x, y);
    }
    int  main() {
    	cv::Mat 画布(500, 500, CV_8UC3);
    	画布 = cv::Scalar(255,255,255);
    	cv::Point 点1(200, 100), 点2(100, 50), 点3(400, 50), 点4(100, 380);
    
    	cv::circle(画布, 点1, 5, cv::Scalar(255, 0, 0), -1);
    	cv::circle(画布, 点2, 5, cv::Scalar(255, 0, 0), -1);
    	cv::circle(画布, 点3, 5, cv::Scalar(255, 0, 0), -1);
    	cv::circle(画布, 点4, 5, cv::Scalar(255, 0, 0), -1);
    	line(画布, 点2 - 点1, 3*(点2 + 点1), Scalar(111, 111, 255));
    	line(画布, 点3+2*(点4 - 点3), 点3 -3 * (点4 - 点3), Scalar(111, 111, 255));
    
    	cv::Point 结果 = 交点(点1, 点2, 点3, 点4);
    	cv::circle(画布, 结果, 5, cv::Scalar(0, 255, 0), -1);
    	std::cout << "最终坐标为" << 结果;
    	cv::imshow("计算交点", 画布);
    	cv::waitKey(-1);
    	return 0;
    }


    以后可以叫我老中医……


    展开全文
  • opencv找直线及直线交点

    万次阅读 2017-12-06 17:16:16
    opencv2.4.9 & VS2013环境 问题描述 在图中找出两条直线,并找到两条直线交点位置。 思路: 1) 读图,二值化,简单腐蚀,之后直线在原图中比较明显,所以考虑直接用霍夫变换寻找直线。 2)霍夫直线检测...

    opencv2.4.9 & VS2013环境

    问题描述

    在图中找出两条直线,并找到两条直线交点位置。
    SRC

    思路:

    1) 读图,二值化,简单腐蚀,之后直线在原图中比较明显,所以考虑直接用霍夫变换寻找直线。

    2)霍夫直线检测可能会检测出多条重叠直线,利用上下两部分直线斜率相反筛选一下,选出两条直线。

    3)两条直线求交点,变为解二元一次方程问题。

    4)画出结果

    实现:

    1)调用opencv中的HoughLinesP函数:

    void HoughLinesP( InputArray image, OutputArray lines,double rho, double theta, int threshold,double minLineLength=0, double maxLineGap=0 );

    image为输入图像,要求是8位单通道图像

    lines为输出的直线向量,每条线用4个元素表示,即直线的两个端点的4个坐标值

    rho和theta分别为距离和角度的分辨率

    threshold为阈值,即步骤3中的阈值

    minLineLength为最小直线长度,在步骤5中要用到,即如果小于该值,则不被认为是一条直线

    maxLineGap为最大直线间隙,在步骤4中要用到,即如果有两条线段是在一条直线上,但它们之间因为有间隙,所以被认为是两个线段,如果这个间隙大于该值,则被认为是两条线段,否则是一条。

    2)检测出的直线为Vec4i类型,一共四位数。分别代表直线上的(x1,y1,x2,y2),求出每条直线写了,Ka * kB<0即代表两条直线鞋履相反

    3)利用四个点坐标解方程,返回point2f类型的一个点

    4)利用Line()以及circle()函数画出图像

    代码:

    /*Copyright@hitzym
    Harbin Institute of Technology
    Nov,29, 2017*/
    # include <opencv2/opencv.hpp>  
    # include <iostream>  
    
    using namespace cv;
    using namespace std;
    
    /*函数功能:求两条直线交点*/
    /*输入:两条Vec4i类型直线*/
    /*返回:Point2f类型的点*/
    Point2f getCrossPoint(Vec4i LineA, Vec4i LineB)
    {
        double ka, kb;
        ka = (double)(LineA[3] - LineA[1]) / (double)(LineA[2] - LineA[0]); //求出LineA斜率
        kb = (double)(LineB[3] - LineB[1]) / (double)(LineB[2] - LineB[0]); //求出LineB斜率
    
        Point2f crossPoint;
        crossPoint.x = (ka*LineA[0] - LineA[1] - kb*LineB[0] + LineB[1]) / (ka - kb);
        crossPoint.y = (ka*kb*(LineA[0] - LineB[0]) + ka*LineB[1] - kb*LineA[1]) / (ka - kb);
        return crossPoint;
    }
    
    int main(){
    
        Mat src, grayImg, binImg, result;
        src = imread("./1.jpg");
        //imshow("srcimage", src);
        //waitKey(30);
    
        /*检查图像是否载入*/
        if (src.empty()) {
            printf("Error Loading Image...\n");
            return -1;
        }
    
        /*转为灰度图*/
        if (src.channels() == 3){
            cvtColor(src, grayImg, CV_BGR2GRAY);
        }
        else if (src.channels() == 2){
            grayImg = src.clone();
        }
    
        /*二值化*/
        threshold(grayImg, binImg, 100, 255, THRESH_BINARY);
        //adaptiveThreshold(grayImg, binImg, 255, ADAPTIVE_THRESH_MEAN_C, THRESH_BINARY, 15, -2);
        //imshow("binary image", binImg);
        //waitKey(100);
    
        /*腐蚀*/
        Mat element = getStructuringElement(MORPH_RECT, Size(2, 1));
        Mat erodeImg; 
        erode(binImg, erodeImg, element);
        //imshow("erode", erodeImg);
        //waitKey(100);
    
        /*霍夫直线检测*/
        vector<Vec4i> Lines;
        HoughLinesP(erodeImg, Lines, 1, CV_PI / 360, 200, 100, 10);
        Vec4i LineStand = Lines[0];
        Vec4i LineAnother;
        double ka = (double)(LineStand[1] - LineStand[3]) / (double)(LineStand[0] - LineStand[2]);
        double kb;
        for (int i = 1; i < Lines.size(); i++)
        {
            double ki = (double)(Lines[i][1] - Lines[i][3]) / (double)(Lines[i][0] - Lines[i][2]);
            if (ki*ka < 0)        
            {
                LineAnother = Lines[i];
                kb = ki;
            }
        }
    
        /*画出两条直线*/
        result = src.clone();
        line(result, Point(LineStand[0], LineStand[1]), Point(LineStand[2], LineStand[3]), Scalar(0, 255, 0), 2, 8);
        line(result, Point(LineAnother[0], LineAnother[1]), Point(LineAnother[2], LineAnother[3]), Scalar(0, 0, 255), 2, 8);
        cout << "直线A过点(" << LineStand[0] << "," << LineStand[1] << ")以及点(" << LineStand[2]<<","<<LineStand[3] << ");斜率为:" << ka << endl;
        cout << "直线B过点(" << LineAnother[0] << "," << LineAnother[1] << ")以及点(" << LineAnother[2] << "," << LineAnother[3] << ");斜率为:" << kb << endl;
    
        /*求交点并画点保存,result.jpg存储在工程目录下*/
        Point2f crossPoint;
        crossPoint = getCrossPoint(LineStand, LineAnother);
        circle(result, crossPoint, 6, Scalar(255, 0, 0));
        imwrite("./result.jpg", result);
        cout << "交点坐标为:" << crossPoint << endl;
        cout << "Copyrigth@zym" << endl;
        imshow("result", result);
        waitKey(100);
        system("pause");
    
        return 0;
    }

    运行结果:

    result

    console
    一个很简单的小程序~
    请各位看官多多指教!

    展开全文
  • OpenCV计算两条直线的交点

    千次阅读 2021-07-19 13:44:48
    计算两条直线的交点,算法来源于python用opencv实现直线检测和计算交点,现翻译为C++实现。 bool getCrossPoint( cv::Point2i &out, cv::Point2i p1, cv::Point2i p2, cv::Point2i p3, cv::Point2i p4) ...

     

     为了计算矩形框与直线的交点P1、P2,需要分别计算矩形4条边与直线的交点。

    
    bool
    getCrossPoint(
        std::pair<cv::Point2i, cv::Point2i> &out,
        cv::Rect2i rc, cv::Point2i p1, cv::Point2i p2)
    {
        // LOG(INFO) << "getCrossPoint: begin";
    
        std::vector<cv::Point2i> pts;
    
        cv::Point2i ptt;
        if (getCrossPoint(ptt, p1, p2, 
                cv::Point2i(rc.x, rc.y),
                cv::Point2i(rc.x + rc.width, rc.y)) && 
            (ptt.x >= rc.x && ptt.x < rc.x + rc.width))
        {
            // LOG(INFO) << "getCrossPoint: ptt="  << ptt.x << "," << ptt.y;
            pts.push_back(ptt);
        }
    
        cv::Point2i ptb;
        if (getCrossPoint(ptb, p1, p2, 
            cv::Point2i(rc.x, rc.y + rc.height), 
            cv::Point2i(rc.x + rc.width, rc.y + rc.height)) && 
            (ptb.x >= rc.x && ptb.x < rc.x + rc.width))
        {
            // LOG(INFO) << "getCrossPoint: ptb="  << ptb.x << "," << ptb.y;
            pts.push_back(ptb);
        }
    
        cv::Point2i ptl;
        if (getCrossPoint(ptl, p1, p2, 
                cv::Point2i(rc.x, rc.y),
                cv::Point2i(rc.x, rc.y + rc.height)) && 
            (ptl.y >= rc.y && ptl.y < rc.y + rc.height))
        {
            // LOG(INFO) << "getCrossPoint: ptl="  << ptl.x << "," << ptl.y;
            pts.push_back(ptl);
        }
    
        cv::Point2i ptr;
        if (getCrossPoint(ptr, p1, p2, 
            cv::Point2i(rc.x + rc.width, rc.y), 
            cv::Point2i(rc.x + rc.width, rc.y + rc.height)) &&  
            (ptr.y >= rc.y && ptr.y < rc.y + rc.height))
        {
            // LOG(INFO) << "getCrossPoint: ptr="  << ptr.x << "," << ptr.y;
            pts.push_back(ptr);
        }
    
        // LOG(INFO) << "getCrossPoint:"  << pts.size();
        if (pts.size() >= 2)
        {
            out = std::make_pair(pts.front(), pts.back());
            return true;
        }
    
        return false;
    }
    

    计算两条直线的交点,算法来源于python用opencv实现直线检测和计算交点,现翻译为C++实现。

    
    bool
    getCrossPoint(
        cv::Point2i &out, 
        cv::Point2i p1, cv::Point2i p2, 
        cv::Point2i p3, cv::Point2i p4)
    {
        int x1 = p1.x;
        int y1 = p1.y;
        int x2 = p2.x;
        int y2 = p2.y;
    
        int x3 = p3.x;
        int y3 = p3.y;
        int x4 = p4.x;
        int y4 = p4.y;
    
        double k1, b1;
        bool k1_None = false;
        if (x2 - x1 == 0)
        {
            k1_None = true;
        }
        else
        {
            k1 = (double)(y2 - y1) / (double)(x2 - x1); //求出LineA斜率
            b1 = (double)y1 - (double)x1 * k1;
        }
    
        double k2, b2;
        bool k2_None = false;
        if (x4 - x3 == 0)
        {
            k2_None = true;
            b2 = 0;
        }
        else
        {
            k2 = (double)(y4 - y3) / (double)(x4 - x3); //求出LineB斜率
            b2 = (double)y3 - (double)x3 * k2;
        }
    
        if (k1_None)
        {
            if (!k2_None)
            {
                out.x = x1;
                out.y = k2 * x1 + b2;
                LOG(INFO) << "1 x=" << out.x << ", y=" << out.y;
                return true;
            }
        }
        else if (k2_None)
        {
            out.x = x3;
            out.y = k1 * x3 + b1;
            LOG(INFO) << "2 x=" << out.x << ", y=" << out.y;
            return true;
        }
        else if (k2 != k1)
        {
            out.x = (double)(b2 - b1) / (double)(k1 - k2);
            out.y = k1 * (double)out.x + b1;
            LOG(INFO) << "3 x=" << out.x << ", y=" << out.y;
            return true;
        }
    
        out.x = 0;
        out.y = 0;
        return false;
    }
    

    最后发现OpenCV貌似自带了可以实现此功能的函数:cv::clipLine,后面验证一下。

    
    /** @brief Clips the line against the image rectangle.
    
    The function cv::clipLine calculates a part of the line segment that is entirely within the specified
    rectangle. it returns false if the line segment is completely outside the rectangle. Otherwise,
    it returns true .
    @param imgSize Image size. The image rectangle is Rect(0, 0, imgSize.width, imgSize.height) .
    @param pt1 First line point.
    @param pt2 Second line point.
     */
    CV_EXPORTS bool clipLine(Size imgSize, CV_IN_OUT Point& pt1, CV_IN_OUT Point& pt2);
    
    /** @overload
    @param imgSize Image size. The image rectangle is Rect(0, 0, imgSize.width, imgSize.height) .
    @param pt1 First line point.
    @param pt2 Second line point.
    */
    CV_EXPORTS bool clipLine(Size2l imgSize, CV_IN_OUT Point2l& pt1, CV_IN_OUT Point2l& pt2);
    
    /** @overload
    @param imgRect Image rectangle.
    @param pt1 First line point.
    @param pt2 Second line point.
    */
    CV_EXPORTS_W bool clipLine(Rect imgRect, CV_OUT CV_IN_OUT Point& pt1, CV_OUT CV_IN_OUT Point& pt2);
    

    展开全文
  • opencv 寻找轮廓线与圆的交点 在项目过程中 我遇到了一个问题就是要求一段不规则轮廓线与一个圆的交点,网上查了一些资料,如果轮廓线是规则的话还能算出轮廓线的方程可以方便的解出交点,但是现在轮廓线是不固定的...

    opencv 寻找轮廓线与圆的交点

    在项目过程中 我遇到了一个问题就是要求一段不规则轮廓线与一个圆的交点,网上查了一些资料,如果轮廓线是规则的话还能算出轮廓线的方程可以方便的解出交点,但是现在轮廓线是不固定的不规则的所以无法解析出轮廓线的方程, 那么我只能用最笨的办法,弄两个存放圆和轮廓的掩膜然后做 and 运算,找出数值是1 的店就是我要的交点了。

    程序如下:

    #计算轮廓和圆的交点,返回交点坐标。
    def get_contour_circle_intersection(contour,circle):
        '''
        计算轮廓和圆的交点,返回交点坐标。
        contour:轮廓
        circil:单通道灰度图
        '''
        mask = np.zeros(circle.shape, np.uint8)  # 生成和circle 结构相同的掩膜
        cv2.drawContours(mask, [contour], -1, 255, 1) #画出轮廓
        dst=cv2.bitwise_and(mask,circle)  #轮廓和圆的 与运算
        dst=cv2.dilate(dst, None)         #膨胀获得的点
        res=get_corner(dst)               #获得点的角点坐标
        return res
    
    
    def get_corner(grayimg):
        """角点测试 Demo
            grayimg :为一个灰度图
            返回 res
                角点坐标,1,2是亚像素角点, 3,4是角点
        """
        gray = np.float32(grayimg)
        cornerP = cv2.cornerHarris(gray, 3, 5, 0.04)
        cornerP[cornerP > 0] = 255
    
    
        #cornerP=cv2.dilate(cornerP,None)    #膨胀
        ret, cornerP = cv2.threshold(cornerP, 0.01 * cornerP.max(), 255, 0) #阈值化二值化
        cornerP = np.uint8(cornerP)
        cv2.imshow('cornerP', cornerP)
        # 图像连通域
        ret, labels, stats, centroids = cv2.connectedComponentsWithStats(cornerP) #??????????
        # 迭代停止规则
        criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 100, 0.001)
        corners = cv2.cornerSubPix(gray, np.float32(centroids), (5, 5), (-1, -1), criteria) #计算亚像素角点
        res = np.hstack((centroids[1:], corners[1:])) #列表 在水平方向上平铺
        res = np.int0(res)   #列表取整
        return res

    效果图:

     

    上面角点坐标就是 轮廓和圆的交点坐标。

    展开全文
  • opencv求任意两条直线交点

    千次阅读 2018-07-10 12:59:50
    函数功能:求两条直线交点 求两条直线交点 /*函数功能:求两条直线交点*/ /*输入:两条Vec4i类型直线*/ /*返回:Point2f类型的点*/ Point2f getCrossPoint(Vec4i LineA, Vec4i LineB) { double ka, kb; ka = ...
  • opencv求解两条直线的交点

    千次阅读 2018-12-09 11:46:16
    假设现在有一个点集,需要拟合出最能够表达点集轮廓的几条直线,并求直线之间的交点。 从点集中拟合直线可以采用的方法:随机抽样一致性(RANSAC),霍夫变换(though transform) c++ 程序代码 /** @brief 计算直线...
  • opencv3找直线并求任意两条直线交点

    千次阅读 2018-07-09 20:51:21
    opencv3找直线并求任意两条直线交点,并显示出来,是直线交点,因为我把线段延长了。 求交点函数 /*函数功能:求两条直线交点*/ /*输入:两条Vec4i类型直线*/ /*返回:Point2f类型的点*/ Point2f getCrossPoint...
  • Opencv学习笔记-----求取两条直线的交点坐标

    万次阅读 多人点赞 2016-12-15 12:06:07
    求取二直线交点(基于OpenCv) 理论补充: 两直线是否有交点(或线段齐延长线是否相交)是一个Line-line intersection(Wikipedia)问题 在一个2维平面中有两直线(点到点、(点到点,这两条直线的交点用行列式表示如下:...
  • c++ opencv 计算两条线的交点

    千次阅读 2019-07-09 22:51:34
    La = vertices[0].y - vertices[2].y; Lb = vertices[0].x - vertices[2].x; Lc = vertices[0].x*vertices[2].y - vertices[2].x*vertices[0].y; LLa = vertices[1].y - vertices[3]....
  • 在一张CAD图上需要知道墙角,并且标注出来,设想先检测出两面墙壁,即两条直线,然后计算线的交点即可 解决过程 首先要在python里面opencv库,之后读取图片,然后是直线检测前常规性的转灰度图、高斯模糊、边缘...
  • 原博客是opencv版本,转成opencvsharp非常方便 public static void Main() { Mat mat = new Mat(800, 800, MatType.CV_8UC3); Line2D l1 = new Line2D(100, 100, 100, 700); Line2D l2 = new Line2D...
  • OpenCV中求解两条直线的交点

    千次阅读 2018-08-01 10:51:02
    问题1:给出两组坐标点[x1,y1][x2,y2]确定直线Line1? Line1的方程表示为: ------------(1) 分别带入两组坐标点,因为,,三个参数可以同比例放大缩小的。...因为标题也写出来了在OpenCV环境下...
  • 在“学习OpenCV3"的QQ群众,网友且行且珍惜针对前期博客(https://www.cnblogs.com/jsxyhelu/p/9345590.html)中的内容提出了以下问题: 比如这张图,利用PCA求出了特征向量之后,我想要求解与轮廓的交点,不...
  • OpenCV

    2019-08-14 15:07:00
    OpencvForUnity 插件的文档 :https://enoxsoftware.github.io/OpenCVForUnity/3.0.0/doc/html/annotated.html OpenCVSharp : https://github.com/shimat/opencvsharp OpenCVSharp 文档:...
  •  因为要求两个交点,所以要迭代两次,flag为1是正斜率,flag为0是负斜率,k和b是直线的两个参数,看代码: Point solve_edge_pionts(Ellipse& e, double &k, double &b,int flag) { //初始点 double x = (e....
  • 本期将介绍使用OpenCV用两种不同的方法实现快速查找计算直线/网格线交点坐标。 直线交点计算思路与常用方法 直线交点的计算这里列举几个比较常用的方法: ① 在知道直线方程的前提下(或知道直线上一点和直线角度)...
  • 一、问题   已知两条直线l1(x1,y1,x2,y2)l_1(x_1,y_1,x_2,y_...若相交,计算出两条直线的交点和夹角。 二、分析 1、直线方程 y−y1y2−y1=x−x1x2−x1⇒{ax+by+c=0a=−(y2−y1)b=x2−x1c=(y2−y1)x1−(x2−x1)y1k=−.
  • 已经先处理过原图,利用canny算子边缘检测,如何求出图像中直线交点? (有代码最好- -) 我在网上查询,用hough变换,可是在检测过程中,并不能完全找全每一条边,另外也不是很明白如何求出直线方程,从而求出...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,489
精华内容 995
关键字:

opencv交点