Lenguajes
Web/Otros
Extra
Enlaces

Nota del Traductor: Este artículo es ya algo viejo, del 99, y a pesar de que muchas de las cosas que se explican han quedado ya obsoletas, resulta muy interesante si te gusta trabajar directamente con el hardware de tu máquina. Si estás buscando herramientas actuales para desarrollar juegos o aplicaciones que utilicen directamente la tarjeta gráfica entonces te recomiendo que busques información sobre OpenGL, DirectX, SDL o Allegro. Dicho esto, comenzamos con el tutorial:

Parte 1: Algunas cosas que deberías saber

Todos los modos SVGA que quieras usar deben ser compatibles con VESA (Video Electronics Standards Association). Esto no suele ser un problema ya que VESA tiene a nuestra disposición muchas resoluciones y modos. Este documento cubre los modos de 256 y 16 millones de colores, ya que para los modos de 15 y 16 bits es necesario saber utilizar las máscara de bits y muchas otras cosas que podemos dejar para más adelante. Además, estaremos usando interrupciones VESA. Si estás trabajando en DOS, asegúrate de tener  una BIOS VESA en tu tarjeta gráfica o un driver VESA cargado. Con windows 9x no debería haber ningún problema en una ventana de Ms-Dos. Este tutorial utiliza algo de ensamblador, pero no te preocupes, no necesitas saber ensamblador, simplemente sigue los pasos. Para este tutorial asumo que posees los siguientes conocimientos:

1. Lo que es un byte y cómo acceder a uno en tu lenguaje (¿¡Estás programando, verdad!?).
2. Algunos conocimientos sobre memoria. (Segmentación y todo eso).

Parte 2: Uso de la memoria SVGA

Como muchos de vosotros sabréis, la memoria de las tarjetas de vídeo puede ser accedida desde el segmento 0xA000-0xAFFF. Sin embargo, debes saber que no es una posición fija en sentido estricto. Debes entenderlo como una simple "ventana" o un simple canal de comunicación hacia tu tarjeta de vídeo. No te asustes todavía, ahora mismo lo explico mejor. En tu tarjeta de vídeo hay una memoria (empiezo por lo fácil), algunas tienen 128KB, otras más nuevas tienen 32MB, ... pero para nuestras necesidades entre 2MB y 4MB serán más que suficientes. Te estarás preguntando, "¿cómo accedo a la memoria de vídeo?", bien, ¡aquí es donde entra en acción el segmento 0xA000! Cuando escribas en ese segmento, los datos van directamente a tu tarjeta de vídeo. Ahora, si eres inteligente, y sé que lo eres, dirás "bien, tengo una tarjeta de 4MB ¡pero del segmento 0xA000 al 0xAFFF hay sólo 65536bytes! Sí, es cierto, porque una tarjeta de vídeo usa "bancos" para direccionar su memoria. Un "banco" es simplemente un "segmento" de memoria de tarjeta de vídeo. Si estás perdido, aquí tienes un ejemplo (estoy asumiendo una granularidad de ventana de 64k, no te preocupes si no sabes qué es). Cuando usamos el banco 0, los segmentos 0xA000 a 0xAFFF hacen referencia a los segmentos 0x0000 to 0x0FFF de la memoria de la tarjeta de vídeo, y:

Banco 1 - 0x1000 a 0x1FFF (65,536 bytes diferencia)
Banco 2 - 0x2000 a 0x2FFF (65,536 bytes diferencia)
Banco 3 - 0x3000 a 0x3FFF (65,536 bytes diferencia)

Ahora, si has notado algún patrón aquí es porque... ¡LO HAY!

Lo que hace, básicamente, cuando cambias un banco, es decirle a la tarjeta gráfica que los segmentos 0xA000 a 0xAFFF hacen referencia a distintos lugares de la memoria de la tarjeta gráfica. Con este método puedes acceder a tanta memoria como quieras. Esto es bueno ya que 800x600x16 Millones usa 1.44MB de memoria de vídeo. Seguramente dirás que esta explicación es fantástica y todo eso, pero, ¿Cómo cambio bancos? y ¿Cómo llamo a VESA? y ¿Cómo funcionan todos esos modos? Bien, calma, vamos a por ello.

Parte 3: Modos de Vídeo

Si has llegado hasta aquí, te felicito por tu perserverancia, voy a explicarte los modos de vídeo. Primero, un recordatorio para los modos de 256 colores. En cualquier modo de 256 colores hay un byte (8-bits) por cada píxel. Por lo tanto, el famoso modo VGA 0x13 (320x200x256) usa... ¡64000bytes! Este modo es fácil, porque no hay cambio de bancos, ya que todo lo que necesitas para acceder a toda la pantalla son los segmentos de 0xA000 a 0xAFFF, por supuesto, esto no es lo que buscamos. Para todos los modos de 256 colores un byte no corresponde a un color. Corresponde a un número de 0 a 255 de una tabla de colores de 18-bits. Ejemplo:

00 00 FF 0A
0F 37 37 37
37 37 37 37
37 37 37 37

Imagina que esto es un volcado hexadecimal de un modo 4x4 (eh, lo estoy poniendo fácil, ¿ok?). Obviamente, un único byte tiene un límite de 0 a 255. En este caso, el pixel 3,0 (x,y) tiene un valor de 255, o 0xFF. Lo que le está diciendo a la tarjeta de vídeo es que mire en la tabla de colores la posición 255 qué color es. Imaginemos que esta posición en la tabla tiene un valor de 00 3F 00 (RGB). Así que, en el punto 3,0 la tarjeta de vídeo muestra un punto verde muy brillante. Sé que para muchos de vosotros esto es bien sabido, pero lo que vendrá ahora no lo será si estás leyendo esto por el modo SVGA. Como dije antes, estoy descartando los modos de 15 y 16 bits. Si te gustaría leer sobre éstos lee "Master Class Assembly" o similar. Bien, sigamos con la materia. Para los modos de 24 bits, 16,7 millones de colores, cada pixel es direccionado con TRES bytes. Ahora, esta parte es sorprendentemente fácil. Lo que hace la tarjeta de vídeo es, por cada píxel, coger 3 bytes de la memoria (vale, lo suponías). ¡El valors RGB! NOTA: En algunas tarjetas de vídeo podría estar en orden BGR. Así que, para la dirección de los bytes de los píxels, he aquí una fórmula:

Dirección = Y*BytesPorLínea + X*3

BytesPorLínea es fácil de averiguar. Digamos que estás usando 320x200x16M. Para cada píxel hay 3 bytes y en cada LÍNEA de la pantalla hay 320 píxels, así que, 320*3 = 960bytes por línea. (Excepto si la tarjeta es no-lineal, entonces es relativo a la tarjeta). Ahora, esto es sorprendentemente fácil, pero hay un problema. Cada banco es de 65536 bytes PERO eso NO QUIERE decir que todos los píxels van a caber en un banco. 65536/3 = 21845.333... Hay que odiar cuando ESO pasa. Así que, el píxel número 21845 siempre tendrá uno de sus 3 bytes en el primer banco y los otros dos estarán empezando en el segundo banco. Básicamente, lo que quiero decir es que no puedes usar simplemente esa fórmula. Busca por "píxel cross-overs". Ahora la parte divertida. Los comandos para usar todos estos conocimientos.

Parte 4: Juntándolo todo

Para este ejemplo voy a usar el modo 320x200x16M. Para acceder a VESA en QuickBasic necesitas usar el comando CALL INTERRUPT. Para todos aquellos que no estén familiarizados con este comando, aseguraos de que tenéis cargada la biblioteca qb.lib en qb4.5 o qbx.lib en qb7.1. También, utilizad ‘$INCLUDE : ‘QB.BI’ en el comenzamiento del programa. Para ejecutar qb7.1 y hacer un programa que permita llamar a interrupciones deberías hacerlo de esta manera:

qbx /L:qbx.lib

Y en la ventana que aparece a continuación escribe:

'$INCLUDE : 'QB.BI'
DIM [SHARED] regs AS RegType

No, no estoy asumiendo que seas idiota. La mayoría de gente no usa interrupciones.

Sigamos:

Para cambiar la resolución, escribe:

regs.AX = &h4F02
regs.BX = &hdesired mode (For a listing of the modes, see the Reference section)
CALL INTERRUPT (16, regs, regs)

To change the active bank, type:

regs.AX = &h4F05
regs.BX = 0
regs.DX = bank number (starts at 0)
CALL INTERRUPT (16, regs, regs)

Ahora, para escribir píxels, simplemente usa la fórmula y en el caso de cross-overs te sugiero lo siguiente:

- Haz una lista de todos los píxels que están cruzados entre bancos.
- Cuando tu programa detecte estos píxels especiales haz una rutina especial para cada uno con SELECT CASE o algo similar.

O (método avanzado):

- Reserva una larga porción de memoria EMS o XMS.
- Escribe tus píxels ahí.
- Y durante el redibujado vertical vuelca todo esto en la memoria de vídeo, cambiando bancos cuando sea necesario.

Eso es todo.  Diviértete, haz juegos y no seas lamer, ¡no robes código!

Parte 5: Referencia

Modos de vídeo (en hexadecimal):

Número Resolución
100 640x400x256
101 640x480x256
102(6A) 800x600x16
103 800x600x256
104 1024x768x16
105 1024x768x256
106 1280x1024x16
107 1280x1024x256
109 132x25x16 (texto)
10A 132x43x16 (texto)
10B 132x50x16 (texto)
10C 132x60x16 (texto)
10F 320x200x16 (texto)
112 640x480x16M



Redactado por Joshua Weaver, traducido por Nenillo.

Inicio | JavaScript necesario para este enlace

Noticias en RSS2 XHTML Vlido CSS Vlido