Login | ViewVC Help
View File | Revision Log | Show Annotations | Download File | View Changeset | Root Listing
root/aysalia/trunk/Aysalia DOS/Source/Menu/AyDosMnu.asm
Revision: 27
Committed: Fri Dec 7 23:18:13 2018 UTC (2 years, 10 months ago) by daniel-marschall
File size: 9834 byte(s)
Log Message:
Aysalia DOS now compatible with Win95 and Win98

File Contents

# User Rev Content
1 daniel-marschall 9
2     ; Aysalia DOS Launcher
3     ; Launches aydos1.gam and aydos2.gam
4 daniel-marschall 22 ; Revision 2018-12-07
5 daniel-marschall 9 ; (C) 2018 Daniel Marschall, ViaThinkSoft
6    
7     .model small
8 daniel-marschall 27 .stack 100h
9 daniel-marschall 11
10     ; -------------------------------------------------------
11    
12 daniel-marschall 9 .data
13    
14 daniel-marschall 22 exename1 db "AYDOS1.GAM", 0
15     exename2 db "AYDOS2.GAM", 0
16     cmdargs db 0, '', 0Dh
17 daniel-marschall 9
18     dummy_fcb db 36 dup(0)
19    
20     paramblk dw 0 ; use environment of parent
21     dw cmdargs ; command line arguments
22     dw 0 ; cmdargs_seg
23     dw dummy_fcb ; fcb1
24     dw 0 ; fcb1_seg
25     dw dummy_fcb ; fcb2
26     dw 0 ; fcb2_seg
27    
28 daniel-marschall 22 menu1 db 13, 10, \
29     13, 10, \
30     13, 10, \
31     13, 10, \
32     ' Aysalia DOS', 13, 10, \
33     13, 10, \
34     13, 10, \
35     ' Welches Spiel soll gestartet werden?', 13, 10, \
36     13, 10, \
37     ' Dr', 81h, 'cke eine der folgenden Tasten:', 13, 10, \
38     13, 10, \
39     ' 1 Aysalia DOS I', 13, 10, \
40     ' 2 Aysalia DOS II', 13, 10, \
41     13, 10, \
42     ' 9 Beenden', 13, 10, \
43     13, 10, \
44     13, 10, \
45     13, 10, 0
46 daniel-marschall 17
47 daniel-marschall 22 error1 db 13, 10, \
48     'Fehler: Spiel kann nicht gestartet werden. Fehlt eine Datei?', 13, 10, \
49     13, 10, 0
50 daniel-marschall 9
51 daniel-marschall 22 gameover1 db 13, 10, \
52     'Spiel zu Ende!', 13, 10, \
53     13, 10, 0
54 daniel-marschall 9
55 daniel-marschall 11 ; -------------------------------------------------------
56    
57 daniel-marschall 9 .code
58    
59     clear_vga PROC
60 daniel-marschall 22 mov ax, 0A000h
61 daniel-marschall 9 mov es, ax
62     xor di, di
63     mov ax, 0
64     mov cx, 64000
65     rep stosb
66     ret
67     clear_vga ENDP
68    
69 daniel-marschall 11 set_screen12 PROC
70     mov ah, 0 ; set screen mode
71     mov al, 12h ; graphic mode, 640x480 pixel, 16 colors (VGA)
72     int 10h
73     ret
74     set_screen12 ENDP
75    
76 daniel-marschall 9 setup_paramblk PROC
77     mov ax, cs
78     mov [paramblk + 4], ax ; cmdargs_seg
79     mov [paramblk + 8], ax ; fcb1_seg
80     mov [paramblk + 12], ax ; fcb2_seg
81     ret
82     setup_paramblk ENDP
83    
84 daniel-marschall 11 set_numlock_on PROC
85 daniel-marschall 27 push es
86    
87     ; In Windows 98+, we cannot access the BIOS Data Area,
88     ; so we use this technique to check if we are inside Windows.
89     ; This code was taken from http://www.fysnet.net/chkwin.htm
90     xor ax,ax ; point es:di to 0000:0000h
91     mov es,ax ;
92     mov di,ax ;
93     mov ax,1602h ; Get API entry point
94     int 2Fh ; call to multiplex interrupt
95     mov ax,es ;
96     or ax,ax ; if es:di doesn't point to 0000:0000h
97     jnz short is_win ; then Windows is running a DOS box
98     or di,di ; else
99     jnz short is_win ; we are in True DOS
100    
101     ; Now the actual code that sets numlock on
102 daniel-marschall 11 push ds
103     mov ax, 40h
104 daniel-marschall 22 mov ds, ax ; Go to BIOS Data Area ( http://stanislavs.org/helppc/bios_data_area.html )
105 daniel-marschall 11 mov bx, 17h ; Load Keyboard flag byte 0
106 daniel-marschall 22 mov al, [bx] ; Read
107     or al, 20h ; Set bit 5 (numlock) to 1
108     mov [bx], al ; Write
109 daniel-marschall 11 pop ds
110 daniel-marschall 27
111     is_win:
112     pop es
113 daniel-marschall 11 ret
114     set_numlock_on ENDP
115 daniel-marschall 9
116 daniel-marschall 11 flush_keyb_buf PROC
117     mov ah, 0Ch ; Flush input buffer and input
118     mov al, 0
119 daniel-marschall 9 int 21h
120 daniel-marschall 11 ret
121     flush_keyb_buf ENDP
122 daniel-marschall 9
123 daniel-marschall 11 exit_to_dos PROC
124 daniel-marschall 22 mov ah, 4Ch
125 daniel-marschall 11 mov al, 00h
126     int 21h
127     ret
128     exit_to_dos ENDP
129 daniel-marschall 9
130 daniel-marschall 11 sleep_5 PROC
131 daniel-marschall 21 mov ah, 00h
132 daniel-marschall 17 int 1Ah
133 daniel-marschall 21 cmp dx, 7FFFh
134 daniel-marschall 22 jg sleep_5_upperhalf
135     sleep_5_lowerhalf:
136 daniel-marschall 21 mov bx, dx
137 daniel-marschall 22 add bx, 91 ; 18.2 = 1 sec (therefore 91 = 5 sec)
138     sleep_5_lowerhalf_again:
139 daniel-marschall 21 int 1Ah
140 daniel-marschall 17 cmp dx, bx
141 daniel-marschall 22 jl sleep_5_lowerhalf_again
142 daniel-marschall 11 ret
143 daniel-marschall 22 sleep_5_upperhalf:
144 daniel-marschall 21 mov bx, dx
145     sub bx, 7FFFh
146 daniel-marschall 22 add bx, 91 ; 18.2 = 1 sec (therefore 91 = 5 sec)
147     sleep_5_upperhalf_again:
148 daniel-marschall 21 int 1Ah
149     sub dx, 7FFFh
150     cmp dx, bx
151 daniel-marschall 22 jl sleep_5_upperhalf_again
152 daniel-marschall 21 ret
153 daniel-marschall 11 sleep_5 ENDP
154 daniel-marschall 9
155 daniel-marschall 22 print_color_string PROC
156     ; This function requires:
157     ; dx = Pointer to zero terminated string
158     ; cl = Color
159     mov ah, 0Eh
160     print_color_string_again:
161     mov bx, dx
162 daniel-marschall 25 mov al, [bx]
163 daniel-marschall 27 test al, al ; is the character zero? then we are done
164     jz print_color_string_end
165 daniel-marschall 22 mov bl, cl
166     int 10h
167 daniel-marschall 25 add dx, 1 ; go to next character
168 daniel-marschall 22 jmp print_color_string_again
169     print_color_string_end:
170     ret
171     print_color_string ENDP
172    
173     set_bg_color PROC
174     ; This function requires:
175     ; bl = Color
176 daniel-marschall 21 mov ah, 0Bh
177     mov bh, 00h
178     int 10h
179 daniel-marschall 22 ret
180     set_bg_color ENDP
181 daniel-marschall 21
182 daniel-marschall 22 print_menu_screen PROC
183 daniel-marschall 23 ; Clear screen
184     call clear_vga
185 daniel-marschall 22
186     ; Set background color
187     mov bl, 8 ; dark green background
188     call set_bg_color
189    
190     ; Set text color
191     mov cl, 0Fh ; white font
192 daniel-marschall 9 lea dx, menu1
193 daniel-marschall 22 call print_color_string
194    
195 daniel-marschall 11 ret
196     print_menu_screen ENDP
197    
198 daniel-marschall 17 print_error_screen PROC
199 daniel-marschall 23 ; Clear screen
200     call clear_vga
201 daniel-marschall 21
202 daniel-marschall 22 ; Set background color
203     mov bl, 4 ; dark red background
204     call set_bg_color
205    
206     ; Set text color
207     mov cl, 0Fh ; white font
208 daniel-marschall 17 lea dx, error1
209 daniel-marschall 22 call print_color_string
210    
211 daniel-marschall 17 ret
212     print_error_screen ENDP
213    
214 daniel-marschall 23 print_gameover_message PROC
215 daniel-marschall 22 ; Keep cursor position
216 daniel-marschall 21
217 daniel-marschall 22 ; Set background color
218 daniel-marschall 27 mov bl, 4 ; dark red background
219 daniel-marschall 22 call set_bg_color
220    
221     ; Set text color
222 daniel-marschall 27 mov cl, 0Fh ; white font
223 daniel-marschall 11 lea dx, gameover1
224 daniel-marschall 22 call print_color_string
225    
226 daniel-marschall 11 ret
227 daniel-marschall 23 print_gameover_message ENDP
228 daniel-marschall 11
229     ; -------------------------------------------------------
230    
231     start:
232     ; Setup data segment
233     mov ax, @data ; moving base address of data to ax
234     mov ds, ax ; moving contents of ax into ds
235     ; data section now gets initialized
236    
237     ; Preserve the original screen mode
238     mov ah, 0Fh ; Query screen mode
239     int 10h
240     push ax ; actually, we are only interested in register al (screen mode), not in ah (column count)
241 daniel-marschall 9
242 daniel-marschall 11 ; Change numlock to ON
243     ; DOSBox has a bug where the NumLock is not correctly set to the setting of the host system,
244     ; so you have to press the NumLock key twice so that DOSBox recognizes the status.
245     ; see: https://sourceforge.net/p/dosbox/bugs/71/
246     ; https://superuser.com/questions/255102/is-there-a-way-to-use-the-numeric-keypad-in-dosbox/1146986
247     ; Since the game uses number keys very often, we set NumLock to ON
248     call set_numlock_on
249    
250     ; Reduce size of own application to give the called applications more space
251     ; see https://stackoverflow.com/a/10067627
252     mov ah, 4Ah
253 daniel-marschall 14 mov bx, 100 ; 100 paragraphs a 16 bytes = 1600 bytes
254 daniel-marschall 11 int 21h
255    
256     menu:
257     ; Video Mode VGA 12
258     call set_screen12
259    
260     ; Flush keyboard buffer
261     call flush_keyb_buf
262    
263     ; Print menu screen
264     call print_menu_screen
265    
266 daniel-marschall 9 retry:
267     ; Query keyboard input
268 daniel-marschall 11 mov ah, 07h ; Direct character input, without echo
269 daniel-marschall 9 int 21h
270     cmp al, '1'
271     je prog1
272     cmp al, '2'
273     je prog2
274     cmp al, '9'
275 daniel-marschall 11 je exit
276 daniel-marschall 9
277     ; Invalid input
278     jmp retry
279    
280     prog1:
281     ; Clear screen
282     call clear_vga
283    
284     ; Setup parameter block for the EXEC command
285     call setup_paramblk
286    
287     ; Start game 1
288 daniel-marschall 27 mov ax, @data ; ds:dx = ASCIZ program name (must include extension)
289     mov ds, ax
290     lea dx, exename1
291     mov ax, @data ; es:bx = Parameter block
292     mov es, ax
293 daniel-marschall 9 mov bx, paramblk
294 daniel-marschall 27 mov ah, 4Bh ; execute
295     mov al, 00h ; load and execute
296     int 21h ; DOS API
297 daniel-marschall 9
298 daniel-marschall 17 ; Is everything OK? Or is the GAM file missing?
299     jc error
300    
301 daniel-marschall 11 ; Notify the player that the game has finished
302 daniel-marschall 9 jmp gameover
303    
304     prog2:
305     ; Clear screen
306     call clear_vga
307    
308     ; Setup parameter block for the EXEC command
309     call setup_paramblk
310    
311     ; Start game 2
312 daniel-marschall 27 mov ax, @data ; ds:dx = ASCIZ program name (must include extension)
313     mov ds, ax
314     lea dx, exename2
315     mov ax, @data ; es:bx = Parameter block
316     mov es, ax
317 daniel-marschall 9 mov bx, paramblk
318 daniel-marschall 27 mov ah, 4Bh ; execute
319     mov al, 00h ; load and execute
320     int 21h ; DOS API
321 daniel-marschall 17
322     ; Is everything OK? Or is the GAM file missing?
323     jc error
324 daniel-marschall 9
325 daniel-marschall 11 ; Notify the player that the game has finished
326 daniel-marschall 9 jmp gameover
327 daniel-marschall 11
328 daniel-marschall 17 error:
329     ; Video Mode VGA 12
330     call set_screen12
331    
332     ; Print error
333     call print_error_screen
334    
335     ; Give the player time to read the error message (approx 5 seconds)
336     call sleep_5
337    
338     ; Go back to the menu
339     jmp menu
340    
341 daniel-marschall 9 gameover:
342 daniel-marschall 23 ; Print gameover message
343     call print_gameover_message
344 daniel-marschall 9
345 daniel-marschall 11 ; Give the player time to read the game over message (approx 5 seconds)
346     call sleep_5
347 daniel-marschall 9
348 daniel-marschall 11 ; Go back to the menu
349 daniel-marschall 9 jmp menu
350    
351 daniel-marschall 11 exit:
352 daniel-marschall 9 ; Reset video mode to DOS default
353 daniel-marschall 11 pop ax ; the video mode we have preserved at program start
354     mov ah, 0 ; set screen mode
355 daniel-marschall 9 int 10h
356    
357     ; Return to DOS
358 daniel-marschall 11 call exit_to_dos
359 daniel-marschall 9
360 daniel-marschall 11 ; -------------------------------------------------------
361    
362 daniel-marschall 9 end start