dimanche 30 janvier 2022

With C++ openCV, split video frames into blocks, join back together & output new video

As a very simple test (prior to ultimately performing various transformations on the blocks), I'm trying to split up frames of a video file - initially just into 4 blocks, then stitch back together, before outputting to a new file.

I've written the following code (running on Google Colab). However, it keeps failing, due to errors posted below the code.

I'm new to C++ and OpenCV, so likely a clear & obvious mistake. But, I've been scratching my head over this for hours, with no luck. Any pointers appreciated (pardon the pun).

%%writefile test.cpp

#include<opencv2/opencv.hpp>
#include "opencv2/highgui.hpp"
#include "opencv2/imgproc.hpp"
#include "opencv2/videoio.hpp"
#include <vector>

using namespace std;
using namespace cv;

int main(){

VideoCapture cap;
cap.open("/content/drive/MyDrive/test.mp4");
  int frame_width = static_cast<int>(cap.get(CAP_PROP_FRAME_WIDTH));
  int frame_height = static_cast<int>(cap.get(CAP_PROP_FRAME_HEIGHT));
  Size frame_size(frame_width, frame_height);
  Size sb_size(frame_width/2,frame_height/2);
  int blocks_wide = 2;
  int blocks_high = 2;
  int fps = 20;
  VideoWriter output("/content/drive/MyDrive/output.avi", VideoWriter::fourcc('M', 'J', 'P', 'G'),fps, frame_size);
  Mat frame;
  vector<Mat> small_blocks;
  
for(;;) {
        cap >> frame;
        if (frame.empty()) break;
        for (int y = 0; y < blocks_high; y++) {
          for (int x = 0; x < blocks_wide; x++) {
            small_blocks.push_back(Mat(frame, Rect(x,y,sb_size.width,sb_size.height)).clone());   
      }
    }

  Mat combined(frame_width, frame_height, small_blocks[0].type());
  for(int i = 0; i < small_blocks.size(); i++) {
    for  (int y = 0; y < frame_height; y += sb_size.height)
      {
        for  (int  x = 0; x < frame_width; x += sb_size.width)
        {
          Mat roi = combined(Rect(x,y,sb_size.width,sb_size.height));
          small_blocks[i].copyTo(roi);
        }
      }
  }
    output.write(combined);
}
  cap.release();
    return 0;
}

Here is an example of the errors I've been getting:

    OpenCV Error: Assertion failed (0 <= roi.x && 0 <= roi.width && roi.x + roi.width <= m.cols && 0 <= roi.y && 0 <= roi.height && roi.y + roi.height <= m.rows) in Mat, file /build/opencv-L2vuMj/opencv-3.2.0+dfsg/modules/core/src/matrix.cpp, line 522
terminate called after throwing an instance of 'cv::Exception'
  what():  /build/opencv-L2vuMj/opencv-3.2.0+dfsg/modules/core/src/matrix.cpp:522: error: (-215) 0 <= roi.x && 0 <= roi.width && roi.x + roi.width <= m.cols && 0 <= roi.y && 0 <= roi.height && roi.y + roi.height <= m.rows in function Mat

Aucun commentaire:

Enregistrer un commentaire