Casio PD‑700 — Часть 11: мои программы на BASIC
Кажется, к этому моменту о Casio PD‑700B удалось узнать уже немало, и теперь можно поэкспериментировать с программированием на BASIC. В предыдущих частях я выкладывал программы, которые использовал в ходе исследования. Пришло время показать ещё несколько написанных ранее программ, демонстрирующих его возможности и позволяющих ненадолго отвлечься от изучения внутреннего устройства.
- Пароль на запуск
Благодаря наличию программы "PA", автоматически запускаемой при включении, и оператора "BRK OFF", запрещающего остановку клавишей "BRK", появляется возможность задать действие, принудительно выполняющееся при каждом включении. Первое, что пришло мне на ум - это программа, запрашивающая пароль.
В этой программе я использую системный пароль, устанавливаемый с помощью "PASS" и используемый для защиты программ.
10 BRK OFF:CLEAR:N$=INKEY$
20 FOR I=0 TO 7:B=PEEK(&HD55+I):IF B<255;P$=P$+CHR$(255-B):NEXT I
30 IF P$="";GOTO 100
40 CLS:PRINT "PASS?":LOCATE 0,1:OP$=""
50 FOR I=0 TO 7
60 K$=INPUT$(1):IF K$=CHR$(235);GOTO 60
70 IF K$=CHR$(24);PRINT K$;:OP$="":I=0:GOTO 60
80 OP$=OP$+K$:PRINT "*";:IF OP$=P$;BEEP1:GOTO 100
90 NEXT I:BEEP:BEEP:BEEP:GOTO 40
100 IF N$<>CHR$(235);CLEAR:END
110 CLS:PRINT "NEW?":LOCATE 0,1:INPUT "";@8;NP$
120 IF OP$<>"";PASS OP$
130 IF NP$<>"";PASS NP$
140 CLEAR:BEEP1
Также с помощью этой программы можно установить новый пароль или изменить уже имеющийся. Для этого в момент включения нужно нажимать в отверстие "CONT.". Если пароль ещё не был установлен, сразу появится запрос на ввод нового, если же пароль уже был, запрос на ввод нового появится только после правильного ввода уже имеющегося.
Маленькая хитрость: программу всё ещё можно остановить клавишей "STOP", но для этого требуется замкнуть контакты, которые изначально не выведены.
- Вывод изображений
В отличие от других устройств со схожим процессором, PD‑700B имеет графический дисплей без межсегментных промежутков. При этом ширина дисплея вдвое меньше, чем у большинства устройств с дисплеями такого типа, для которых уже создано множество пиксельных изображений. Я искал изображения, не теряющие основных деталей после обрезки, и остановился на выведенном на Sharp PC‑1350 и опубликованном в этом посте. Для сравнения я вывел его несколькими разными способами.
10 CLEAR:WIDTH,4
20 FOR I=0 TO 63:READ A$:DEFCHR$(255)=A$:PRINT CHR$(255);:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA 140000202010,904848240003,1FFFFFFFFFFC,F3FFFFFFFEC1,3FF0CE3EFCFC,FCF9FBFBFBF9,C000F03CC0F0,FCFCFCFCF8F8,F838C03800C0,F0F0F1F3F3FB,F9FC3CC0F83E,4BFCFFFFFFFF,EFF1FEFFFFFF,FFFF18060100,002444880810,102000000000
120 DATA E01804040000,00010E30CFFF,FFFFFFFFC03F,FFFFFFFF3FC0,C000001E3040,8FBF470747BF,8F6000000000,000000000000,000000000000,608FBF470747,BF8F40301E00,C000FFFFFFFF,FFFF1FE0FFFF,FFFF7F00C030,0E0100000001,320E11110000
130 DATA 212100000718,6080001FFFFF,FFFFFFE01FFF,FFFFFFFFFFFF,000000000000,E0D8C4E0C498,E00000000000,000000040000,000000000000,00E0D8C4E0C4,98E000000000,00000FFFFFFF,FFFFFF7F80FF,FFFFFF7F0000,00FF00000000,030404040300
140 DATA 00000000E01C,03003FFFFFFF,FFFFFF03FCFF,FFFFFFFFFF1F,FF0F03010000,000000000000,000000000000,000708101010,080700000000,000000000000,000000000103,0FFF3FFFFFFF,FFFFFFF00FFF,FFFFFFFF7F07,38C000000000,0000006C8C00
10 CLEAR:WIDTH,2
20 FOR I=0 TO 23:READ A$:DEFCHR$(255)=A$:PRINT CHR$(255);:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA 1400002020109048E018040400000001,482400031FFFFFFF0E30CFFFFFFFFFFF,FFFCF3FFFFFFFEC1C03FFFFFFFFF3FC0,3FF0CE3EFCFCFCF9C000001E30408FBF,FBFBFBF9C000F03C470747BF8F600000,C0F0FCFCFCFCF8F80000000000000000
120 DATA F838C03800C0F0F0000000000000608F,F1F3F3FBF9FC3CC0BF470747BF8F4030,F83E4BFCFFFFFFFF1E00C000FFFFFFFF,EFF1FEFFFFFFFFFFFFFF1FE0FFFFFFFF,18060100002444887F00C0300E010000,08101020000000000001320E11110000
130 DATA 212100000718608000000000E01C0300,001FFFFFFFFFFFE03FFFFFFFFFFFFF03,1FFFFFFFFFFFFFFFFCFFFFFFFFFFFF1F,000000000000E0D8FF0F030100000000,C4E0C498E00000000000000000000000,00000000000400000000000708101010
140 DATA 00000000000000E00807000000000000,D8C4E0C498E000000000000000000000,000000000FFFFFFF01030FFF3FFFFFFF,FFFFFF7F80FFFFFFFFFFFFF00FFFFFFF,FF7F000000FF0000FFFF7F0738C00000,000003040404030000000000006C8C00
10 CLEAR:WIDTH,2
20 FOR I=0 TO 11:READ A$:DEFKAN$(32)=A$:KPRINT "8120";:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA 1400002020109048482400031FFFFFFFE0180404000000010E30CFFFFFFFFFFF,FFFCF3FFFFFFFEC13FF0CE3EFCFCFCF9C03FFFFFFFFF3FC0C000001E30408FBF,FBFBFBF9C000F03CC0F0FCFCFCFCF8F8470747BF8F6000000000000000000000
120 DATA F838C03800C0F0F0F1F3F3FBF9FC3CC0000000000000608FBF470747BF8F4030,F83E4BFCFFFFFFFFEFF1FEFFFFFFFFFF1E00C000FFFFFFFFFFFF1FE0FFFFFFFF,180601000024448808101020000000007F00C0300E0100000001320E11110000
130 DATA 2121000007186080001FFFFFFFFFFFE000000000E01C03003FFFFFFFFFFFFF03,1FFFFFFFFFFFFFFF000000000000E0D8FCFFFFFFFFFFFF1FFF0F030100000000,C4E0C498E0000000000000000004000000000000000000000000000708101010
140 DATA 00000000000000E0D8C4E0C498E0000008070000000000000000000000000000,000000000FFFFFFFFFFFFF7F80FFFFFF01030FFF3FFFFFFFFFFFFFF00FFFFFFF,FF7F000000FF00000000030404040300FFFF7F0738C0000000000000006C8C00
Так как переопределить можно 4 символа, я также проверил скорость и плавность вывода квадратами 32x32, используя по 4 символа Кандзи. Разница не ощутима.
10 CLEAR:WIDTH,2
20 FOR I=0 TO 8 STEP 4
30 FOR J=32 TO 35:READ A$:DEFKAN$(J)=A$:NEXT J
40 LOCATE I,0:KPRINT "8120,8121";
50 LOCATE I,1:KPRINT "8122,8123";
60 NEXT I
70 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA 1400002020109048482400031FFFFFFFE0180404000000010E30CFFFFFFFFFFF,FFFCF3FFFFFFFEC13FF0CE3EFCFCFCF9C03FFFFFFFFF3FC0C000001E30408FBF,2121000007186080001FFFFFFFFFFFE000000000E01C03003FFFFFFFFFFFFF03
120 DATA 1FFFFFFFFFFFFFFF000000000000E0D8FCFFFFFFFFFFFF1FFF0F030100000000,FBFBFBF9C000F03CC0F0FCFCFCFCF8F8470747BF8F6000000000000000000000,F838C03800C0F0F0F1F3F3FBF9FC3CC0000000000000608FBF470747BF8F4030
130 DATA C4E0C498E0000000000000000004000000000000000000000000000708101010,00000000000000E0D8C4E0C498E0000008070000000000000000000000000000,F83E4BFCFFFFFFFFEFF1FEFFFFFFFFFF1E00C000FFFFFFFFFFFF1FE0FFFFFFFF
140 DATA 180601000024448808101020000000007F00C0300E0100000001320E11110000,000000000FFFFFFFFFFFFF7F80FFFFFF01030FFF3FFFFFFFFFFFFFF00FFFFFFF,FF7F000000FF00000000030404040300FFFF7F0738C0000000000000006C8C00
И, наконец, я проверил эффективность вывода путём заполнения области дисплея в RAM (в данном случае необходимо развернуть тетрады в каждом байте). Побайтовая отправка интерпретатором делает такой метод значительно медленнее остальных.
10 CLEAR
20 FOR I=768 TO 1151:READ A:POKE I,A:NEXT I
30 PRINT:BEEP1:A$=INPUT$(1,@)
110 DATA &H41,&H00,&H00,&H02,&H02,&H01,&H09,&H84,&H84,&H42,&H00,&H30,&HF1,&HFF,&HFF,&HFF,&HFF,&HCF,&H3F,&HFF,&HFF,&HFF,&HEF,&H1C,&HF3,&H0F,&HEC,&HE3,&HCF,&HCF,&HCF,&H9F,&HBF,&HBF,&HBF,&H9F,&H0C,&H00,&H0F,&HC3,&H0C,&H0F,&HCF,&HCF,&HCF,&HCF,&H8F,&H8F
120 DATA &H8F,&H83,&H0C,&H83,&H00,&H0C,&H0F,&H0F,&H1F,&H3F,&H3F,&HBF,&H9F,&HCF,&HC3,&H0C,&H8F,&HE3,&HB4,&HCF,&HFF,&HFF,&HFF,&HFF,&HFE,&H1F,&HEF,&HFF,&HFF,&HFF,&HFF,&HFF,&H81,&H60,&H10,&H00,&H00,&H42,&H44,&H88,&H80,&H01,&H01,&H02,&H00,&H00,&H00,&H00
130 DATA &H0E,&H81,&H40,&H40,&H00,&H00,&H00,&H10,&HE0,&H03,&HFC,&HFF,&HFF,&HFF,&HFF,&HFF,&H0C,&HF3,&HFF,&HFF,&HFF,&HFF,&HF3,&H0C,&H0C,&H00,&H00,&HE1,&H03,&H04,&HF8,&HFB,&H74,&H70,&H74,&HFB,&HF8,&H06,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00
140 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H06,&HF8,&HFB,&H74,&H70,&H74,&HFB,&HF8,&H04,&H03,&HE1,&H00,&H0C,&H00,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&HF1,&H0E,&HFF,&HFF,&HFF,&HFF,&HF7,&H00,&H0C,&H03,&HE0,&H10,&H00,&H00,&H00,&H10,&H23,&HE0,&H11,&H11,&H00,&H00
150 DATA &H12,&H12,&H00,&H00,&H70,&H81,&H06,&H08,&H00,&HF1,&HFF,&HFF,&HFF,&HFF,&HFF,&H0E,&HF1,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&H00,&H00,&H00,&H00,&H00,&H00,&H0E,&H8D,&H4C,&H0E,&H4C,&H89,&H0E,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H40,&H00,&H00
160 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H0E,&H8D,&H4C,&H0E,&H4C,&H89,&H0E,&H00,&H00,&H00,&H00,&H00,&H00,&HF0,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&HF7,&H08,&HFF,&HFF,&HFF,&HFF,&HF7,&H00,&H00,&H00,&HFF,&H00,&H00,&H00,&H00,&H30,&H40,&H40,&H40,&H30,&H00
170 DATA &H00,&H00,&H00,&H00,&H0E,&HC1,&H30,&H00,&HF3,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&H30,&HCF,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&HF1,&HFF,&HF0,&H30,&H10,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H70,&H80,&H01,&H01,&H01
180 DATA &H80,&H70,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&H10,&H30,&HF0,&HFF,&HF3,&HFF,&HFF,&HFF,&HFF,&HFF,&HFF,&H0F,&HF0,&HFF,&HFF,&HFF,&HFF,&HFF,&HF7,&H70,&H83,&H0C,&H00,&H00,&H00,&H00,&H00,&H00,&H00,&HC6,&HC8,&H00
Кроме этого, я выводил ещё некоторые изображения. Например, следующее - это кадр из Java игры "Incubus", выпущенной для Siemens SL‑45i.
10 CLEAR:WIDTH,4
20 FOR I=0 TO 63:READ A$:DEFCHR$(255)=A$:PRINT CHR$(255);:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA FD6AF6D0EC50,E1930604090A,0A183C7F7FFC,FF3F3D0F83E0,7F33193DDFEF,FFFF7F7F7F7F,FCE000000000,3F1807E08000,00005C0000ED,000000C01000,0080003EFF80,010101010101,030303010000,1C1C3FFFFEFE,FEFE06030100,000000008000
120 DATA 00000003077E,F8307F7F3F3F,3F1C0101C160,208ECEECE3E7,F0F8392D2D3D,3D3D3D9FDF3E,00000000017F,F00000FF0000,000000000101,0703070F070F,070F060F83E5,71B8D8EFC0C7,CECC8C050504,FF3F1E1F3F63,5BDBC3C7FD79,3B0F00000000
130 DATA 214143F3F83E,0E7FFFFBF3F1,F0F2D37BA9B4,DE6B6F35171F,1B0F07071F9F,8FC7C7C6E17F,0003070BFEFE,1E1C7BE00000,0000287EFFFF,FFFFFFEFDFF7,F9FCFE3FFCF8,400000E07CF6,76363EBCBF7F,FFE02563EBC6,D7CDDBFFFFBF,9F0003060404
140 DATA FFC7838D8501,010180C0F0F8,381C1C8CCEFE,FE7EFEFEFEFE,EEEECECECEDE,9BB9F9F1E3C7,3FFFFF7F5757,57D8F0000000,000000000000,808080808000,B0DC5497A5AD,FB8F77020100,0000070CC828,34D4FA7EFFF7,D3F1A4EE5EFC,FF7FFF3F7FFF
10 CLEAR:WIDTH,2
20 FOR I=0 TO 23:READ A$:DEFCHR$(255)=A$:PRINT CHR$(255);:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA FD6AF6D0EC50E19300000003077EF830,0604090A0A183C7F7F7F3F3F3F1C0101,7FFCFF3F3D0F83E0C160208ECEECE3E7,7F33193DDFEFFFFFF0F8392D2D3D3D3D,7F7F7F7FFCE000003D9FDF3E00000000,00003F1807E08000017FF00000FF0000
120 DATA 00005C0000ED00000000000001010703,00C010000080003E070F070F070F060F,FF8001010101010183E571B8D8EFC0C7,0303030100001C1CCECC8C050504FF3F,3FFFFEFEFEFE06031E1F3F635BDBC3C7,0100000000008000FD793B0F00000000
130 DATA 214143F3F83E0E7FFFC7838D85010101,FFFBF3F1F0F2D37B80C0F0F8381C1C8C,A9B4DE6B6F35171FCEFEFE7EFEFEFEFE,1B0F07071F9F8FC7EEEECECECEDE9BB9,C7C6E17F0003070BF9F1E3C73FFFFF7F,FEFE1E1C7BE00000575757D8F0000000
140 DATA 0000287EFFFFFFFF0000000000008080,FFEFDFF7F9FCFE3F80808000B0DC5497,FCF8400000E07CF6A5ADFB8F77020100,76363EBCBF7FFFE00000070CC82834D4,2563EBC6D7CDDBFFFA7EFFF7D3F1A4EE,FFBF9F00030604045EFCFF7FFF3F7FFF
10 CLEAR:WIDTH,2
20 FOR I=0 TO 11:READ A$:DEFKAN$(32)=A$:KPRINT "8120";:NEXT I
30 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA FD6AF6D0EC50E1930604090A0A183C7F00000003077EF8307F7F3F3F3F1C0101,7FFCFF3F3D0F83E07F33193DDFEFFFFFC160208ECEECE3E7F0F8392D2D3D3D3D,7F7F7F7FFCE0000000003F1807E080003D9FDF3E00000000017FF00000FF0000
120 DATA 00005C0000ED000000C010000080003E0000000001010703070F070F070F060F,FF800101010101010303030100001C1C83E571B8D8EFC0C7CECC8C050504FF3F,3FFFFEFEFEFE060301000000000080001E1F3F635BDBC3C7FD793B0F00000000
130 DATA 214143F3F83E0E7FFFFBF3F1F0F2D37BFFC7838D8501010180C0F0F8381C1C8C,A9B4DE6B6F35171F1B0F07071F9F8FC7CEFEFE7EFEFEFEFEEEEECECECEDE9BB9,C7C6E17F0003070BFEFE1E1C7BE00000F9F1E3C73FFFFF7F575757D8F0000000
140 DATA 0000287EFFFFFFFFFFEFDFF7F9FCFE3F000000000000808080808000B0DC5497,FCF8400000E07CF676363EBCBF7FFFE0A5ADFB8F770201000000070CC82834D4,2563EBC6D7CDDBFFFFBF9F0003060404FA7EFFF7D3F1A4EE5EFCFF7FFF3F7FFF
10 CLEAR:WIDTH,2
20 FOR I=0 TO 8 STEP 4
30 FOR J=32 TO 35:READ A$:DEFKAN$(J)=A$:NEXT J
40 LOCATE I,0:KPRINT "8120,8121";
50 LOCATE I,1:KPRINT "8122,8123";
60 NEXT I
70 LOCATE 0,0:BEEP1:K$=INPUT$(1,@)
110 DATA FD6AF6D0EC50E1930604090A0A183C7F00000003077EF8307F7F3F3F3F1C0101,7FFCFF3F3D0F83E07F33193DDFEFFFFFC160208ECEECE3E7F0F8392D2D3D3D3D,214143F3F83E0E7FFFFBF3F1F0F2D37BFFC7838D8501010180C0F0F8381C1C8C
120 DATA A9B4DE6B6F35171F1B0F07071F9F8FC7CEFEFE7EFEFEFEFEEEEECECECEDE9BB9,7F7F7F7FFCE0000000003F1807E080003D9FDF3E00000000017FF00000FF0000,00005C0000ED000000C010000080003E0000000001010703070F070F070F060F
130 DATA C7C6E17F0003070BFEFE1E1C7BE00000F9F1E3C73FFFFF7F575757D8F0000000,0000287EFFFFFFFFFFEFDFF7F9FCFE3F000000000000808080808000B0DC5497,FF800101010101010303030100001C1C83E571B8D8EFC0C7CECC8C050504FF3F
140 DATA 3FFFFEFEFEFE060301000000000080001E1F3F635BDBC3C7FD793B0F00000000,FCF8400000E07CF676363EBCBF7FFFE0A5ADFB8F770201000000070CC82834D4,2563EBC6D7CDDBFFFFBF9F0003060404FA7EFFF7D3F1A4EE5EFCFF7FFF3F7FFF
10 CLEAR
20 FOR I=768 TO 1151:READ A:POKE I,A:NEXT I
30 PRINT:BEEP1:A$=INPUT$(1,@)
110 DATA &HDF,&HA6,&H6F,&H0D,&HCE,&H05,&H1E,&H39,&H60,&H40,&H90,&HA0,&HA0,&H81,&HC3,&HF7,&HF7,&HCF,&HFF,&HF3,&HD3,&HF0,&H38,&H0E,&HF7,&H33,&H91,&HD3,&HFD,&HFE,&HFF,&HFF,&HF7,&HF7,&HF7,&HF7,&HCF,&H0E,&H00,&H00,&H00,&H00,&HF3,&H81,&H70,&H0E,&H08,&H00
120 DATA &H00,&H00,&HC5,&H00,&H00,&HDE,&H00,&H00,&H00,&H0C,&H01,&H00,&H00,&H08,&H00,&HE3,&HFF,&H08,&H10,&H10,&H10,&H10,&H10,&H10,&H30,&H30,&H30,&H10,&H00,&H00,&HC1,&HC1,&HF3,&HFF,&HEF,&HEF,&HEF,&HEF,&H60,&H30,&H10,&H00,&H00,&H00,&H00,&H00,&H08,&H00
130 DATA &H00,&H00,&H00,&H30,&H70,&HE7,&H8F,&H03,&HF7,&HF7,&HF3,&HF3,&HF3,&HC1,&H10,&H10,&H1C,&H06,&H02,&HE8,&HEC,&HCE,&H3E,&H7E,&H0F,&H8F,&H93,&HD2,&HD2,&HD3,&HD3,&HD3,&HD3,&HF9,&HFD,&HE3,&H00,&H00,&H00,&H00,&H10,&HF7,&H0F,&H00,&H00,&HFF,&H00,&H00
140 DATA &H00,&H00,&H00,&H00,&H10,&H10,&H70,&H30,&H70,&HF0,&H70,&HF0,&H70,&HF0,&H60,&HF0,&H38,&H5E,&H17,&H8B,&H8D,&HFE,&H0C,&H7C,&HEC,&HCC,&HC8,&H50,&H50,&H40,&HFF,&HF3,&HE1,&HF1,&HF3,&H36,&HB5,&HBD,&H3C,&H7C,&HDF,&H97,&HB3,&HF0,&H00,&H00,&H00,&H00
150 DATA &H12,&H14,&H34,&H3F,&H8F,&HE3,&HE0,&HF7,&HFF,&HBF,&H3F,&H1F,&H0F,&H2F,&H3D,&HB7,&H9A,&H4B,&HED,&HB6,&HF6,&H53,&H71,&HF1,&HB1,&HF0,&H70,&H70,&HF1,&HF9,&HF8,&H7C,&H7C,&H6C,&H1E,&HF7,&H00,&H30,&H70,&HB0,&HEF,&HEF,&HE1,&HC1,&HB7,&H0E,&H00,&H00
160 DATA &H00,&H00,&H82,&HE7,&HFF,&HFF,&HFF,&HFF,&HFF,&HFE,&HFD,&H7F,&H9F,&HCF,&HEF,&HF3,&HCF,&H8F,&H04,&H00,&H00,&H0E,&HC7,&H6F,&H67,&H63,&HE3,&HCB,&HFB,&HF7,&HFF,&H0E,&H52,&H36,&HBE,&H6C,&H7D,&HDC,&HBD,&HFF,&HFF,&HFB,&HF9,&H00,&H30,&H60,&H40,&H40
170 DATA &HFF,&H7C,&H38,&HD8,&H58,&H10,&H10,&H10,&H08,&H0C,&H0F,&H8F,&H83,&HC1,&HC1,&HC8,&HEC,&HEF,&HEF,&HE7,&HEF,&HEF,&HEF,&HEF,&HEE,&HEE,&HEC,&HEC,&HEC,&HED,&HB9,&H9B,&H9F,&H1F,&H3E,&H7C,&HF3,&HFF,&HFF,&HF7,&H75,&H75,&H75,&H8D,&H0F,&H00,&H00,&H00
180 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H08,&H08,&H08,&H08,&H08,&H00,&H0B,&HCD,&H45,&H79,&H5A,&HDA,&HBF,&HF8,&H77,&H20,&H10,&H00,&H00,&H00,&H70,&HC0,&H8C,&H82,&H43,&H4D,&HAF,&HE7,&HFF,&H7F,&H3D,&H1F,&H4A,&HEE,&HE5,&HCF,&HFF,&HF7,&HFF,&HF3,&HF7,&HFF
- 2D рисование
В "PB‑1000 Command Reference" на странице 13 в качестве примера использования плоттера приведён код, выводящий фигуры, вычисляя координаты их вершин относительно заданного центра и соединяя их отрезками.
Я адаптировал его для вывода на экране PD‑700B, подобрал масштаб, размер и координаты центров фигур.
10 CLEAR:ANGLE 0:DIM X(6),Y(6):R=15
20 FOR K=2 TO 4
30 OX=15+32*(K-2)
40 FOR I=0 TO K+1
50 X(I)=OX+R*SIN(360*I/(K+2)):Y(I)=16-R*COS(360*I/(K+2))
60 NEXT I
70 FOR I=1 TO 2+2*K
80 X(K+2)=X(0):Y(K+2)=Y(0)
90 FOR J=0 TO K+1
100 X1=ROUND(X(J),-2):Y1=ROUND (Y(J),-2)
110 X2=ROUND(X(J+1),-2):Y2=ROUND(Y(J+1),-2)
120 DRAW(X1,Y1)-(X2,Y2)
130 X(J)=X(J)+(X(J+1)-X(J))/5:Y(J)=Y(J)+(Y(J+1)-Y(J))/5
140 NEXT J:NEXT I:NEXT K
150 K$=INPUT$(1,@)
Так как виртуальный дисплей PD‑700B намного выше физического, я также написал вариант, выводящий фигуру на всю ширину. Для наглядности процесса во время вывода отображаемая область перемещается на текущую позицию, а после завершения можно перемещаться по изображению вверх/вниз клавишами "2"/"4" или "YES"/"NO".
10 CLEAR:WIDTH,4:ANGLE 0:DIM X(5),Y(5):R=47
20 FOR I=0 TO 4
30 X(I)=47+R*SIN(360*I/5):Y(I)=47-R*COS(360*I/5)
40 NEXT I
50 FOR I=1 TO 15
60 X(5)=X(0):Y(5)=Y(0)
70 FOR J=0 TO 4
80 X1=ROUND(X(J),-2):Y1=ROUND (Y(J),-2)
90 X2=ROUND(X(J+1),-2):Y2=ROUND(Y(J+1),-2)
100 L=INT(Y2/8):LOCATE 0,L:DRAW(X1,Y1)-(X2,Y2)
110 X(J)=X(J)+(X(J+1)-X(J))/5:Y(J)=Y(J)+(Y(J+1)-Y(J))/5
120 NEXT J:NEXT I:BEEP1
210 K$=INPUT$(1,@)
220 IF K$="2" OR K$=CHR$(241);IF L<10;L=L+1:IF M=1;L=L+3:M=0
230 IF K$="2" OR K$=CHR$(240);IF L>0;L=L-1:IF M=0;L=L-3:M=1
240 LOCATE 0,L:GOTO 210
- 3D рисование
Также путём вычислений можно выводить на экран проекции трёхмерных фигур. На обложках некоторых каталогов было представлено демонстрационное изображение мексиканской шляпы, выведенной на Sharp MZ‑80B. Оригинальный код нашёлся в этом посте, а тут можно увидеть адаптации под многие другие устройства.
Я также адаптировал его под экран PD‑700B, а так как при разрешении 32x96 часть деталей становится неразличимой, как и в предыдущей программе использовал для вывода виртуальный дисплей. Перемещение отображаемой области в процессе на позицию вывода и управление клавишами "2"/"4" и "YES"/"NO" здесь также реализованы аналогично.
10 CLEAR:WIDTH,4:ANGLE 0
20 DIM D(95):FOR I=0 TO 95:D(I)=100:NEXT I
30 FOR Y=-180 TO 180 STEP 9
40 FOR X=-180 TO 180 STEP 4
50 SX=47+X/4-Y/9:IF SX<0 OR SX>95;GOTO 90
60 R=SQR(X*X+Y*Y):Z=100*COS(R)-30*COS(3*R)
70 SY=25-Y/9-Z/5
80 IF D(SX)>SY;LOCATE 0,SY/8:DRAW(SX,SY):D(SX)=SY
90 NEXT X:NEXT Y
100 LOCATE 0,0:L=0:M=1
110 BEEP:BEEP1:BEEP:BEEP1:BEEP:BEEP1
210 K$=INPUT$(1,@)
220 IF K$="2" OR K$=CHR$(241);IF L<7;L=L+1:IF M=1;L=L+3:M=2
230 IF K$="8" OR K$=CHR$(240);IF L>0;L=L-1:IF M=2;L=L-3:M=1
240 LOCATE 0,L:GOTO 210
Конечно, это нельзя использовать для оценки производительности, поскольку для каждого устройства используется свой размер, плотность и учёт границ экрана. Но конкретно этот код выполняется за 17 минут и 17 секунд, из которых 36 секунд занимает постоянное вычисление для перемещения на позицию вывода. Увидеть весь процесс вывода в ускоренном режиме можно тут.
- Анимация
При имеющейся скорости вывода сделать нормальную анимацию практически невозможно. Но с виртуальным дисплеем высотой 128 пикселей можно сначала вывести 4 изображения, а затем только перемещаться по ним! Я взял изображения глаз из проекта для Arduino, выбрал 4 наиболее выразительных и обрезал под размер экрана.
Благодаря тому, что большая часть остаётся неизменной, удалось сильно уменьшить размер программы. Я записал данные только различающихся символов и при выводе перехожу по необходимым, используя список с правильной последовательностью номеров символов.
Ещё одна сложность заключалась в том, что при выводе последнего символа в строке, курсор автоматически переходит на следующую строку, и таким образом пропадает первая. Чтобы перехода не происходило, последний символ я вывожу путём записи необходимых данных в область дисплея.
10 CLEAR:WIDTH,2:DIM N(46)
20 FOR I=0 TO 46:READ A:N(I)=100+A:NEXT I
30 FOR I=0 TO 46:RESTORE N(I):READ A$:DEFKAN$(32)=A$:KPRINT "8120";:NEXT I
40 RESTORE 130:FOR I=2192 TO 2207:READ A:POKE I,A:NEXT I:FOR I=2288 TO 2303:READ A:POKE I,A:NEXT I
61 LOCATE 0,0:T=350:GOSUB 90
62 LOCATE 0,7:T=280:GOSUB 90
63 LOCATE 0,0:T=250:GOSUB 90
64 LOCATE 0,3:T=300:GOSUB 90
65 LOCATE 0,0:T=350:GOSUB 90
66 LOCATE 0,5:T=80:GOSUB 90
67 LOCATE 0,0:T=50:GOSUB 90
68 LOCATE 0,5:T=80:GOSUB 90
69 LOCATE 0,0:T=150:GOSUB 90
70 LOCATE 0,3:T=300:GOSUB 90
80 GOTO 61
90 FOR I=0 TO T:NEXT I:RETURN
100 DATA 1,2,3,4,5,6,7,8,9,10,11,12,13,14,3,4,15,6,7,16,9,10,16,12,17,18,19,20,21,22,7,8,9,10,11,12,1,23,24,4,16,25,7,26,27,10,16
101 DATA FFFFFFFFF8C000000000000000000000FFFFFFFF000000000000000000000000
102 DATA 0000000000000000000000000000000000000000000000071F3F3F3F1F070000
103 DATA 000000000000C0F8FFFFFFFFFFFFFFFF0000000000000000FFFFFFFFFFFFFFFF
104 DATA FFFFFFFFFFFFFFFFF8C0000000000000FFFFFFFFFFFFFFFF0000000000000000
105 DATA 0000000000000000000000000000000000071F3F3F3F1F070000000000000000
106 DATA 00000000000000000000C0F8FFFFFFFF000000000000000000000000FFFFFFFF
107 DATA FFFFFFFF030000000000000000000000FFFFFFFFFF7F1F070100000000000000
108 DATA 00000000000000C0F0F8F8F8F0C0000000000000000000000000000000000000
109 DATA 0000000000000003FFFFFFFFFFFFFFFF00000001071F7FFFFFFFFFFFFFFFFFFF
110 DATA FFFFFFFFFFFFFFFF0300000000000000FFFFFFFFFFFFFFFFFF7F1F0701000000
111 DATA 00C0F0F8F8F8F0C0000000000000000000000000000000000000000000000000
112 DATA 000000000000000000000003FFFFFFFF0000000000000001071F7FFFFFFFFFFF
113 DATA FFFFFFFFF8C00000000000000000E0F8FFFFFFFF000000000000000000000000
114 DATA FCFCFCF8E0000000000000000000000000000000000000000000000000000000
115 DATA F0FCFEFEFEFCF000000000000000000000000000000000000000000000000000
116 DATA 0000000000000000000000000000000000000000000000000000000000000000
117 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF0080C0C0E0E0E0F0F0F0F8F8
118 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF8F8F8F8F8F8F8FFFFFFFFFFFFFFF8F8
119 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF8F8F8F8F8F8F8F8FFFFFFFFFFFFFFFF
120 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFCF8F8F8F8F8F8F8
121 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF8FFFFFFFFFFFFFFFCFCFCF8F8F8F8F8
122 DATA FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF8F8F8F8F8F0F0F0E0E0E0C0FFFFFFFF
123 DATA 0000000000000000000000000000000000000000000000000000000000001F7F
124 DATA 000000000000C0F8FFFFFFFFFFFFFFFFFFFFFF7F1F000000FFFFFFFFFFFFFFFF
125 DATA 00000000000000000000C0F8FFFFFFFF00000F3F7F7F7F3F0F000000FFFFFFFF
126 DATA 000000000000000000000000000000C000000000000000000000000000000000
127 DATA E0E0E0C000000003FFFFFFFFFFFFFFFF00000001071F7FFFFFFFFFFFFFFFFFFF
130 DATA &H00,&H00,&H08,&H0E,&H0F,&H0F,&H0F,&H0E,&H08,&H00,&H00,&H30,&HFF,&HFF,&HFF,&HFF
131 DATA &H00,&H00,&H00,&H00,&H00,&H00,&H00,&H10,&H70,&HF1,&HF7,&HFF,&HFF,&HFF,&HFF,&HFF
Увидеть анимацию в действии можно тут.
Не исключено, что когда-нибудь, если я завершу некоторые наработки, здесь появится ещё несколько программ или игр. Ну а сейчас у меня ещё достаточно интересной информации, которой мне предстоит поделиться!







Комментарии
Отправить комментарий