TheImagingSource / ic4-examples

IC4 Example Programs
Apache License 2.0
5 stars 3 forks source link

ImageBuffer copy #15

Closed 5CoJL closed 4 months ago

5CoJL commented 4 months ago

Hello Tim,

I'm sorry for asking tutorials instead of reporting actual issues, but I just can't wrap my head around some methods with only the support of the ic4 documentation.

I'm trying to copy an ImageBuffer for image processing of a single frame. The problem I have is that I can't find how to call CopyFrom() into a new ImageBuffer that I would create. The only way I found to access a buffer is calling FromMemory, but, correct me if I'm wrong, I'm just pointing on the buffer and rewriting its content rewrites the original buffer content as well.

TL;DR: I want to copy the ImageBuffer, but I can't create a ImageBuffer on my own, so I can't call ImageBuffer.CopyFrom(). The only way I can think of to get a reference ImageBuffer and a copy of it to modify is to get another ImageBuffer.FromMemory of a frame I don't care about and to CopyFrom() towards it.

TIS-Tim commented 4 months ago

No worries, every question has the chance to improve the documentation!

To create your own ImageBuffer objects you can create a BufferPool, and then request buffers using GetBuffer on that.

It will even automatically do some smart caching for you to avoid unnecessary memory allocations.

However: In many situations where you think you need a copy, a reference might already suffice. If your program holds a reference to an ImageBuffer object it got from a sink, it owns the buffer and can keep it. Just make sure the sink allocates enough buffers so that streaming can continue, if that is required.

5CoJL commented 4 months ago

Thank you dearly for the support.

I understand I should try to only maintain a single reference. However, calling your ImageBuffer.SaveAsPng() makes a convenient ImageBuffer-to-png-conversion. And if I want to tweak an image directly from the buffer and acquire the png, I figured I would write in the ImageBuffer via its pointer, and call SaveAsPng on the reference.

However, this effectively overwrites my initial ImageBuffer. Hence my query for additional ImageBuffers to make sure I only get a copy of the ImageBuffer I want to rewrite.

Would you recommend a better approach ? First thing that comes to mind is to re-rewrite the reference to its original state, but 1'440'000 pixels over and over again seems a little op-hungry. As I'm using a very few amount of frames, I was aiming for instead being a little more memory-hungry and getting more ImageBuffers on the go.

Edit: I'm using multiple tweaking algorithms, applying each of them to a single frame. Hence my need for multiple ImageBuffers

TIS-Tim commented 4 months ago

If you need the unmodified data and modified data at the same time, there obviously is no way around a copy.

In regards to memory bandwidth, it might be beneficial to perform the copy operation as part of the transformation algorithm (instead of copying first and then modify, writing the same memory again).