DrawFile_Render / Draw Files / Fonts / Scaling
Pages: 1 2
Mike Howard (479) 223 posts |
As some will know, I’ve been plodding along in my attempt to ‘wimpify’ an old scrabble clone I did way back. I’ve not made much ground of late, since I decided to investigate the use of Draw files instead of sprites. First, I created my letter tiles as Draw files, in Artworks. This was working fine until one day, without any code changes I get an error message ‘More than one font table in file (location &1EC in file)’. This address, &1EC, coincides with the end of the file. The file(s) (all based on the same initial file) seem to me to have only one font table and at the correct point in the file. They also read into Draw & Artworks without problem. Reading them into Draw and resaving them gets rid of the error, adding 88 bytes to the file in the process. Second, I don’t quite understand how to scale these Draw files. I’m using OSLib and the DrawFile_Render transformation matrix, in the form of a two dimensional array, accepts integers. How do I store say 0.5 in an integer? :-) I’m clearly missing something, probably something simple knowing me. Any comments? |
Stuart Swales (8827) 1357 posts |
The transformation matrix uses 16.16 fixed-point arithmetic, so to scale by an integer factor n, you would supply n<<16 as the diagonal elements. 0.5 would be represented by 1<<15. For a general n/m, use (n<<16)/m. |
Mike Howard (479) 223 posts |
Ahh, many thanks Stuart. |
Mike Howard (479) 223 posts |
I’m still investigating using Draw files, though not yet convinced over sprites. Using a large Draw file rendered in a window (the game board) is slow and looks bad compared to using an icon and a sprite. The process I mean, not the result. I’m simply opening a window and then rendering the Draw file within it. It appears to need redrawing immediately though which I wouldn’t of expected and is maybe contributing to the tardiness. Maybe I need some kind of background screen banking. I seem to remember doing that with the single tasking BASIC version. Is Draw file rendering just slow? |
Rick Murray (539) 13857 posts |
Are you rendering everything, or using the clipping rectangles to only render that which is necessary?
Likely slower than plotting pixels to the screen due to the plotting calculations and the complexity of the objects to be drawn. |
David J. Ruck (33) 1636 posts |
The AWRender module will render the Drawfile with anti-aliasing, which looks far better. |
Mike Howard (479) 223 posts |
I’ve only tried the full Draw file as I imagine the complexity of attempting to work out where the rectangles are within the file would be huge. I have thought about splitting the board into a number of squares, then I could plot just those squares when they coincide with the returned rectangles? Initially though, when the window is first opened, it’s as though the board gets rendered, then the wimp itself somehow overwrites it and I have to redraw it. Dunno.
Great, thanks, I’ll take a look. |
Mike Howard (479) 223 posts |
Is this usable from ‘C’ or is assembler required? Do you know of any documentation? |
Rick Murray (539) 13857 posts |
I would imagine that you already have code to translate a point clicked in the window to be a point on your virtual table, yes? Well, it’s the same idea, but you do it twice, to determine one x,y point of the window, and then the diagonally opposite x,y point. This will give you the visible part of your virtual table as can be seen in the window. Now that you know what’s visible, you can apply this to redraw rectangles to understand what part of what is visible is required to be redrawn. Then, and I’m talking out of my intergluteal cleft here as I’ve not used Drawfiles as I hate maths, you will need to calculate the bounding boxes for the Draw objects (the DrawFile renderer can plot these to aid you), and convert them into OS (VDU) co-ords rather than whatever it is that Draw uses internally. Then the simple part (!), just compare the bounding box of the Draw object to that which is needing to be redrawn. If there’s an overlap, then the object should be drawn. If no overlap, skip the object and look at the next one. That being said, how are you handling moving/plotting tiles? I would have thought it would have been better to plot “the table” (with the board and the little holder) and then plot the letter tiles individually afterwards. Take a look at my Koi-Koi (in !Store). It draws the screen using the same sort of method, drawing the table, then the cards “on the table” and then…
How is the window defined? If you are drawing stuff to the entire table area yourself, you’ll want the window to not be auto-redraw, and to not have a background colour. Then the Wimp will only draw the window furniture, leaving it to you to fill the window.
For the lulz, open your window in the middle of the screen. Then click Menu on the Pinboard to the left to open the menu. Drag that across your window. |
Mike Howard (479) 223 posts |
The complexity I was thinking about was rendering numerous partial parts of the board which is a single Draw file. Currently, the board is a single, simple Draw file, containing a square with a 15×15 grid of smaller squares, exactly like the real thing. Yes, I will know which already placed tiles need rendering (no problem) and I would also know which part of the board needs rendering but having only the single Draw file for the board I don’t have options currently. I can’t just step into a Draw file at any given point and start rendering from there! If I carve up the board into sections I could then render only those sections that coincide. Or am I being dim again :-) |
Steve Drain (222) 1620 posts |
I cannot do details off the top of my head, but DrawFile_Render allows you specify a clipping rectangle. This is very simply derived from Wimp_GetRectangle during a Wimp_RedrawWindow event. There is absolutely no need to do any complex calculations. |
Rick Murray (539) 13857 posts |
Sorry, I forgot you were using the DrawFile module. Because… with the traditional way of rendering DrawFiles, that’s more or less exactly what you do. ;-)
Yup. That’s exactly it. Looked at StrongHelp, and it’s R4 pointing to a block of four words (left, bottom, right, top). It even wants the co-ords in OS units. So, basically, work out what the redraw rectangle relates to with respect to the window work area, then toss that at DrawFile_Render and let it do the checking and complicated maths for you. ;-) |
Chris Hall (132) 3560 posts |
as I imagine the complexity of attempting to work out where the rectangles are within the file would be huge. Not at all. If you create the Draw File using MakeDraw, then you can make a note of where things are. You can also use named groups – work out the smallest group bounding box which contains the mouse position and then its 12 character name will tell you which item it is. See for example !CountDn from !Store. Or !DrawDis but DrawFile_Render allows you specify a clipping rectangle Not exactly. It will skip any item whose bounding box is wholly outside the clipping rectangle you specify but will attempt to render anything that is inside or crosses the boundary, relying on the clipping rectangle that might have been set by Wimp_GetRectangle (e.g. in a redraw window request loop) to mask out the unwanted bit. |
Rick Murray (539) 13857 posts |
That makes sense. It’s a heck of a lot simpler to rely upon the graphics window clipping than to try to calculate the maths in order to draw a part of a path (especially if it’s a Bézier curve!).
Happens all the time. SpriteOp doesn’t support a method of plotting part of a sprite. |
Mike Howard (479) 223 posts |
Thanks Steve, Chris and Rick. I’ll look at all the options once I figure out the basics of what is going on. Taking the board on it’s own, leaving aside the dragging and placing of tiles, if I don’t use the clipping mask, the board Draw file in it’s entirety gets rendered and the window is redrawn. Juat not to my liking. If I use the clipping mask, i.e. the os_box as returned by wimp_get_rectangle, the window does not get redrawn. So, I need to understand what should be happening. Is it the case that, if given the x/y co-ords and a clipping rectangle (as opposed to a zero), Drawfile_Render will render only the part of said Drawfile that would fall within the screen bounds of the clipping mask if the File were to be rendered at x/y? That’s not happening here. |
Steve Fryatt (216) 2106 posts |
Yes, but you may well have to do some coordinate conversion to allow for the differences between screen coordinates, work area coordinates and coordinates into your drawfile. It’s not something that I’ve played with before, and I don’t really have the time to think about it in more detail. Chris’s advice isn’t particularly relevant here: all objects in drawfiles have a bounding box by definition. You don’t need to make any effort to track where things are, because DrawFile_Render will do that all for you, for any drawfile, by default. |
Steve Drain (222) 1620 posts |
Reading back a little, I cannot help feeling that Mike’s better bet is using sprites, which the Wimp will handle for you. Do not worry about scaling for different screen resolutions – let that be of concern to the user, at least for now. I have 1900×1200 resolution screens from 12" to 28", so the actual size is not something you can know. As for DrawFile, it is probably worth saying that it is really only worth clipping a drawfile if it is very complex or extended, with only part on view.1 Otherwise Render the whole in each GetRectangle iteration and let the Wimp mask it. 1 Chris’s signalling images, for instance. ;-) |
Rick Murray (539) 13857 posts |
I’d agree with this. I did look at the feasibility of using DrawFiles for the game I mentioned, but wasn’t certain my starting abilities would do justice. Plus, bunging a bitmap on the screen is really simple.
My impression is that the repeated drawing was noticeably laggy, hence the idea of using clipping to cut out unnecessary redraws.
This. It’s hard to design for modern devices given that “an inch” could be damn near anything. My Koi-Koi game fits nicely on my screen. I would imagine it’s a little green patch in the corner of Clive’s monster. ;-) I tend to aim things (that I do) for a standard HD screen (1280×720) so it shouldn’t look too awful on most people’s machines (my own monitor is 1280×1024). I would imagine “the former troll” was the only person using a silly tiny resolution. Hell, my little 7" LCD panel can manage 1024×600 so it can almost cope with HD (and the Pi GPU scaling makes it quite useable). |
Mike Howard (479) 223 posts |
Well thanks for all the comments. I’m leaning towards sprites now I must admit. I did get this working the way I intended but then on return after doing something else, an old problem manifested itself again. I have no idea how!!!! Anyway, I can render the Draw file (most times) but a weird thing is, the docs state “R4 Pointer to clipping rectangle in OS units, or 0 for none” OS units do not work here, I get nothing. If I use Draw units, it renders where I expect. That’s when using a clipping mask. Using zero in R4 instead, plots the whole file but that that looks a bit interlaced. Maybe not weird, maybe DrawFile_Render makes a decision based on the contents of R4. |
David J. Ruck (33) 1636 posts |
How about a hybrid approach, render the drawfile elements in to a series of sprites at the screen dpi and colour depth. That way you get the highest possible resolution (particularly in EX0 EY0 modes), but no speed penalty. |
Mike Howard (479) 223 posts |
Ok, worth taking a look at, thanks, I’ll give that a whirl. So, finally, using Draw files, I got the rendering of the board and the re-drawing of the screen to work consistently, using a clipping mask in response to get_rectangle. Maybe because the board is large (dimensions) it is not quick to display and is beaten hands down by using an icon and a sprite. Not to mention the latter method is much easier to code. Maybe the the squares on the board should be icons too :-) |
Matthew Phillips (473) 721 posts |
Sorry if my comments diverted you down a dead end! Druck’s hybrid approach is probably a good idea. Another approach, with RiscOSM uses, is to use DrawFile_Render to a sprite and plot that to the screen in response to redraw requests. That speeds up redraw a lot. |
Mike Howard (479) 223 posts |
Not a dead end at all. I learned a lot and enjoyed it in the process. The hybrid approach is something I’m going to try for sure. My scaling of sprites is not good, especially at smaller sizes and or with rectangular pixels. First I might try icon/sprite for the board, letting the Wimp take care of that, and Draw files for tiles which I’ll look after. I haven’t seen any gotchas when using a mixture of icons and user rendered graphics. |
Mike Howard (479) 223 posts |
So, before I set off on the hybrid adventure, is it true to say that I just need to; Setup a block of memory for the sprite area. |
Rick Murray (539) 13857 posts |
|
Pages: 1 2