I wrote a bit about "jank" in JUCE

Ahh, true, I totally ignored this. I was under the impression a component’s cachedImage invalidates on any repaint() call. So for example, my CaretComponent calls setVisible on itself, which calls repaint on itself, which calls repaint on the TextEditor, which calls repaint on the Form its in… so all of those components would have their cache invalidated. So, I don’t think it would rescue me from “jank” caused by repaint calls (which are everywhere!).

Actually, maybe like others, I’m generally unclear about the “good” setBufferedToImage use cases.

The docs are a bit murky, but reading the code it seems that cachedImage->paint is only ever called in paintWithinParentContext which is called from paintComponentAndChildren (which recursively goes through the hierarchy top down painting children)

So if I’m understanding correctly, setBufferedToImage would be better named cacheComponentAndChildrenUntilRepaint — the cache is only used when the component’s parent is painting and is calling paintComponentAndChildren (opposite direction of what’s happening with the caret example).

Oooh, this makes sense!