2
votes

I'm building a simple application in c++ (32-bits) that uses opencv to grab frames from a rtsp camera.

The function that grabs the camera frames run in a separated thread from the main program.

I've testes this application with a mp4 video, and it works fine. I was able to grab frames and process them. However when I use the rtsp link, although I was able to open a connection with the camera, whenever I tried to read both grab() and read() functions returns False.

First, i thought it was an issue with the rtsp link, but I made a simple Python application to test it, and it worked as well. So it was not the link.

This is the code that I'm using to grab the frames:

#ifndef _IMAGE_BUFFER_H_
#define _IMAGE_BUFFER_H_

#include <opencv2/core.hpp>
#include <opencv2/videoio.hpp>
#include <opencv2/highgui.hpp>

.
.
.

VideoCapture capture_;

string address_;
atomic<bool> keep_alive_;
thread thread_;
int fps_;
mutex mutex_;
list<FramePair> frames_;

int Run()
{

    capture_.open(address_, cv::CAP_ANY);

    if (!capture_.isOpened()) {
        printf("Could not open Camera feed! \n");
        return -1;
    }

    uint64_t period = uint64_t((float(1) / float(fps_)) * float(1000));

    period = period - (period / 20);

    uint64_t t0 = getCurrentTimeInMilli();
    while (keep_alive_) {

        uint64_t difftime = getCurrentTimeInMilli() - t0;
        if (difftime < period) {
            uint64_t sleep_time = period - difftime;
            if (sleep_time < period) {
                std::this_thread::sleep_for(std::chrono::milliseconds(sleep_time));
            }
        }

        t0 = getCurrentTimeInMilli();

        CaptureFrame();
    }

    return 0;
}

void CaptureFrame()
{
    Mat frame;

    bool ret = capture_.read(frame);
    if (!ret) {
        printf("Error in frame reading! \n");
    }

    vector<uint8_t> jpeg;
    cv::imencode(".jpg", frame, jpeg, vector<int>());

    mutex_.lock();

    frames_.push_back(FramePair(getCurrentTimeInMilli(), jpeg));

    if (frames_.size() > FRAME_QUEUE_SIZE)
        frames_.pop_front();

    mutex_.unlock();
}

The OpenCv version that I'm using is 3.4.5.

The link : rtsp://<user>:<pass>@<ip>:<port>/media

I appreciate any help on this matter.


Edit1:

What I have tried:

  • I`ve tried this this, but it didn't work
  • Also Tried with a pre-built opencv 3.4.0 version for 64 bits and still the same

1
Is your Python environment 64 or 32 bit. I'd look with procmon which dlls are/not loaded, (you might have a silent failure). Check maybe also the traffic with Wireshark to see if any communication occures for that protocol.Damien LEFEVRE
I've made tests on both environments, and both worked. Right now i'm recompiling my opencv from source with the same flags from the python opencv. so at least I leave them with the same configuration.MBoaretto

1 Answers

0
votes

Sorry for answering my own question.

But after a lot of trial and error, and reading various SO threads regarding the issue of using cv::VideoCapture in in Windows.

I found the issue,

I was trying to statically link OpenCv in my application, and due to license issues ffmpeg cannot be compiled statically along with the application.

I solved it by, copying the opencv_ffmpegxxx.dll, which can be found in /bin/ . And pasting it in my .exe folder as suggested in here.

There might be some workaround to embed ffmpeg dll in the application as suggested in here, but i haven't tried yet. I hope someone else can benefit from this issue.

Thanks for the help.