;******************************** ;Sinus-Berechnung in Integer- ;Arithmetik ;******************************** ;******************************** ;Sinustabelle fuer Winkel 0..90 ;(Werte * 32767) sintab: dw 0,572,1144,1715,2286 dw 2856,3425,3993,4560,5126 dw 5690,6252,6813,7371,7927 dw 8481,9032,9580,10126,10668 dw 11207,11743,12275,12803,13328 dw 13848,14364,14876,15383,15886 dw 16384,16876,17364,17846,18323 dw 18794,19260,19720,20173,20621 dw 21062,21497,21925,22347,22762 dw 23170,23571,23964,24351,24730 dw 25101,25465,25821,26169,26509 dw 26841,27165,27481,27788,28087 dw 28377,28659,28932,29196,29451 dw 29697,29934,30162,30381,30591 dw 30791,30982,31163,31335,31498 dw 31650,31794,31927,32051,32165 dw 32269,32364,32448,32523,32587 dw 32642,32687,32722,32747,32762 dw 32767 ;******************************** ;IN: HL = Winkel in Grad ;OUT: HL = SIN(HL) * 32767 ; A = Vorzeichenflag ; 0 wenn positiv ; &FF wenn negativ intsin: ld bc,360 loop1: bit 7,h ;Winkel positiv? jr z,loop2 ;-> ja, okay add hl,bc ;ansonsten + 360 jr loop1 ;-> weiter testen loop2: or a ;Carry loeschen sbc hl,bc ;Winkel - 360 jr nc,loop2 ;->weiter,wenn >=0 add hl,bc ;sonst korrigieren ld e,l ;Winkel nach DE ld d,h ld bc,90 xor a ;Vorz.flag = 0 sbc hl,bc ;Winkel < 90? jr nc,test2 ;-> nein ex de,hl ;sonst HL = Winkel jr gettab ;Tab.wert holen test2: sbc hl,bc ;Winkel < 180? jr nc,test3 ;-> nein ld hl,180 ;sonst HL = or a ;180 - Winkel sbc hl,de jr gettab ;Tab.wert holen test3: dec a ;Vorz.flag = &FF sbc hl,bc ;Winkel < 270? jr nc,test4 ;- > nein ex de,hl ;sonst HL = or a ;Carry loeschen sbc hl,bc ;Winkel - 180 sbc hl,bc jr gettab ;Tab.wert holen test4: ld hl,360 ;Wenn Winkel>=270 sbc hl,de ;HL = 360 - Winkel gettab: add hl,hl ;Winkel * 2 ld de,sintab ;+ Start Tabelle add hl,de ;= Tabellenadr. ld e,(hl) ;Lowbyte nach E inc hl ld d,(hl) ;Highbyte nach D ex de,hl ;Ergebnis nach HL ret ;******************************** ;Multiplikation mit 32-Bit-Ergeb. ;IN: HL = 1. Faktor ; DE = 2. Faktor ;OUT: DE = Lowword Ergebnis ; HL = Highword Ergebnis mul32: ld b,16 ;16 Bit abgrasen ld ix,0 ;Lowword loeschen mloop: add ix,ix ;Teilergebnis * 2 adc hl,hl ;u. 1. Faktor * 2 jr nc,noadd ;-> nicht addieren add ix,de ;2. Faktor add. jr nc,noadd ;-> kein Uebertrag inc hl ;Highword + 1 noadd: djnz mloop ;-> naechstes Bit push ix ;Lowword nach DE pop de ret ;******************************** ;32-Bit-Vorzeichenwechsel ;IN: DE = Lowword ; HL = Highword ;OUT: DE = -Lowword ; HL = -Highword vzw32: xor a ;Akku loeschen sub e ;32-Bit-Wert ld e,a ;byteweise ld a,0 ;negieren sbc a,d ld d,a ld a,0 sbc a,l ld l,a ld a,0 sbc a,h ld h,a ret ;******************************** ;Berechnet DE * COS(HL) gerundet ;IN: DE = Faktor ; HL = Winkel in Grad ;OUT: HL = DE * COS(HL) cosmul: ld bc,90 add hl,bc ;Winkel + 90 Grad ;******************************** ;Berechnet DE * SIN(HL) gerundet ;IN: DE = Faktor ; HL = Winkel in Grad ;OUT: HL = DE * SIN(HL) sinmul: push de ;Faktor retten call intsin ;HL=Sin(HL)*32767 pop de ;Faktor holen call mul32 ;HL,DE = HL * DE or a ;Vorz. testen call m,vzw32 ;ev. umdrehen ld bc,16384 ;32768/2 ex de,hl ;Low <-> Highword add hl,bc ;Add. fuer Rundung ex de,hl ld bc,0 ;Uebertrag zum adc hl,bc ;Highword addieren sla d ;Ergebnis * 2 und adc hl,hl ;mit dem Highword ret ;weiterrechnen ;******************************* ;Testroutine: Sinus- und ;Cosinuskurve zeichnen plot equ 0f000h drawsn: ld hl,0 ;Startwinkel=0 ld bc,320 ;Zaehler ploop: push bc ;Zaehler retten push hl ;Winkel retten push hl push hl push hl ld de,150 ;Faktor call sinmul ;HL=DE*SIN(HL) ld de,200 add hl,de ;Y = Ergebn. + 200 pop de ;X = Winkel call plot ;GRA PLOT ABSOLUTE pop hl ;Winkel holen ld de,150 ;Faktor call cosmul ;HL=DE*COS(HL) ld de,200 add hl,de ;Y = Ergebn. + 200 pop de ;X = Winkel call plot ;GRA PLOT ABSOLUTE pop hl ;Winkel inc hl inc hl ;Winkel + 2 pop bc ;Zaehler dec bc ;Zaehler - 1 ld a,b ;schon = 0? or c jr nz,ploop ;-> nein ret end