opencv / opencv

Open Source Computer Vision Library
https://opencv.org
Apache License 2.0
75.95k stars 55.62k forks source link

highgui: wayland: imshow() doesn't create window automatically if no namedWindow() #25497

Closed Kumataro closed 2 weeks ago

Kumataro commented 2 weeks ago

System Information

OpenCV version: 4.x branch ( https://github.com/opencv/opencv/commit/2cd330486ec4597eab49c1575fc4a6603f205a6a ) Operating System / Platform: Ubuntu 24.04 Compiler & compiler version: GCC 13.2

Detailed description

We can use imshow() with window which is not created by namedWindow().

https://docs.opencv.org/4.x/d7/dfc/group__highgui.html#ga453d42fe4cb60e5723281a89973ee563

If the window was not created before this function, it is assumed creating a window with cv::WINDOW_AUTOSIZE.

It works well with GTK3 highgui-backed. However it doesn't work well with Wayland highgui-backend.

Steps to reproduce

opencv-log.png is copied from opencv/docs folder.

// g++ main.cpp -o a.out -I /usr/local/include/opencv4 -lopencv_core -lopencv_highgui -lopencv_imgcodecs
#include <opencv2/core.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/imgcodecs.hpp>
#include <iostream>
#include <string>

int main(void)
{
  std::cout << "cv::currentUIFramework() returns " << cv::currentUIFramework() << std::endl; 

  cv::Mat src;
  src = cv::imread("opencv-logo.png");

  // cv::namedWindow("src");

  int key = 0;
  do
  {
      cv::imshow("src", src );
      key = cv::waitKey(50);
  } while( key != 'q' );
  return 0;
}

Issue submission checklist

Kumataro commented 2 weeks ago

While this was happening, I noticed that the CPU usage was 100%.

However, even if I called namedWindow() in advance and the image was displayed correctly, the CPU usage was 100%.

I also created an additional patch to reduce CPU usage, but this issue was not resolved. For the above reasons, CPU usage does not seem to be the cause.

Kumataro commented 2 weeks ago

https://github.com/opencv/opencv/blob/2a2ff5525720d110c9c462cd46e0e0655c7fb0fa/modules/highgui/src/window_wayland.cpp#L2462-L2473

To reuse the result of getInstance() repeatedly looks like better efficient implementation. However, it defined as static shared_ptr member variable in CvWlCore. If it reaches out of scope, cv_wl_core::~cv_wl_core() is called and all windows will be destroyed.

https://github.com/opencv/opencv/blob/2a2ff5525720d110c9c462cd46e0e0655c7fb0fa/modules/highgui/src/window_wayland.cpp#L2289-L2292