chiark / gitweb /
JPEG support and other fixes from Nick Clark
[ssr] / StraySrc / Libraries / Sapphire / s / wimp
1 ;
2 ; wimp.s
3 ;
4 ; Starting and ending of Wimp tasks (TMA)
5 ;
6 ; © 1994-1998 Straylight
7 ;
8
9 ;----- Licensing note -------------------------------------------------------
10 ;
11 ; This file is part of Straylight's Sapphire library.
12 ;
13 ; Sapphire is free software; you can redistribute it and/or modify
14 ; it under the terms of the GNU General Public License as published by
15 ; the Free Software Foundation; either version 2, or (at your option)
16 ; any later version.
17 ;
18 ; Sapphire is distributed in the hope that it will be useful,
19 ; but WITHOUT ANY WARRANTY; without even the implied warranty of
20 ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21 ; GNU General Public License for more details.
22 ;
23 ; You should have received a copy of the GNU General Public License
24 ; along with Sapphire.  If not, write to the Free Software Foundation,
25 ; 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26
27 ;----- Standard header ------------------------------------------------------
28
29                 GET     libs:header
30                 GET     libs:swis
31
32 ;----- External dependencies ------------------------------------------------
33
34                 GET     sapphire:except
35                 GET     sapphire:libOpts
36                 GET     sapphire:roVersion
37                 GET     sapphire:sapphire
38
39 ;----- Main code ------------------------------------------------------------
40
41                 AREA    |Sapphire$$Code|,CODE,READONLY
42
43 ; --- wimp_init ---
44 ;
45 ; On entry:     R0 == pointer to application name
46 ;
47 ; On exit:      --
48 ;
49 ; Use:          Initialises the WindowManager, and stores away useful
50 ;               snippets of information, like the task handle we've been
51 ;               given.  It also registers an exit handler so that the Wimp
52 ;               gets closed down.
53
54                 EXPORT  wimp_init
55 wimp_init       ROUT
56
57                 STMFD   R13!,{R0-R3,R12,R14}    ;Stash some registers
58                 WSPACE  wimp__wSpace            ;Find my workspace
59
60                 ; --- Make sure I'm not already running ---
61
62                 LDR     R0,wimp__taskh          ;What's my task handle?
63                 CMP     R0,#0                   ;0 is a silly task handle
64                 LDMNEFD R13!,{R0-R3,R12,PC}^    ;If not silly, quit now
65
66                 ; --- Find what WIMP version we're set for ---
67
68                 LDR     R0,wimp__optName        ;Find the option name
69                 BL      libOpts_find            ;Try to find the option block
70                 LDRCS   R3,[R0,#0]              ;If found, load version
71                 MOVCC   R3,#0                   ;Otherwise use a default
72
73                 ; --- Suss out the Wimp version from the OS version ---
74
75                 BL      rov_init                ;Initialise RISC OS version
76                 BL      rov_version             ;Work out the RISC OS version
77                 LDR     R14,=310                ;Get the number 310
78                 CMP     R0,R14                  ;Is it version 3.10 yet?
79                 MOVLT   R0,#200                 ;No -- use RISC OS 2
80                 MOVGE   R0,R14                  ;Otherwise use RISC OS 3.10
81
82                 ; --- Now use whichever is bigger ---
83                 ;
84                 ; Woe betides a foolish person who sets wimp_minVersion to
85                 ; be 350 :-)
86
87                 CMP     R0,R3                   ;Which is the biggest?
88                 MOVLT   R0,R3                   ;If the user's, use that
89
90                 ; --- Initialise the Wimp ---
91
92                 LDR     R1,=&4B534154           ;The traditional magic no.
93                 LDR     R2,[R13,#0]             ;Get the app name pointer
94                 MOV     R3,#-1                  ;Give me *all* messages
95                 SWI     Wimp_Initialise         ;Crank up the WindowMangler
96
97                 ; --- Store useful stuff away ---
98
99                 STR     R0,wimp__version        ;Store WIMP's real version
100                 STR     R1,wimp__taskh          ;Store my task handle too
101
102                 ; --- Set me up to close down at the end ---
103
104                 BL      except_init             ;Make sure except is going
105                 ADR     R0,wimp__die            ;Point to my exit handler
106                 MOV     R1,R12                  ;Get my workspace pointer
107                 BL      except_atExit           ;Set it up nicely then
108
109                 ; --- Return with the knowledge of a job well done ---
110
111                 LDMFD   R13!,{R0-R3,R12,PC}^    ;Return to caller
112
113 wimp__optName   DCB     "WIMP"
114
115                 LTORG
116
117 wimp__wSpace    DCD     0
118
119 ; --- wimp__die ---
120 ;
121 ; On entry:     --
122 ;
123 ; On exit:      --
124 ;
125 ; Use:          Closes down the WindowManager nicely, just so that it
126 ;               doesn't have to do it itself.
127
128 wimp__die       ROUT
129
130                 STMFD   R13!,{R0,R1,R14}        ;Stash my registers
131                 LDR     R0,wimp__taskh          ;Get my task handle
132                 LDR     R1,=&4B534154           ;The magic number again
133                 SWI     XWimp_CloseDown         ;Close down the WIMP then
134                 LDMFD   R13!,{R0,R1,PC}^        ;Return to caller
135
136                 LTORG
137
138 ; --- wimp_taskHandle ---
139 ;
140 ; On entry:     --
141 ;
142 ; On exit:      R0 == the application's task handle
143 ;
144 ; Use:          Returns the application's task handle.
145
146                 EXPORT  wimp_taskHandle
147 wimp_taskHandle ROUT
148
149                 STMFD   R13!,{R14}              ;Save a register
150                 LDR     R0,wimp__wSpace         ;Find my workspace offset
151                 LDR     R14,sapph_workspace     ;Load workspace block base
152                 LDR     R0,[R0,R14]             ;Load WIMP version number
153                 LDMFD   R13!,{PC}^              ;Return to caller
154
155                 LTORG
156
157 ; --- wimp_version ---
158 ;
159 ; On entry:     --
160 ;
161 ; On exit:      R0 == the WIMP's version number (may not be the one the
162 ;                     client asked for)
163 ;
164 ; Use:          Returns the WindowManager's version number.
165
166                 EXPORT  wimp_version
167 wimp_version    ROUT
168
169                 STMFD   R13!,{R14}              ;Save a register
170                 WSPACE  wimp__wSpace,R0         ;Find workspace
171                 LDR     R0,[R0,#:INDEX: wimp__version]
172                 LDMFD   R13!,{PC}^              ;Return to caller
173
174                 LTORG
175
176 ; --- wimp_strWidth ---
177 ;
178 ; On entry:     R0 == pointer to a string
179 ;
180 ; On exit:      R0 == width of the string in OS units
181 ;
182 ; Use:          Returns the width of a string, as it would be displayed in
183 ;               an icon (i.e. taking into account things like the current
184 ;               desktop font etc.)  The width is exact, so if you want to
185 ;               e.g. draw a box round it, you'll have to add on a little
186 ;               clearance at each end.  8 OS units seems to be a good size
187 ;               for the clearance (so the total width you'd use is given by
188 ;               wimp_strWidth(string)+16, because it has two ends).
189
190                 EXPORT  wimp_strWidth
191 wimp_strWidth   ROUT
192
193                 ; --- We need to find the string length anyway ---
194                 ;
195                 ; This length calculation is done inline to avoid a
196                 ; dependency on string.  It's not very long, anyway, and
197                 ; it *does* save a MOV R5,R0 :-)
198
199                 STMFD   R13!,{R1-R7,R14}        ;Save a bunch of registers
200                 MOV     R5,#0                   ;Length counter starts at 0
201                 MOV     R7,#0                   ;Width so far
202                 MOV     R6,R0                   ;Keep string pointer
203 00wimp_strWidth LDRB    R14,[R0,R5]             ;Get a byte from the string
204                 CMP     R14,#' '                ;Is it a control char?
205                 ADDCS   R5,R5,#1                ;Bump on *anyway* (see above)
206                 BCS     %00wimp_strWidth        ;If more to go, loop back
207
208                 ; --- Now try to find the current font handle ---
209
210                 MOV     R0,#8                   ;Read Wimp font handle
211                 SWI     XWimp_ReadSysInfo       ;Find out from WindowMangler
212                 BVS     %01wimp_strWidth        ;If Wimp too old/buggy, skip
213                 CMP     R0,#0                   ;Is there there a real font?
214                 BEQ     %01wimp_strWidth        ;No -- skip ahead too
215
216                 ; --- Now suss out the width of the string ---
217                 ;
218                 ; There maybe a shift character on the beginning, so
219                 ; treat that seperately ;-)
220
221                 LDRB    R14,[R6,#0]             ;Load the first character
222                 CMP     R14,#&8B                ;Is it a shift character
223                 BNE     %10wimp_strWidth        ;No -- jump on a bit
224                 ADD     R6,R6,#1                ;Yes -- point past this char
225                 MOV     R5,R0                   ;Look after font handle
226                 BL      wimp_version            ;Get the wimp version
227                 CMP     R0,#340                 ;RISC OS 3.5 or higher?
228                 CMPGE   R1,#1                   ;Is there a symbol font?
229                 MOVGE   R0,R1                   ;Yes -- use this
230                 MOVGE   R1,R14                  ;And the shift character
231                 MOVLT   R0,R5                   ;Otherwise use current hnd
232                 MOVLT   R1,#'M'                 ;...and be generous
233                 MOV     R2,#(1<<4)              ;Return OS coords
234                 SWI     Font_CharBBox           ;Get bounding box
235                 MOV     R0,R5                   ;Put normal handle back in R0
236                 SUB     R7,R3,R1                ;Put width in R7
237
238 10wimp_strWidth SWI     Font_SetFont            ;Set up the desktop font
239                 MOV     R1,#1000                ;A nice big round number
240                 MOV     R2,R1                   ;And another nice big number
241                 SWI     Font_Converttopoints    ;Font_StringWidth is weird
242                 MOV     R3,R2                   ;Move coords to right regs
243                 MOV     R2,R1                   ;That means both of them
244                 MOV     R1,R6                   ;Retreive string pointer
245                 MOV     R4,#-1                  ;Don't split the string
246                 ADD     R5,R5,#1                ;Move this counter on one
247                 SWI     Font_StringWidth        ;Find the width of the string
248                 MOV     R1,R2                   ;Move coordinates back again
249                 MOV     R2,R3                   ;Again, that means both
250                 SWI     Font_ConverttoOS        ;Convert to OS units now
251                 MOV     R0,R1                   ;Put the width in R0
252                 ADD     R0,R0,R7                ;Add on previous width
253                 LDMFD   R13!,{R1-R7,PC}^        ;Return to caller, then
254
255                 ; --- Just normal system font ---
256
257 01wimp_strWidth MOV     R0,R5,LSL #4            ;Multiply by character width
258                 LDMFD   R13!,{R1-R7,PC}^        ;Return to caller
259
260                 LTORG
261
262 ;----- Workspace ------------------------------------------------------------
263
264                 ^       0,R12
265 wimp__wStart    #       0
266
267 wimp__taskh     #       4                       ;Wimp task handle
268 wimp__version   #       4                       ;Wimp version number
269
270 wimp__wSize     EQU     {VAR}-wimp__wStart
271
272                 AREA    |Sapphire$$LibData|,CODE,READONLY
273
274                 DCD     wimp__wSize
275                 DCD     wimp__wSpace
276                 DCD     0
277                 DCD     wimp_init
278
279 ;----- That's all, folks ----------------------------------------------------
280
281                 END