xpenguins cont'd - repainting a window after penguins walk on it, and when penguins overlap.
Hi all, After a few days' break I've returned to modifying the xpenguins source to run in a window of my choosing (e.g. terminal). I've finally (partially) resolved the problem of restoring the background behind the penguins (so they don't leave trails where they've walked over icons and such) with as little flickering as possible. I ended up keeping a penguin-bounding-box-sized pixmap of the original background behind the penguin, and selectively sending a clear/expose event to the strip that the penguin-rectangle had just left, while updating the background pixmap with the strip that the penguin-rectangle would move to next. Then this updated background pixmap is painted onto the window where the penguin will go and the penguin is plonked on top. It means that instead of clear/exposing the entire penguin-rectangle for each frame of the animation, only the little strip that is exposed when the penguin-rectangle moves is. Sounds a bit confusing but I don't know how else to explain it. One problem remains and that happens when penguins overlap each other -- suppose penguin A overlaps penguin B and they're heading towards each other (in xpenguins penguins just go through each other). Then when penguin A's background pixmap is updated, it will contain a little slice of penguin B in it (in the wrong position) and vice versa. This little slice of penguin propogates through the background pixmap as the penguin moves, which looks a little odd. Can anyone think of a nice way to handle this? The only thing I can think of is to do some sort of collision/overlapping detection and then be careful about the bits of background that gets copied between the penguins in question. However I'm not a computer scientist and the only way that makes sense for me to implement this is lots of inefficient loops to check every penguin against every other penguin. A related question -- do you think it's viable to make one (transparent) window per penguin? It would be easier than drawing them directly onto an existing window (Famous Last Words), but say I had 25 penguins -- would 25 new windows be a big memory drain or is X good at that sort of thing? (Thanks for that suggestion Xavier. I would rather not assume a compositor though, I have Fedora at work and Ubuntu at home but it's too sucky to have Compiz on it). cheers, Amy - By the way, if anyone can make a Grug theme for xpenguins ... I would be so happy :D ___ xorg@lists.freedesktop.org: X.Org support Archives: http://lists.freedesktop.org/archives/xorg Info: http://lists.freedesktop.org/mailman/listinfo/xorg Your subscription address: arch...@mail-archive.com
Re: xpenguins cont'd - repainting a window after penguins walk on it, and when penguins overlap.
Thanks all for your suggestions, they're much appreciated! I'm going to try the collision detection as an exercise since it seems like a classic problem and I have an easy case (2D rectangles). I'll also look into the SHAPE extension and have a tinker. Pat - the Grug books by Ted Prior were some of my favourites when I was little (still are!) :) http://www.childrensclassics.com.au/ccp0-catshow/grug_books_ted_prior_series_collecting.html I'll check back with the xorg list once I've made a bit of progress/gotten stuck. cheers! Amy On 07/06/11 00:10, Peter Harris wrote: Create one window per penguin, using the SHAPE extension. The server will handle this (and most of the rest of the things you mention above) so you don't have to. On 07/06/11 03:47, Corbin Simpson wrote: Alan's answer is great for your case. If you're feeling adventurous, you could create a spatial dictionary -- an associative array which stores all of the penguins by coordinates, using buckets which correspond to spatial areas. This massively reduces collision checking time for one-against-many, especially when you have lots of sprites to check. It might be overkill here, unless you're planning on making thousands of penguins. :3 ~ C. ___ xorg@lists.freedesktop.org: X.Org support Archives: http://lists.freedesktop.org/archives/xorg Info: http://lists.freedesktop.org/mailman/listinfo/xorg Your subscription address: arch...@mail-archive.com
clip masks/simulating transparency
Hi all, Being recently introduced to xpenguins, I thought it would be hilarious to get the penguins to run around in a window of my choice instead of the desktop (small things for small minds...;)). To this end I've started fiddling around with the xpenguins source and learning Xlib along the way, and now there's just one thing left to do to achieve heart-warming goodness. The problem is that the penguins obscure the window on which they are drawn. This can be demonstrated by getting xpenguins, using 'xwininfo' on a terminal (say) to get the window ID, and then running xpenguins -id window ID. It would be best if the window were maximised and there be no other windows on that desktop (I've put in some changes to get around this in my fiddling but that's besides the point). You see that the penguins leave little trails of window background colour behind them. Every 100 cycles xpenguins sends an Expose event to the window to remove these. By sending an expose event every time a penguin is drawn I can eliminate the trails entirely, _but_ the non-penguin part of the penguin rectangle itself is still drawn in window colour (for the terminal, that grey colour windows are by default). From examining the xpenguins source (ToonDraw in toon_draw.c), to draw the penguins: - the penguin clip mask is applied to the GC (these are penguin-shaped clip masks, I've checked) - the penguin pixmap is XCopyArea'd over to the window on which the penguins are being drawn, using the GC with the clip mask. - said clip mask is removed. According to this, the non-penguin pixels should not be drawn on at all, meaning that I shouldn't be getting bits of grey background on the penguins. Does anyone know why this is still happening? Other things I've tried are (assuming we're drawing penguins on a terminal): - dropping a clear window (no background pixmap or background pixel) on top of the terminal and drawing on that using the clip mask -- this removes the grey background bits -but- it leaves a trail of penguin behind. - XCopyArea-ing the relevant bits of the terminal onto my clear window to cover up the penguin trail -- doesn't work (I assume because the terminal is essentially covered up by my clear window/penguin trail?) - First XCopyArea-ing the relevant bits of terminal onto my penguin pixmap, THEN using the mask to copy just the penguin on top of that, and then XCopyArea-ing that pixmap (ie entire rectangle, not using the mask) onto my clear window. This gives a weird flickering background that is often blue. If anyone can give me some pointers I'd be grateful. I'm at the tearing-hair-out stage. [If anyone wants to give this a go I can send a working copy of what I've done so far. ToonDraw() in toon_draw.c is the relevant function]. cheers (sorry for overly-long post) Amy ___ xorg@lists.freedesktop.org: X.Org support Archives: http://lists.freedesktop.org/archives/xorg Info: http://lists.freedesktop.org/mailman/listinfo/xorg Your subscription address: arch...@mail-archive.com
Re: clip masks/simulating transparency
Hi all, I've sort-of worked it out (I think??) but would still like suggestions on this. The penguins -are- being drawn using the clip mask correctly onto the window of my choice. The problem was that each penguin comprises a little animation (penguin is moving), and the expose event was only being sent once per animation, not after every single frame of the animation. Since the penguins move only a few pixels per animations (say 20 or so) it looked like the clip mask just wasn't working. I've modified the code to send an expose event after each frame of the animation is drawn (so truly after each penguin is drawn), but now (as expected) it looks very very flickery -- every cycle we get a XClearArea where the old penguin was, an XExposeEvent where the old penguin was, and a XCopyArea of the next frame of the animation. Can anyone think of an alternative way to do this (have the penguins walk over a screen of my choosing and restore said window after they've passed through, without too much flickering?) -- perhaps I can copy the relevant bit of background as the background of the penguin pixmap itself, although I think I'd need to send an XExposeEvent before I can grab the background? [So close! Soon I shall have penguins taking over my windows! SOON! bahaha] cheers Amy ___ xorg@lists.freedesktop.org: X.Org support Archives: http://lists.freedesktop.org/archives/xorg Info: http://lists.freedesktop.org/mailman/listinfo/xorg Your subscription address: arch...@mail-archive.com