800 FPS en un PC

Después de los anteriores artículos de frames por segundo en un PC, a la hora de mostrar una imagen en pantalla, usando tecnología de los 80 y los 90, a raiz de hacerlo en un Spectrum.

El código está escrito en Visual C++ 2008 (9.0), y aprovecha las características de DirectDraw 7 en DirectX para aprovechar el hardware de la GPU en los procesos. Es extremadamente portable, pudiéndose compilar en ANSI o UNICODE, y soportando las arquitecturas x86, x64 e IA64 (Itanium).

Viene de un código original mío de hace algunos años, con algunos añadidos de última hora. No se incluye el array de bytes conteniendo el mapa de bits de la imagen, sino que se ha incluído vía recurso de Windows. Además ahora la animación utiliza la técnica de doble buffer para evitar parpadeos, lo que a la práctica implica una transferencia de información del doble, ya que el bitmap se vuelca al backbuffer (Blit), y luego el backbuffer se intercambia con la pantalla (Flip). Por supuesto, podríamos haber accedido directamente al mapa de bits de la supercicie (usando lpSurface), y transferir la información allí vía software, pero eso sería más lento.

De base, se permite ejecutar el programa, en ventana, o en pantalla completa. Generalmente en modo pantalla completa, el rendimiento es superior, pues el Flip, puede realizarse simplemente intercambiando páginas en la memoria de video.

A pesar de tener que volcar 1,2 Mb de información (19 veces más que el PC bajo DOS, y 200 veces más que el Spectrum), consigue obtener un rendimiento 814 frames por segundo, con un consumo de CPU que raramente sobrepasa el 5%. Como curiosidad, el mismo código, pero volcando vía GDI, o sea, llamando a DirectDrawCopyBitmap, que basicamente llama a la función de la API BitBlt, arrojaba unos 150 FPS.

El rendimiento de esta versión, viene limitado por el ancho de banda de la tarjeta gráfica. Así en una 6800 XT, se consiguen unos 4.200 cuadro por segundo, que encaja con la velocidad de transferencia de aproximadamente 5 Gb/s.

Verás que en el fuente, hay también bastantes funciones del tipo DirectDraw… (como DirectDrawCreateOffScreenSurface, o DirectDrawBlit) que no se llaman, están ahí, por si te resultan de utilidad.

Plataforma Tamaño (Kb.) Velocidad (FPS) Ancho de banda
Spectrum 256×192 (6 Kb) 13,5 81 Kb/s
PC DOS 16 bit 320×200 8 bits (64 Kb) 105 6 Mb/s
PC DOS 32 bit 320×200 8 bits (64 Kb) 518 33 Mb/s
Windows 32 bit 640×480 32 bits (1200 Kb) 814 953 Mb/s



Tienes disponible para descargar, los fuentes, el archivo de proyecto, y los binarios x86 y x64 aquí (560 Kb en formato RAR).. Para reducir en lo posible el tamaño del archivo, he omitido el ejecutable para IA64, aunque si lo quieres, no tienes más que pedirmelo.



3 comentarios en “800 FPS en un PC”

  1. En pantalla completa, parpadea horriblemente y saca 60 frames (quizás porque sea un monitor TFT), pero en ventana me saca 93689 frames y 7189 FPS en una 8800GTS.

  2. Digo yo, no es por ser puntilloso, pero siendo portabilidad la capacidad de portar un software a diferentes plataformas, por mucho que un código se pueda compilar en ANSI, Unicode, o Klingon, si usas las DirectX (bibliotecas que sólo existen para una única plataforma –salvando wines, cedegas, y paralels–) deja de ser portable automáticamente.

  3. Vaya RFOG, la verdad que tenía curiosidad sobre el rendimiento que iba a dar en un pepino como la 8800 GTS. Ciertamente es solo rasterizado 2D, pero da ¡casi el doble que mi 6800 XT!

    maeghith, creo que tienes algo de confusión. Si miras la definición de multiplataforma en la wikipedia, dice algo así como: "Una plataforma es una combinación de hardware y software usada para ejecutar aplicaciones; en su forma más simple consiste únicamente de un sistema operativo, una arquitectura, o una combinación de ambos. La plataforma más conocida es probablemente Microsoft Windows en una arquitectura x86". Por lo tanto, con la definición en la mano, DirectX son efectivamente multiplataforma. Personalmente voy más allá, y considero 9x, NT, y NTx64 diferentes plataformas.

Deja un comentario