alandefreitas / matplotplusplus

Matplot++: A C++ Graphics Library for Data Visualization 📊🗾
https://alandefreitas.github.io/matplotplusplus/
MIT License
4.2k stars 323 forks source link

Plotting 2D matrix with image() function takes 30 minutes #104

Open JeffR1992 opened 3 years ago

JeffR1992 commented 3 years ago

Bug category

Describe the bug I'm trying to plot a 2D grid using the matplot::image() function, but for reasons unbeknownst to me, it literally takes 30 minutes to produce the expected output. I have a std::vector<std::vector<int8_t>> called occupancy_grid_map that has 4000 rows and 4000 cols, and plot it using the following code inside a larger function:

matplot::image(occupancy_grid_map);
matplot::show();

When the above code runs, it initially produces a blank/white plot window. However, after 30 minutes, this blank plot window is finally replaced by the expected 2D image plot. Looking at the processes that run during the 30 minute waiting period, I see that gnuplot runs at 100% throughout this time, so it seems that this might be where the problem could lie (I have gnuplot 5.2 patchlevel 2).

If you'd like me to do some more experiments I'd be more than happy to, since I'm very excited about this library and would hate to be unable to use it due to performance issues like this.

Platform

Environment Details:

alandefreitas commented 3 years ago

Hi @JeffR1992,

Thanks for reporting the issue. The gnuplot pipe is indeed very slow for images but I didn't expect it too be that slow. The image we use in the examples takes me a few seconds to plot 1024 1024 pixels. I would expect 4000 4000 pixels to take about 15 times more but not 30 minutes.

For now, the only solution I can think of is to reduce the image according to the figure size. In the long run, I'm currently working on the opengl backend and images have been working almost instantaneously there (like a game with a single texture). OpenGL even creates smaller versions of the images/textures (minimaps) to fit smaller plots if this can increase performance. Not to mention the whole thing is happening on the GPU. But this is not ready for production.

It's still going to take me a few months to finish this. We could adjust the image object to automatically reduce images larger than the figure, but that would be just one more gnuplot workaround (for instance, it wouldn't be able to resize the image again if the user resized the window) in a list of many.

Using a gnuplot pipe sounded like a obvious idea at first but it seems like it's not designed for plots with many variants. I had no idea it would later require so many workarounds and there would be so many inconsistencies from one version to the other.