在透明垫上绘制网格

时间:2015-01-06 21:12:17

标签: java opencv mat

我想在透明背景上创建一个带有网格的垫子,我可以将其放在其他垫子上面。我与透明部分斗争并且在顶部铺设

Mat image = imread("pic.jpg");
Mat grid = new Mat(image.size(), CV_8UC4, new Scalar(0, 0, 0, 0);

for (//times)
    // draw grid with: line(grid, ... )     

grid.copyTo(image);

首先,网格Mat根本不是透明的,它是黑色的。是不是这样构造了标量?

new Scalar(Blue, Green, Red, Alpha)

另外,如何将图像与另一个图像叠加?这只是覆盖。

1 个答案:

答案 0 :(得分:2)

以下是用C ++编写的示例程序,但它在java中应该非常类似:

    cv::Mat input = cv::imread("../inputData/Lenna.png");

    cv::Mat inputBGRA;
    cv::cvtColor(input, inputBGRA, CV_BGR2BGRA);

    cv::Mat gridSolid = cv::Mat(input.size(), inputBGRA.type(), cv::Scalar(0,0,0,0));
    cv::Mat gridMask = cv::Mat(input.size(), CV_8UC1, cv::Scalar(0));

    cv::Mat gridAlpha = cv::Mat(input.size(), inputBGRA.type(), cv::Scalar(0,0,0,0));


    cv::line(gridSolid, cv::Point(0,0), cv::Point(512,512), cv::Scalar(0,255,0,255), 10);
    cv::line(gridSolid, cv::Point(0,512), cv::Point(512,0), cv::Scalar(0,255,0,255), 10);
    cv::line(gridMask, cv::Point(0,0), cv::Point(512,512), cv::Scalar(255), 10);    // single channel
    cv::line(gridMask, cv::Point(0,512), cv::Point(512,0), cv::Scalar(255), 10);    // single channel

    // copy and use the mask. copying eliminates the original values where the mask is set
    cv::Mat outputCopy = inputBGRA.clone();
    gridSolid.copyTo(outputCopy,gridMask);



    // here set the scalar alpha value to less than 255
    // both lines use different alpha values
    cv::line(gridAlpha, cv::Point(0,0), cv::Point(512,512), cv::Scalar(0,255,0,120), 10);
    cv::line(gridAlpha, cv::Point(0,512), cv::Point(512,0), cv::Scalar(0,255,0,180), 10);

    cv::Mat outputWeightSum = inputBGRA.clone();
    //cv::addWeighted(inputBGRA, 0.5, gridAlpha, 0.5, 0, outputWeightSum);

    // manually add weighted sum PER ALPHA VALUE:
    for(int y=0; y<outputWeightSum.rows; ++y)
        for(int x=0; x<outputWeightSum.cols; ++x)
        {
            // the bigger the alpha value, the less of the original image is kept at that pixel
            cv::Vec4b imgPix = outputWeightSum.at<cv::Vec4b>(y,x);
            cv::Vec4b gridPix = gridAlpha.at<cv::Vec4b>(y,x);

            // use alpha channel vor blending
            float blendpart = (float)gridPix[3]/(float)255;

            // set pixel value to blended value
            outputWeightSum.at<cv::Vec4b>(y,x) = blendpart * gridPix + (1.0f-blendpart) * imgPix;
        }

实际上你不需要这个例子中的alpha通道,但是如果你有更复杂的“网格”具有不同的alpha值,那可能会很好。

我得到了这些结果:

  1. 方法:复制:
  2. enter image description here

    1. 方法:与alpha通道混合:
    2. enter image description here