Переривання
10h має у своєму складі кілька функцій для висновку інформації на екран:
AH=09h – висновок
символу з заданим атрибутом у поточній позиції курсору;
AH=0Ah – висновок
символу без атрибута в поточній позиції курсору;
AH=0Eh – висновок
символу без атрибута в поточний позици курсору в режимі “телетайп” (символи
Carriage Return (0Dh), Lint Feed (0Ah), Bell (07h), BackSpace (08h)
розглядаються як керуючі і не відображаються на екрані);
AH=13h – висновок
рядка символів з різними додатковими опціями: зі зрушенням курсору і без
зрушення, з визначенням атрибута для всього рядка, для кожного символу або без
визначення атрибута. Керуючі символи – такі ж, як і для функції AH=0Eh. Дана
функція підтримується BIOS IBM PC XT, AT.
Функція AH=09h працює
як у текстових, так і графічних режимах. Виведений символ міститься в регістр
AL, його атрибут – у регістр BL. Регістр BH задає номер активної видеостраници,
а регістр CX – число повторень для виведеного символу. У тому випадку, якщо
поточний відеорежим адаптера – графічний, значення в регістрі BL задає колір
символу. При цьому якщо біт 7 BL дорівнює 1, виконується операція що виключає АБО
кодів пикселов символу і поточного умісту відеопам'яті. Такий висновок у
графічних режимах гарантує видимість символу навіть на тлі, що збігається з кольором
символу. Крім того, спрощується “стирання” символу: для відновлення екрана
досить вивести символ з установленым в одиницю битому 7 і тим же кодом кольору
символу в інших бітах (графічні режими до 12h включно) у ту ж позицію екрана ще
раз. Докладніше про висновок символів у графічному режимі див. у 9.7.
Як
приклад використання функції AH=09h привем функцію висновку на екран вертиально
довільної ASCIIZ – рядка символів, на початок якої вказує str, із заданим
атрибутом attr. Рядок виводиться на активну сторінку відеоадаптера, починаючи з
рядка stroka і стовпця stolb. Лівий верхній кут екрана має координати (0,0).
Функція працює коректно як у текстових, так і в графічних режимах
відеоадаптера. Після висновку чергового символу рядка курсор позиционируется
звертанням до функції goto_xy() ( варіант функції, щорекомендується – L8_11.C).
функція перевіряє коректність заданих параметрів. У випадку успіху повертається
констаната OK; якщо початкова крапка для рядка задана поза екраном,
повертається константа BAD_PARAM; якщо весь рядок не уміщається на екрані,
виводиться тільки її частина і повертається константа END_OF_SCREEN. Курсор
установлюється на останньому виведенном символі рядка.
/*L9_1.C*/
#include <dos.h>
#include “screen.h”
int vert_prn(int stroka,
int stjlb, char * str, char attr)
{register char cur_page;
union REGS r;
/*Визначення поточний видеостранмцы. */
cur_page=*(char far*)MK_FP(0*40,0*62);
/*Перевірка параметрів функції спробою позиционирования
курсору. Исли повернення не дорівнює нулю, параметри неприпустимі.*/
if
(goto_xy(stroka, stolb, cur_page)==BAD_PARAM)
return
BAD_PARAM;
while(*str)
{/* Висновок
символу й атрибута в поточній позиції курсору * /
r.h.bh=cur_page; r.h.bl=attr; r.x.cx=1;
r.h.ah=0*09; r.h.al=*str++; int86(0*10, &r, &r);
stroka++; /*збільшуємо
номер рядка*/
/*
Переміщення курсору з контролем повернення. */
if
(goto_xy( stroka,stolb, cur_page )==BAD_PARAM)
return END_OF_SCREEN;
}
return
OK;
}
Функцію легко змусити
виводити рядка горизонтально: після висновку чергового символу варто нарощувати
номер рядків, а не стовпця.
Далі приводиться
приклад функції hor_prn(), що виводить рядок символів горизонтально, починаючи з
заданого рядка і стовпця з заданим атрибутом. Зміст параметрів і значень, що
повертаються функцією, такий же, як і для функції vert_prn(див.L9_1.C):
/*L9_2.C*/
#include <dos.h>
#include “screen.h”
hor_prn(int stroka, int
stjlb, char * str, char attr)
{register char cur_page;
union REGS r;
/*Визначення поточної відеосторінки. */
cur_page=*(char far*)MK_FP(0x40,0x62);
/*Перевірка параметрів на допустимість.*/
if
(goto_xy(stroka, stolb, cur_page)==BAD_PARAM)
return
BAD_PARAM;
while(*str)
{/* Висновок
символу й атрибута в поточній позиції курсору * /
r.h.bh=cur_page; r.h.bl=attr; r.x.cx=1;
r.h.ah=0x09; r.h.al=*str++; int86(0x10, &r, &r);
stolb++; /*збільшуємо
номер рядка*/
/*
Переміщення курсору з контролем повернення. */
if
(goto_xy(stroka,stolb, cur_pag )==BAD_PARAM)
return END_OF_SCREEN;
}
return
OK;
}
Корисної
для висновку рамок, заповнення областей екрана буде функція printche(), що
виводить, починаючи з рядка str і стовпця stolb, символ symb з атрибутом atr
задане число раз n. Після завершення роботи функції курсор розташовується в
позиції (str, stolb). Лівий верхній кут екрана відповідає координатам (0, 0). У
випадку успіху функція повертає константу OK. Якщо задані неприпустимі str і
stolb і у випадку, коли запитане число n символів не уміщається на екрані,
повертається константа BAD_PARAM. Для висновку використовується активна
відеосторінка адаптера.
/*L9_3.C*/
#include<dos.h>
#include“screen.h”
int prinche( int str, intstolb, char*stolb,
char atr, int n )
{ register cur_page; register max_stolb; union REGS r;
/*
Визначення поточної відеосторінки і максимального
числа
стовпців тексту для поточного режиму.*/
cur_page=*(char far*) MK_FP(0x40,0x62);
max_stolb=*(unsigned far*) MK_FP (0x40, 0x4a);
/*
Перевірка параметрів на допустимість. */
if
(goto_xy(str stolb, cur_page)==BAD_PARAM)
return
BAD_PARAM;
/*
Перевірка того, чи поміститься на екрані висновок n символів */
if
(max_stolb<(stolb+n-1))
return
BAD_PARAM;
/* Висновок
символу й атрибута задане число раз. */
r.h.ah=0x09; r.h.al=symb; r.h.bh=cur_page;
r.h.bl=atr; r.x.cx=n; int86(0x10, &r, &r);
return
OK;
}
При організації
віконного інтерфейсу часто виникає задача висновку рамки для вікна. Далі приводиться
текст Си – функції border(), що виводить через звертання до функції printche()
прямокутну рамку. Перший елемент масиву (style[0]) – задає символ лівого
верхнього кута рамки, що випливає елемент (style[1]) – символ верхньої
горизонтальної лінії, (style[2]) – символ правого верхнього кута, (style[3]) і
(style[4]) – символи лівої і правий вертикальних границь, style[5] – символ
лівого нижнього кута рамки, style[6] – символ нижньої горизонтальної лінії,
style[7] – символ правого нижнього кута. Наприклад, для того щоб одержати
подвійну рамку, варто було б описати масив style так:
char style[8]={‘\x9’, ‘\xCD’, ‘\cBB’, ‘\xBA’,
’\xBA’ ‘\x8’, ‘\xCD’, ‘\xBC’};
Атрибут символу для рамки задається значенням atr.
Функція border() виводить посередине верхнього рядка рамки заголовок для вікна
символами з атрибутом atr_title. На початок SCIIZ-рядка заголовка вказує
параметр title. Якщо він дорівнює NULL, заголовок не виводиться. Координати
лівого верхнього кута рамки задаються рядком s0 і стовпцем c0, верхнього
нижнього кута – рядком s1 і стовпцем c1. У випадку успіху функція повертає
константу OK; якщо по заданих координатах рамка не може бути побудована, повертається
константа BAD_PARAM.
/*L9_4.C*/
#include<string.h>
#include<dos.h>
#include“screen.h”
int border(int s0, intc0, int s1, int c1,
char *title,
char atr_title, char style[ ],
char atr)
{ register max_stolb; max_string, s;
max_stolb=*(char far*) MK_FP(0x40, 0x4a);
max_string=*(char far*) MK_FP(0x40, 0x84);
/*
Контроль допустимості параметрів:
чи можна вивести всю рамку на екран;
чи можна помістити у верхньому рядку
заголовок? */
if
(s0>=0&&s0<s1
&&c0>=0&&c0<c1&&s1,=max_string &&c1<max_stolb
&&
((title!=NULL &&
(c1-c0)>=strlen(title)) || title==NULL))
{ printche (s0, c0, style [0], atr,1);
printche (s0, c0+1, style [1], atr, c1-c0-1);
printche (s0, c1, style [2], atr, 1);
for(s=s0+1; s<s1; s++)
{
printche (s, c0, style [3], atr, 1);
printche (s, c1, style [4], atr,1); }
printche (s1, c0, style [5], atr,1);
printche (s1, c0+1, style [6], atr, c1-c0-1);
printche (s1, c1, style [7], atr,1);
if (title!=NULL)
hop_prn (s0, c0+(c1-c0-strlen(title))/2+1,
title, atr_title);
return OK; }
else
return
BAD_PARAM;
}
Функції vert_prn(),
hor_prn(), printche(), border() придатні як у текстових, так і в графічних
режимах роботи відеоадаптерів і мають майже максимально досяжну при
використанні ВіоSа швидкість. Можливе їхнє поліпшення складається у
використанні зовнішніх перемінних для режимів параметрів, що змінюються тільки
при переключенні, відеосистеми (максимального числа стовпців, номера поточної
відеосторінки, максимального числа рядків тексту).
![]() |
![]() |
![]() |