Bibliotheque graphique mode vesa sous djgpp (version 2.0)

Description

Cette bibliotheque utilise un pointeur sur la memoire video, l'affichage est, je crois, plus rapide ! Mais elle ne gere pas le 32 bits (et certaine fonction ne marche pas avec du 24 bits). Elle est conçue pour le 16bits!

Source / Exemple :


#include "vesaV2.h"

void vesa_pixel(unsigned char *dest, unsigned long int valeur, int x, int y)
{
  int a, b;
  long int destination;

      destination = ((y*table_mode.resolution_horizontale)+x)<<1;
          dest[destination] = valeur&0xff;
          dest[destination+1] = valeur>>8;

  return;
}

void synchronise(unsigned char * buffer)
{	while (!(inportb(0x3da) & 8));
	vesa_aff_total(buffer);
}

void affiche_ligne(unsigned char* buffer, unsigned long int color,int x1, int y1, int x2, int y2)
{
	int indice;
	int dx,dy;
	int x,y;
	float m;

	if(x1 == x2)
		x2++;
	if(x1 > x2)
		indice=1;
	else
		indice=0;

	if (!indice)
	{
		dx=x2-x1;
		dy=y2-y1;
		m=(float)dy/dx;
		if((m <= 1) && (m >= -1))
		{
			for(x=0; x<dx; x++)
			{
				y=(int)(m*x+y1);
				vesa_pixel(buffer,color, x+x1, y);
			}
		}
		else
		{
			if((dx == 1) && (y2 > y1))
			{
				for(; y1 < y2; y1++)
				vesa_pixel(buffer,color, x1, y1);
			}
			else if((dx == 1) && (y2 < y1))
			{
				for(; y1 > y2; y1--)
				vesa_pixel(buffer,color, x1, y1);
			}
			else
			{
				m=(float)dx/dy;
				if(m > 0)
				{
					for(y = 0; y <= dy; y++)
					{
						x=(int)(m*y+x1);
						vesa_pixel(buffer,color, x, y+y1);
					}
				}
				else
				{
					for(y = 0; y > dy; y--)
					{
						x=(int)(m*y+x1);
						vesa_pixel(buffer,color, x, y+y1);
					}
				}
			}
		}
	}
	if (indice == 1)
	{
		dx=x1-x2;
		dy=y1-y2;
		m=(float)dy/dx;
		if((m <= 1) && (m >= -1))
		{
			for(x = 0; x < dx; x++)
			{
				y=(int)(y1-m*x);
				vesa_pixel(buffer,color, x1-x, y);
			}
		}
		else
		{
			m=(float)dx/dy;
			if(m > 0)				
			{
				for(y = 0; y < dy; y++)
				{
					x=(int)(x1-m*y);
					vesa_pixel(buffer,color, x, y1-y);							}
			}
			else
			{
				for(y = 0; y > dy; y--)
				{
					x=(int)(x1-m*y);
					vesa_pixel(buffer,color, x, y1-y);
				}
			}
		}
	}
}

void vga_mode( int mode )
{
  __dpmi_regs r;
  memset( &r, 0, sizeof( r ) );
  r.x.ax = mode;
  __dpmi_int( 0x10, &r );
  video = (unsigned char *)0xA0000 + __djgpp_conventional_base;
  if( mode == 0x13 )
  {
    vesa_support_lfb = 1;
    table_mode.resolution_horizontale = 320;
    table_mode.resolution_verticale = 200;
    table_mode.bits_par_point = 8;
  }
  return;
}

int vesa_detection()
{
  __dpmi_regs r;
  r.x.ax = 0x4F00;
  r.x.di = __tb & 0x0F;
  r.x.es = (__tb >> 4) & 0xFFFF;
  dosmemput( &table_mode, sizeof(table_vesa), __tb );
  __dpmi_int(0x10, &r);
  dosmemget(__tb, sizeof(table_vesa), &table_vesa);
  if( strncmp(table_vesa.vesa_signature,"VESA",4) != 0 )
    return 0;
  return table_vesa.version_principale;
}

void vesa_info( int mode )
{
  __dpmi_regs r;
  r.x.ax = 0x4F01;
  r.x.cx = mode;
  r.x.di = __tb & 0x0F;
  r.x.es = (__tb >> 4) & 0xFFFF;
  __dpmi_int(0x10, &r);
  dosmemget(__tb, sizeof(table_mode), &table_mode);
  return;
}

int vesa_adresse()
{
  __dpmi_meminfo mem;
  if( vesa_support_lfb == 1 )
  {
    mem.size = (unsigned long)( table_mode.resolution_horizontale * table_mode.resolution_verticale );
    mem.address = table_mode.adresse_lineaire;
    if( __dpmi_physical_address_mapping( &mem ) == -1 )
      return 0;
    video = (unsigned char *)( mem.address + __djgpp_conventional_base );
    __dpmi_free_physical_address_mapping( &mem );
  }
  else
    video = (unsigned char *)( 0xA0000 + __djgpp_conventional_base );
  return 1;
}

int vesa_mode( int mode )
{
  __dpmi_regs regs;
  regs.x.ax = 0x4F02;
  if( vesa_support_lfb )
    regs.x.bx = 0x4000+mode;
  else
    regs.x.bx = mode;
  __dpmi_int(0x10, &regs);
  if( regs.x.ax == 0x4F )
    return 1;
  else
    return 0;
}

void vesa_test_lfb()
{
  if( table_mode.attribut_du_mode & 0x80 )
    vesa_support_lfb = 1;
  else
    vesa_support_lfb = 0;
}

int vesa_initialisation( int mode )
{
  __dpmi_regs r;
  if( mode <= 0x13 )
  {
    vga_mode( mode );
    return 1;
  }
  r.x.ax = 0x0F00;
  __dpmi_int(0x10, &r);
  memset( &table_vesa, 0, sizeof( table_vesa ) );
  memset( &table_mode, 0, sizeof( table_mode ) );
  if( !( vesa_detection() ) )
    return 0;
  vesa_info( mode );
  if( ( table_mode.attribut_du_mode & 1 ) != 1 )
    return -1;
  if( ( ( table_mode.attribut_fenetre_A & 4 ) >> 2 ) == 1 )
    vesa_affwin = 0;
  else if( ( ( table_mode.attribut_fenetre_B & 4 ) >> 2 ) == 1 )
    vesa_affwin = 1;
  else
    return -2;
  vesa_test_lfb();
  if( !( vesa_adresse() ) )
    return -3;
  if( !( vesa_mode( mode ) ) )
    return -4;
  return 1;
}

void vesa_aff_zone( unsigned char *source, int destX, int destY, int sourceX, int sourceY, int copieX, int copieY, int largeur )
{
  int a, b, banque, __resx = table_mode.resolution_horizontale;
  long int destination, ptr, __winmem, __winmem2;
  __dpmi_regs r;
  switch( __resx )
  {
    case 320:
      destination = ((destY<<8)+(destY<<6)+destX);
      break;
    case 640:
      destination = ((destY<<9)+(destY<<7)+destX);
      break;
    case 800:
      destination = ((destY<<9)+(destY<<8)+(destY<<5)+destX);
      break;
    case 1024:
      destination = ((destY<<10)+destX);
      break;
    case 1280:
      destination = ((destY<<10)+(destY<<8)+destX);
      break;
    default:
      return;
  }
  switch( table_mode.bits_par_point )
  {
    case 8:
      a = 1;
      ptr = (sourceY*largeur)+sourceX;
      break;
    case 15:
    case 16:
      a = 2;
      destination = destination<<1;
      ptr = ((sourceY*largeur)+sourceX)<<1;
      copieX = copieX<<1;
      largeur = largeur<<1;
      __resx = __resx<<1;
      break;
    default:
      a = 3;
      destination += destination<<1;
      ptr = 3*((sourceY*largeur)+sourceX);
      copieX += copieX<<1;
      largeur += largeur<<1;
      __resx += __resx<<1;
      break;
  }
  if( vesa_support_lfb )
  {
    for( a=0 ; a<copieY ; a++ )
    {
      memcpy( &video[destination], &source[ptr], copieX );
      destination += __resx;
      ptr += largeur;
    }
  }
  else
  {
    __winmem = table_mode.taille_fenetre<<10;
    __winmem2 = __winmem - copieX;
    banque = destination / __winmem;
    if( vesa_banque != banque )
    {
      r.x.ax = 0x4F05;
      r.x.bx = 0x0000;
      r.x.dx = banque<<table_mode.pas_fenetre;
      r.h.bh = 0x0000;
      r.h.bl = vesa_affwin;
      __dpmi_int(0x10, &r);
      vesa_banque = banque;
    }
    destination = destination % __winmem;
    for( a=0 ; a<copieY ; a++ )
    {
      if( destination > __winmem )
      {
        destination -= __winmem;
        banque++;
        r.x.ax = 0x4F05;
        r.x.bx = 0x0000;
        r.x.dx = banque<<table_mode.pas_fenetre;
        r.h.bh = 0x0000;
        r.h.bl = vesa_affwin;
        __dpmi_int(0x10, &r);
        vesa_banque = banque;
      }
      if( destination < __winmem2 )
        memcpy( &video[destination], &source[ptr], copieX );
      else
      {
        b = __winmem - destination;
        memcpy( &video[destination], &source[ptr], b );
        banque++;
        r.x.ax = 0x4F05;
        r.x.bx = 0x0000;
        r.x.dx = banque<<table_mode.pas_fenetre;
        r.h.bh = 0x0000;
        r.h.bl = vesa_affwin;
        __dpmi_int(0x10, &r);
        vesa_banque = banque;
        memcpy( &video[0], &source[ptr+b], copieX - b );
        destination -= __winmem;
      }
      destination += __resx;
      ptr += largeur;
    }
  }
  return;
}

void vesa_aff_total( unsigned char *source )
{
  int __memb;
  long int __memt = table_mode.resolution_horizontale * table_mode.resolution_verticale;
  __dpmi_regs r;
  long int __winmem = table_mode.taille_fenetre<<10;

  switch( table_mode.bits_par_point )
  { 
    case 15:
    case 16:
      __memt = __memt << 1;
      break;
    case 8:
    case 24:
      __memt += __memt << 1;
  }

  if( vesa_support_lfb )
    memcpy( video, source, __memt );
  else
  {
    __memb=0;
    do
    {
      if( __memt >= __winmem )
      {
        r.x.ax = 0x4F05;
        r.x.dx = __memb << table_mode.pas_fenetre;
        r.h.bh = 0x00;
        r.h.bl = vesa_affwin;
//      r.x.dx = (banque*table_mode.taille_fenetre)/table_mode.pas_fenetre;      //
        __dpmi_int(0x10, &r);
        vesa_banque = __memb;
        memcpy( video, source, __winmem );
        source += __winmem;
        __memb++;
        __memt -= __winmem;
      }
      else if( __memt > 0 )
      {
        r.x.ax = 0x4F05;
        r.x.dx = __memb << table_mode.pas_fenetre;
        r.h.bh = 0x00;
        r.h.bl = vesa_affwin;
//      r.x.dx = (banque*table_mode.taille_fenetre)/table_mode.pas_fenetre;      //
        __dpmi_int(0x10, &r);
        vesa_banque = __memb;
        memcpy( video, source, __memt );
        __memb++;
        __memt=0;
      }
      else
        break;
    } while( 1 );
  }
  return;
}

void vesa_copie_opaque( unsigned char *dest, unsigned char *source, int destX, int destY, long int ptr, int copieX, int copieY, int dest_largeur, int source_largeur)
{
  int a;
  long int destination;
  switch( table_mode.bits_par_point )
  {
    case 8:
      destination = (destY*dest_largeur)+destX;
      for( a=0 ; a<copieY ; a++ )
      {
        memcpy( &dest[destination], &source[ptr], copieX );
        destination+=dest_largeur;
        ptr+=source_largeur;
      }
      break;
    case 15:
    case 16:
      destination = ((destY*dest_largeur)+destX)<<1;
      ptr = ptr<<1;
      dest_largeur = dest_largeur<<1;
      source_largeur = source_largeur<<1;
      copieX = copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        memcpy( &dest[destination], &source[ptr], copieX );
        destination+=dest_largeur;
        ptr+=source_largeur;
      }
      break;
    case 24:
      destination = 3*((destY*dest_largeur)+destX);
      ptr += ptr<<1;
      dest_largeur += dest_largeur<<1;
      source_largeur += source_largeur<<1;
      copieX += copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        memcpy( &dest[destination], &source[ptr], copieX );
        destination+=dest_largeur;
        ptr+=source_largeur;
      }
      break;
  }
  return;
}

void vesa_copie_transparence( unsigned char *dest, unsigned char *source, int destX, int destY, long int ptr, int copieX, int copieY, int dest_largeur, int source_largeur)
{
  int a, b;
  long int destination;
  switch( table_mode.bits_par_point )
  {
    case 8:
      destination = (destY*dest_largeur)+destX;
      for( a=0 ; a<copieY ; a++ )
      {
        for( b=0 ; b<copieX ; b++ )
        {
          if( source[ptr] )
            dest[destination] = source[ptr];
          ptr++;
          destination++;
        }
        destination+=dest_largeur-copieX;
        ptr+=source_largeur-copieX;
      }
      break;
    case 15:
    case 16:
      destination = ((destY*dest_largeur)+destX)<<1;
      ptr = ptr<<1;
      dest_largeur = dest_largeur<<1;
      source_largeur = source_largeur<<1;
      copieX = copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        for( b=0 ; b<copieX ; b+=2 )
        {
          if( source[ptr] || source[ptr+1] )
          {
            dest[destination] = source[ptr];
            dest[destination+1] = source[ptr+1];
          }
          ptr+=2;
          destination+=2;
        }
        destination += (dest_largeur-copieX);
        ptr += (source_largeur-copieX);
      }
      break;
    case 24:
      destination = 3*((destY*dest_largeur)+destX);
      ptr += ptr<<1;
      dest_largeur += dest_largeur<<1;
      source_largeur += source_largeur<<1;
      copieX += copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        for( b=0 ; b<copieX ; b+=3 )
        {
          if( source[ptr] || source[ptr+1] || source[ptr+2] )
          {
            dest[destination] = source[ptr];
            dest[destination+1] = source[ptr+1];
            dest[destination+2] = source[ptr+2];
          }
          ptr+=3;
          destination+=3;
        }
        destination += (dest_largeur-copieX);
        ptr += (source_largeur-copieX);
      }
      break;
  }
  return;
}

void vesa_coloration( unsigned char *dest, unsigned long int valeur, int destX, int destY, int copieX, int copieY, int largeur)
{
  int a, b;
  long int destination;
  switch( table_mode.bits_par_point )
  {
    case 8:
      destination = (destY*largeur)+destX;
      for( a=0 ; a<copieY ; a++ )
      {
        memset( &dest[destination], valeur, copieX );
        destination+=largeur;
      }
      break;
    case 15:
    case 16:
      destination = ((destY*largeur)+destX)<<1;
      largeur = largeur<<1;
      copieX = copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        for( b=0 ; b<copieX ; b+=2 )
        {
          dest[destination] = valeur&0xff;
          dest[destination+1] = valeur>>8;
          destination+=2;
        }
        destination += (largeur-copieX);
      }
      break;
    case 24:
      destination = 3*((destY*largeur)+destX);
      largeur += largeur<<1;
      copieX += copieX<<1;
      for( a=0 ; a<copieY ; a++ )
      {
        for( b=0 ; b<copieX ; b+=3 )
        {
          dest[destination] = valeur>>16;
          dest[destination+1] = valeur>>8;
          dest[destination+2] = valeur&0xff;
          destination+=3;
        }
        destination += (largeur-copieX);
      }
      break;
  }
  return;
}

unsigned long int vesa_pix( unsigned char rouge, unsigned char vert, unsigned char bleu)
{
  unsigned long int __pixf;
  switch( table_mode.bits_par_point )
  {
    case 15:
      __pixf = ( (rouge &0xF8) << 7 ) + ( (vert &0xF8) << 2 ) + ( (bleu &0xF8) >> 3 );
      break;
    case 16:
      __pixf = ( (rouge &0xF8) << 8 ) + ( (vert &0xFC) << 3 ) + ( (bleu &0xF8) >> 3 );
      break;
    case 24:
      __pixf = ( rouge << 16 ) + ( vert << 8 ) + bleu;
      break;
    default:
      __pixf=0;
      break;
  }
  return __pixf;
}

int vesa_base( unsigned int pixel, unsigned int ligne )
{
  __dpmi_regs r;
  r.x.ax = 0x4f07;
  r.h.bh = 0x00;
  r.h.bl = 0x00;
  r.x.cx = pixel;
  r.x.dx = ligne;
  __dpmi_int(0x10, &r);
  return ( r.x.ax == 0x004f );
}

int vesa_base_detect( unsigned int *pixel, unsigned int *ligne )
{
  __dpmi_regs r;
  r.x.ax = 0x4f07;
  r.h.bh = 0x00;
  r.h.bl = 0x01;
  __dpmi_int(0x10, &r);

  • pixel = r.x.cx;
  • ligne = r.x.dx;
return ( r.x.ax == 0x004f ); } int vesa_sligne( unsigned int taille ) { __dpmi_regs r; r.x.ax = 0x4f06; r.h.bl = 0x00; r.x.cx = taille; __dpmi_int(0x10, &r); return ( r.x.ax == 0x004f ); } int vesa_sligne_detect( unsigned int *lbits, unsigned int *lpixs, unsigned int *lmax ) { __dpmi_regs r; r.x.ax = 0x4f06; r.h.bl = 0x01; __dpmi_int(0x10, &r);
  • lbits = r.x.bx;
  • lpixs = r.x.cx;
  • lmax = r.x.dx;
return ( r.x.ax == 0x004f ); }

Conclusion :


Les deux fichiers principaux sont "vesav2.c" et "vesav2.h",
Ces deux sources sont tirées du web et recomposé pour etre compatible avec djgpp !
Trillian

Codes Sources

A voir également

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.