SDL_LockTexture on MacOS


So one of my visitors pointed out an issue with one of my tutorials on MacOS: Lazy Foo' Productions - Texture Manipulation. He gets a black screen instead of a little stick figure.

The tutorial:

  1. creates a streamable texture
  2. locks it
  3. memcpy’s a png sourced image into the texture
  4. unlocks it
  5. does some other tutorial code
  6. locks the texture once more
  7. iterates through pixels to make the background color transparent (the is the important parts of the tutorial)
  8. unlocks it one last time
  9. renders the texture

My understanding of SDL_LockTexture populates pixels value with a pointer to the texture’s pixels. I can then manipulate the array of data the pixel pointer points to as I need to (ie, memcpy an SDL_Surface’s pixels into it), then SDL_UnlockTexture should upload the pixels addresed in the pointer. After the unlock, that pointer should be just a useless memory address which is why I null it out the tutorial. This works as expected on Windows.

However on MacOS, my visitor said he had to not null out the pointer after the first unlock, skip the second lock, and the second unlock was successful and rendered the image properly.

So is this a bug on MacOS (I replicated it on a ARM Mac Mini right before posting this), or have I been using the lock/unlock texture function incorrectly?

Well, the current documentation for SDL_LockTexture() says:

So I suspect your program has just been getting “lucky” (or unlucky, really) before now.

1 Like

Yeah, you can’t rely on the contents of the pointer from SDL_LockTexture() being pre-populated with anything useful. The reason is that it can be slow to copy the texture data back from the GPU, un-tile it, etc., and most of the time you’re just wanting to copy new data to the texture (such as in the case of video playback, a new frame for an emulator, etc.)

Just iterate over the image data and change the alpha before copying it to the texture. If you really must do it separately, keep your own copy of the image data around.

Also, if you’re going to use SDL_LockTexture() and memcpy() stuff to it, make sure the pitch is what you’re expecting!

1 Like

Welp, I thought the locking functioned like glGetTexImage, and the mention of being read only meant that alterations to the pixel data don’t affect the original texture until unlocked. Looks like I got some refactoring to do and a dozen tutorial to update.

I really wanted to clear the bug backlog by the end of the month :disappointed:

I think you mean write only. I don’t find that ambiguous; if it’s write-only, reading cannot be expected to return anything useful.