4.3.4 Создание специальных символов.

Error message

Notice: Undefined index: add term path in hansel_get_breadcrumbs() (line 524 of /data/sites/msdosworld.ru/www/sites/all/modules/hansel/hansel.module).

  Только  монохромный  адаптор не может выводить  символы  вида,
заданного  самим  программистом.  Цветной  адаптор  позволяет 128
символов, определяемых пользователем, PCjr - 256, а EGA - 1024 из
которых одновременно доступно 512. Для цветного адаптора ROM-BIOS
содержит  данные для разрисовки только первых 128 символов набора
ASCII (с номерами от 0 до 127). Следующие 128 символов недоступны
для Вас, пока Вы не создатите их, используя описанную здесь  тех-
нику. Отметим, что MS DOS  3.00  предоставляет  команду GRAFTABL,
которая  предоставляет требуемые данные для второй порции из  128
символов. PCjr имеет данные для второй порции из 128 символов уже
готовые. EGA имеет полные наборы символов для режимов с 200 стро-
ками и с 350 строками.
   Символы для графического адаптора и PCjr описываются с помощью
матрицы 8*8 точек. Данные для каждого символа содержатся в восьми
байтах. Каждый байт  содержит  установку  для  точек одного ряда,
начиная с верхнего ряда, причем старший бит (номер 7)  соответст-
вует самой левой точке в ряду. Когда соответствующий бит равен 1,
то точка высвечивается. Для описания символа Вы должны определить
правильные последовательности битов для восьми байтов и поместить
их в последовательные ячейки памяти.  На рис.  4-3 показано как 8
байтов описывают бубновую масть.
   Все 128  символов  вместе  требуют  1024  байта, хотя вовсе не
требуется,  чтобы были описаны все символы.   Специальный  вектор
прерывания   (постоянный   указатель   в   младших адресах памяти
[1.2.0])  указывает на адрес первого байта первого символа расши-
ренного набора, т.е. на символ номер 128. Когда в позицию символа
в видеобуфере посылается код 128, то просматриваются и  выводятся
первые восемь байт. Если номер  символа 129, то выводятся байты с
девятого по шестнадцатый, и т.д.
   Номер  этого вектора прерывания 1FH и он расположен по  адресу
0000:007C. Поместите значение  смещения  в младшее слово (сначала
младший байт), а адрес сегмента - в старшее слово (снова, сначала
младший байт).  Отметим,  что  можно  символы с большими номерами
кодов,  не  отводя памяти для символов с меньшими номерами;  надо
просто чтобы вектор указывал на некоторый  адрес, который меньше,
чем адрес начала блока, содержащего данные для описания символов.
Восьмибайтные  последовательности,   описывающие  символы ASCII с
кодами  128-255 приведены в [4.3.5].  У PCjr вектор 1FH указывает
на вторые 128 символов ASCII, а вектор  44H - на первые. Оба этих
вектора могут быть изменены, допуская полный набор 256  символов,
определяемых пользователем.
   Для EGA картина намного сложнее, но и намного гибче.  При ини-
циализации  текстового режима один из двух наборов символов  (8*8
или 8*14) копируется из ПЗУ EGA в  карту битов 2 видеобуфера. Эта
часть буфера рассматривается как разбитая на блоки, причем  стан-
дартный набор символов помещается в блок 0.  При условии, что EGA
оснащен  достаточной памятью могут быть определены еще три  блока
для описания символов.   Размер  блока  определяется числом строк
матрицы, используемой для описания символа.  Символы, описываемые
матрицей 8*8 требуют 8*256 или  2048  байт. Когда разрешены более
одного  блока  символов, то бит 3 байта атрибутов  определяет  из
какого блока будут браться данные для описания символа.


   Какой из  блоков  будет  использоваться  зависит  от установки
битов  0-3  регистра выбора карты символов, адрес порта  которого
3C5H.  Предварительно надо  послать  3 в порт 3C4H, чтобы указать
требуемый  регистр.  Биты 1-0 дают номер блока символов,  который
берется когда бит 3 байта  атрибутов равен 0, а биты 3-2 - делают
то же самое, когда бит 3 равен 1. Когда установка обоих пар битов
совпадает, то  возможность  использования  двух  наборов символов
отсутствует  и бит 3 байта атрибутов переключается  на  установку
интенсивности символа. В этом  случае используется только блок 0.
Однако никто не может помешать Вам поместить свои символы в любую
нужную Вам позицию в этом  блоке.   Если  Вы изменили стандартный
набор  символов, то Вы можете в любой момент восстановить его  из
ПЗУ.

   Высокий уровень.

   В Бейсике Вы должны позаботиться о том, чтобы данные описываю-
щие символы находились за пределами памяти, используемой програм-
мой. Если имеется много памяти, то можно поместить данные в стар-
шие адреса; если имеется опасность конфликта, то следует  исполь-
зовать команду CLEAR для  ограничения  количества памяти, которую
может использовать Бейсик.  Затем следует поместить адрес первого
байта данных в вектор прерывания. В следующем примере описывается
символ 128 как квадратная рамка.  Операторы DATA содержат  значе-
ния, описывающие символ. Они  равны  либо 255, либо 129; в первом
случае все биты равны 1, а во втором равны 1 только крайние биты.
О вычислении десятичных значений, соответствующих данным цепочкам
битов см. приложение Б.

100 '''помещаем данные, начиная с адреса &H3000
110 DATA 255, 129, 129, 129, 129, 129, 129, 255
120 DEF SEG = &H3000    'указываем начало сегмента
130 FOR N = 0 TO 7      'определяем 8 байт
140 READ Q              'читаем 1 байт
150 POKE N,Q            'помещаем его в память
160 NEXT                'и т.д.
170 '''установка вектора прерывания
180 DEF SEG = 0         'указываем на начало памяти
190 POKE 124,0          'указываем смещение
200 POKE 125,0          '
210 POKE 126,0          'указываем сегмент
220 POKE 127,&H30       '
230 '''печатаем символ
240 LOCATE 12,12: PRINT CHR$(128)  'теперь есть символ 128

   Средний уровень.

   Для цветного адаптора и PCjr используйте функцию 25H  прерыва-
ния 21H для изменения вектора  прерывания  1FH.   При входе DS:DX
должны  указывать  на первый байт блока данных.  Более  подробное
описание см. в [1.2.3]. В примере создаются два символа с номера-
ми 128 и 129.  Они являются зеркальными отображениями друг друга,
а выведенные подряд образуют небольшой прямоугольник.


;---в сегменте данных
CHARACTER_DATA   DB  11111111B, 10000000B, 10000000B, 10000000B
                 DB  10000000B, 10000000B, 10000000B, 11111111B
                 DB  11111111B, 00000001B, 00000001B, 00000001B
                 DB  00000001B, 00000001B, 00000001B, 11111111B

;---установка вектора прерывания
   PUSH DS                ;сохраняем DS
   LEA  DX,CHAR_DATA      ;смещение для данных в DX
   MOV  AX,SEG CHAR_DATA  ;сегмент для данных в DS
   MOV  DS,AX             ;
   MOV  AH,25H            ;функция установки вектора
   MOV  AL,1FH            ;номер изменяемого вектора
   INT  21H               ;установка вектора
   POP  DS                ;восстанавливаем DS

;---печать символов
   MOV  AH,2              ;номер функции
   MOV  DL,128            ;первый символ
   INT  21H               ;вывод его
   MOV  DL,129            ;второй символ
   INT  21H               ;вывод его

   Для EGA функция 11H прерывания 10H манипулирует набором симво-
лов. Эта функция может быть очень сложной, когда она используется
для создания специальных режимов  экрана, но ее основное примене-
ние достаточно простое. Имеется четыре подфункции. Когда AL равен
0, то данные, определяемые  пользователем переносятся из памяти в
специальный  блок  символов.  Когда AL равен 1 или 2,  то  наборы
данных для символов 8*14 и 8*8 соответственно копируются из ПЗУ в
блок символов.  Когда AL равен 3, то функция устанавливает назна-
чение блока в регистре выбора карты символов, как описано выше. В
последнем случае надо просто поместить соотвествующие данные в BL
и вызвать функцию.  Для  загрузки  данных  из ПЗУ поместите номер
блока  в BL и выполните функцию.  Для загрузки своих данных  надо
чтобы ES:BP указывали на них,  число передаваемых символов должно
быть  в  CX, смещение (номер символа) в блоке должно  быть в  DX,
число байтов на символ - в BH, а номер блока - в BL.  После этого
вызывайте прерывание 10H. Вот пример:

;---устанавливаем 128 пользовательских символов в блоке 0
   MOV  AX,SEG CHARACTER_DATA   ;ES:BP должны указывать на данные
   MOV  ES,AX                   ;
   MOV  BP,OFFSET CHARACTER_DATA   ;
   MOV  CX,128                  ;число символов
   MOV  DX,128                  ;начальное смещение
   MOV  BL,0                    ;номер блока
   MOV  BH,8                    ;матрица 8*8
   MOV  AL,1                    ;номер подфункции
   MOV  AH,11H                  ;номер функции
   INT  10H                     ;переносим данные


 

Вы находитесь в разделе: 

Добавить коментарий