Example #1
0
void gld_BindTexture(GLTexture *gltexture, unsigned int flags)
{
  const rpatch_t *patch;
  unsigned char *buffer;
  int w, h;

  if (!gltexture || gltexture->textype != GLDT_TEXTURE)
  {
    qglBindTexture(GL_TEXTURE_2D, 0);
    last_glTexID = NULL;
    return;
  }

#ifdef HAVE_LIBSDL_IMAGE
  if (gld_LoadHiresTex(gltexture, CR_DEFAULT))
  {
    gld_SetTexClamp(gltexture, flags);
    last_glTexID = gltexture->texid_p;
    return;
  }
#endif

  gld_GetTextureTexID(gltexture, CR_DEFAULT);

  if (last_glTexID == gltexture->texid_p)
  {
    gld_SetTexClamp(gltexture, flags);
    return;
  }

  last_glTexID = gltexture->texid_p;

  if (*gltexture->texid_p != 0)
  {
    qglBindTexture(GL_TEXTURE_2D, *gltexture->texid_p);
    gld_SetTexClamp(gltexture, flags);
    return;
  }

  buffer=(unsigned char*)Z_Malloc(gltexture->buffer_size,PU_STATIC,0);
  if (!(gltexture->flags & GLTEXTURE_MIPMAP) && gl_paletted_texture)
    memset(buffer,transparent_pal_index,gltexture->buffer_size);
  else
    memset(buffer,0,gltexture->buffer_size);
  patch=R_CacheTextureCompositePatchNum(gltexture->index);
  gld_AddPatchToTexture(gltexture, buffer, patch, 0, 0,
                        CR_DEFAULT, !(gltexture->flags & GLTEXTURE_MIPMAP) && gl_paletted_texture);
  R_UnlockTextureCompositePatchNum(gltexture->index);
  if (*gltexture->texid_p == 0)
    qglGenTextures(1, gltexture->texid_p);
  qglBindTexture(GL_TEXTURE_2D, *gltexture->texid_p);
  
  if (gltexture->flags & GLTEXTURE_HASHOLES)
  {
    SmoothEdges(buffer, gltexture->buffer_width, gltexture->buffer_height);
  }

  buffer = gld_HQResize(gltexture, buffer, gltexture->buffer_width, gltexture->buffer_height, &w, &h);

  gld_BuildTexture(gltexture, buffer, false, w, h);

  gld_SetTexClamp(gltexture, flags);
}
Example #2
0
void R_RenderMaskedSegRange(drawseg_t *ds, int x1, int x2)
{
  int      texnum;
  sector_t tempsec;      // killough 4/13/98
  const rpatch_t *patch;
  R_DrawColumn_f colfunc;
  draw_column_vars_t dcvars;
  angle_t angle;

  R_SetDefaultDrawColumnVars(&dcvars);

  // Calculate light table.
  // Use different light tables
  //   for horizontal / vertical / diagonal. Diagonal?

  curline = ds->curline;  // OPTIMIZE: get rid of LIGHTSEGSHIFT globally

  // killough 4/11/98: draw translucent 2s normal textures

  colfunc = R_GetDrawColumnFunc(RDC_PIPELINE_STANDARD, drawvars.filterwall, drawvars.filterz);
  if (curline->linedef->tranlump >= 0 && general_translucency)
    {
      colfunc = R_GetDrawColumnFunc(RDC_PIPELINE_TRANSLUCENT, drawvars.filterwall, drawvars.filterz);
      tranmap = main_tranmap;
      if (curline->linedef->tranlump > 0)
        tranmap = W_CacheLumpNum(curline->linedef->tranlump-1);
    }
  // killough 4/11/98: end translucent 2s normal code

  frontsector = curline->frontsector;
  backsector = curline->backsector;

  // cph 2001/11/25 - middle textures did not animate in v1.2
  texnum = curline->sidedef->midtexture;
  if (!comp[comp_maskedanim])
    texnum = texturetranslation[texnum];

  // killough 4/13/98: get correct lightlevel for 2s normal textures
  rw_lightlevel = R_FakeFlat(frontsector, &tempsec, NULL, NULL, false) ->lightlevel;
  walllights = GetLightTable(rw_lightlevel);
  walllightsnext = GetLightTable(rw_lightlevel + 1);

  maskedtexturecol = ds->maskedtexturecol;

  rw_scalestep = ds->scalestep;
  spryscale = ds->scale1 + (x1 - ds->x1)*rw_scalestep;
  mfloorclip = ds->sprbottomclip;
  mceilingclip = ds->sprtopclip;

  // find positioning
  if (curline->linedef->flags & ML_DONTPEGBOTTOM)
    {
      dcvars.texturemid = frontsector->floorheight > backsector->floorheight
        ? frontsector->floorheight : backsector->floorheight;
      dcvars.texturemid = dcvars.texturemid + textureheight[texnum] - viewz;
    }
  else
    {
      dcvars.texturemid =frontsector->ceilingheight<backsector->ceilingheight
        ? frontsector->ceilingheight : backsector->ceilingheight;
      dcvars.texturemid = dcvars.texturemid - viewz;
    }

  dcvars.texturemid += curline->sidedef->rowoffset;

  if (fixedcolormap) {
    dcvars.colormap = fixedcolormap;
    dcvars.nextcolormap = dcvars.colormap; // for filtering -- POPE
  }

  patch = R_CacheTextureCompositePatchNum(texnum);

  // draw the columns
  for (dcvars.x = x1 ; dcvars.x <= x2 ; dcvars.x++, spryscale += rw_scalestep)
    if (maskedtexturecol[dcvars.x] != INT_MAX) // dropoff overflow
      {
        // calculate texture offset - POPE
        angle = (ds->rw_centerangle + xtoviewangle[dcvars.x]) >> ANGLETOFINESHIFT;
        dcvars.texu = ds->rw_offset - FixedMul(finetangent[angle], ds->rw_distance);
        if (drawvars.filterwall == RDRAW_FILTER_LINEAR)
          dcvars.texu -= (FRACUNIT>>1);

        if (!fixedcolormap)
          dcvars.z = spryscale; // for filtering -- POPE

        if (!fixedcolormap)
        {
          int index = ((spryscale * 160 / wide_centerx) >> LIGHTSCALESHIFT);
          if (index >= MAXLIGHTSCALE)
            index = MAXLIGHTSCALE - 1;

          dcvars.colormap = walllights[index];
          dcvars.nextcolormap = walllightsnext[index];
        }
Example #3
0
File: r_data.c Project: AlexMax/d2k
static void R_InitTextures (void)
{
  const maptexture_t *mtexture;
  texture_t    *texture;
  const mappatch_t   *mpatch;
  texpatch_t   *patch;
  int  i, j;
  int         maptex_lump[2] = {-1, -1};
  const int  *maptex;
  const int  *maptex1, *maptex2;
  char name[9];
  int names_lump; // cph - new wad lump handling
  const char *names; // cph -
  const char *name_p;// const*'s
  int  *patchlookup;
  int  nummappatches;
  int  offset;
  int  maxoff, maxoff2;
  int  numtextures1, numtextures2;
  const int *directory;
  int  errors = 0;

  // Load the patch names from pnames.lmp.
  name[8] = 0;
  names = W_CacheLumpNum(names_lump = W_GetNumForName("PNAMES"));
  nummappatches = LittleLong(*((const int *)names));
  name_p = names+4;
  patchlookup = malloc(nummappatches*sizeof(*patchlookup));  // killough

  for (i=0 ; i<nummappatches ; i++)
    {
      strncpy (name,name_p+i*8, 8);
      patchlookup[i] = W_CheckNumForName(name);
      if (patchlookup[i] == -1)
        {
          // killough 4/17/98:
          // Some wads use sprites as wall patches, so repeat check and
          // look for sprites this time, but only if there were no wall
          // patches found. This is the same as allowing for both, except
          // that wall patches always win over sprites, even when they
          // appear first in a wad. This is a kludgy solution to the wad
          // lump namespace problem.

          patchlookup[i] = (W_CheckNumForName)(name, ns_sprites);

          if (patchlookup[i] == -1 && devparm)
            //jff 8/3/98 use logical output routine
            lprintf(LO_WARN,"\nWarning: patch %.8s, index %d does not exist",name,i);
        }
    }
  W_UnlockLumpNum(names_lump); // cph - release the lump

  // Load the map texture definitions from textures.lmp.
  // The data is contained in one or two lumps,
  //  TEXTURE1 for shareware, plus TEXTURE2 for commercial.

  maptex = maptex1 = W_CacheLumpNum(maptex_lump[0] = W_GetNumForName("TEXTURE1"));
  numtextures1 = LittleLong(*maptex);
  maxoff = W_LumpLength(maptex_lump[0]);
  directory = maptex+1;

  if (W_CheckNumForName("TEXTURE2") != -1)
    {
      maptex2 = W_CacheLumpNum(maptex_lump[1] = W_GetNumForName("TEXTURE2"));
      numtextures2 = LittleLong(*maptex2);
      maxoff2 = W_LumpLength(maptex_lump[1]);
    }
  else
    {
      maptex2 = NULL;
      numtextures2 = 0;
      maxoff2 = 0;
    }
  numtextures = numtextures1 + numtextures2;

  // killough 4/9/98: make column offsets 32-bit;
  // clean up malloc-ing to use sizeof

  textures = Z_Malloc(numtextures*sizeof*textures, PU_STATIC, 0);
  textureheight = Z_Malloc(numtextures*sizeof*textureheight, PU_STATIC, 0);

  for (i=0 ; i<numtextures ; i++, directory++)
    {
      if (i == numtextures1)
        {
          // Start looking in second texture file.
          maptex = maptex2;
          maxoff = maxoff2;
          directory = maptex+1;
        }

      offset = LittleLong(*directory);

      if (offset > maxoff)
        I_Error("R_InitTextures: Bad texture directory");

      mtexture = (const maptexture_t *) ( (const byte *)maptex + offset);

      texture = textures[i] =
        Z_Malloc(sizeof(texture_t) +
                 sizeof(texpatch_t)*(LittleShort(mtexture->patchcount)-1),
                 PU_STATIC, 0);

      texture->width = LittleShort(mtexture->width);
      texture->height = LittleShort(mtexture->height);
      texture->patchcount = LittleShort(mtexture->patchcount);

        /* Mattias EngdegÄrd emailed me of the following explenation of
         * why memcpy doesnt work on some systems:
         * "I suppose it is the mad unaligned allocation
         * going on (and which gcc in some way manages to cope with
         * through the __attribute__ ((packed))), and which it forgets
         * when optimizing memcpy (to a single word move) since it appears
         * to be aligned. Technically a gcc bug, but I can't blame it when
         * it's stressed with that amount of
         * non-standard nonsense."
   * So in short the unaligned struct confuses gcc's optimizer so
   * i took the memcpy out alltogether to avoid future problems-Jess
         */
      /* The above was #ifndef SPARC, but i got a mail from
       * Putera Joseph F NPRI <*****@*****.**> containing:
       *   I had to use the memcpy function on a sparc machine.  The
       *   other one would give me a core dump.
       * cph - I find it hard to believe that sparc memcpy is broken,
       * but I don't believe the pointers to memcpy have to be aligned
       * either. Use fast memcpy on other machines anyway.
       */
/*
  proff - I took this out, because Oli Kraus ([email protected]) told
  me the memcpy produced a buserror. Since this function isn't time-
  critical I'm using the for loop now.
*/
/*
#ifndef GCC
      memcpy(texture->name, mtexture->name, sizeof(texture->name));
#else
*/
      {
        size_t j;
        for(j=0;j<sizeof(texture->name);j++)
          texture->name[j]=mtexture->name[j];
      }
/* #endif */

      mpatch = mtexture->patches;
      patch = texture->patches;

      for (j=0 ; j<texture->patchcount ; j++, mpatch++, patch++)
        {
          patch->originx = LittleShort(mpatch->originx);
          patch->originy = LittleShort(mpatch->originy);
          patch->patch = patchlookup[LittleShort(mpatch->patch)];
          if (patch->patch == -1)
            {
              //jff 8/3/98 use logical output routine
              lprintf(LO_ERROR,"\nR_InitTextures: Missing patch %d in texture %.8s",
                     LittleShort(mpatch->patch), texture->name); // killough 4/17/98
              ++errors;
            }
        }

      for (j=1; j*2 <= texture->width; j<<=1)
        ;
      texture->widthmask = j-1;
      textureheight[i] = texture->height<<FRACBITS;
    }

  free(patchlookup);         // killough

  for (i=0; i<2; i++) // cph - release the TEXTUREx lumps
    if (maptex_lump[i] != -1)
      W_UnlockLumpNum(maptex_lump[i]);

  if (errors)
  {
    const lumpinfo_t* info = W_GetLumpInfoByNum(names_lump);
    wadfile_info_t *wf = M_CBufGet(&resource_files_buf, info->wadfile);

    if (wf == NULL) {
      I_Error(
        "R_InitTextures: Bad wadfile for %s (%d)\n", info->name, info->wadfile
      );
    }

    lprintf(LO_INFO,
      "\nR_InitTextures: The file %s seems to be incompatible with \"%s\".\n",
      wf->name,
      (doomverstr ? doomverstr : "DOOM"));
    I_Error("R_InitTextures: %d errors", errors);
  }

  // Precalculate whatever possible.
  if (devparm) // cph - If in development mode, generate now so all errors are found at once
  {
    R_InitPatches(); //e6y
    for (i=0 ; i<numtextures ; i++)
    {
      // proff - This is for the new renderer now
      R_CacheTextureCompositePatchNum(i);
      R_UnlockTextureCompositePatchNum(i);
    }
  }

  if (errors)
    I_Error("R_InitTextures: %d errors", errors);

  // Create translation table for global animation.
  // killough 4/9/98: make column offsets 32-bit;
  // clean up malloc-ing to use sizeof

  texturetranslation =
    Z_Malloc((numtextures+1)*sizeof*texturetranslation, PU_STATIC, 0);

  for (i=0 ; i<numtextures ; i++)
    texturetranslation[i] = i;

  // killough 1/31/98: Initialize texture hash table
  for (i = 0; i<numtextures; i++)
    textures[i]->index = -1;
  while (--i >= 0)
    {
      int j = W_LumpNameHash(textures[i]->name) % (unsigned) numtextures;
      textures[i]->next = textures[j]->index;   // Prepend to chain
      textures[j]->index = i;
    }
}
Example #4
0
//-----------------------------------------------------------------------------
//
// R_DrawPlanes
// At the end of each frame.
//
void R_DrawPlanes(void)
{
    int i;
    visplane_t *pl;

#ifdef RANGECHECK
    if (ds_p > &drawsegs[MAXDRAWSEGS])
        I_Error ("R_DrawPlanes: drawsegs overflow (%i)",
                 ds_p - drawsegs);

    if (lastvisplane > &visplanes[MAXVISPLANES])
        I_Error ("R_DrawPlanes: visplane overflow (%i)",
                 lastvisplane - visplanes);

    if (lastopening > &openings[MAXOPENINGS])
        I_Error ("R_DrawPlanes: opening overflow (%i)",
                 lastopening - openings);
#endif

    if (showrplanestats)
    {
#ifdef __riscos
        extern void _kernel_oswrch (int);
        _kernel_oswrch (31);
        _kernel_oswrch (0);
        _kernel_oswrch (0);
#endif
        printf ("Drawsegs = %u/%u, Visplanes = %u/%u, Openings = %u/%u\n",
                ds_p - drawsegs, MAXDRAWSEGS,
                lastvisplane - visplanes, MAXVISPLANES,
                lastopening - openings, MAXOPENINGS);
    }

    for (pl = visplanes ; pl < lastvisplane ; pl++)
    {
        if (pl->minx <= pl->maxx)
        {
            int picnum = pl->picnum;

            // sky flat
            if (picnum == skyflatnum || (picnum & PL_SKYFLAT))
            {
                int	 x;
                int	 texture;
                int	 offset;
                angle_t  an, flip;
                rpatch_t *tex_patch;

                // killough 10/98: allow skies to come from sidedefs.
                // Allows scrolling and/or animated skies, as well as
                // arbitrary multiple skies per level without having
                // to use info lumps.
                an = viewangle;

                if (picnum & PL_SKYFLAT)
                {
                    // Sky Linedef
                    const line_t *l = &lines[picnum & ~PL_SKYFLAT];

                    // Sky transferred from first sidedef
                    const side_t *s = *l->sidenum + sides;

                    // Texture comes from upper texture of reference sidedef
                    texture = texturetranslation[s->toptexture];

                    // Horizontal offset is turned into an angle offset,
                    // to allow sky rotation as well as careful positioning.
                    // However, the offset is scaled very small, so that it
                    // allows a long-period of sky rotation.
                    an += s->textureoffset;

                    // Vertical offset allows careful sky positioning.
                    dc_texturemid = s->rowoffset - 28 * FRACUNIT;

                    // We sometimes flip the picture horizontally.
                    //
                    // DOOM always flipped the picture, so we make it optional,
                    // to make it easier to use the new feature, while to still
                    // allow old sky textures to be used.
                    flip = l->special==272 ? 0u : ~0u;
                }
                else	// Normal DOOM sky, only one allowed per level
                {
                    dc_texturemid = skytexturemid;	// Default y-offset
                    texture = skytexture;			// Default texture
                    flip = 0;				// DOOM flips it
                }

                // Sky is always drawn full bright,
                //  i.e. colormaps[0] is used.
                // Because of this hack, sky is not affected
                //  by INVUL inverse mapping.
                dc_colormap = (fixedcolormap ? fixedcolormap : colormaps);

                dc_ylim = textureheight[texture];
                dc_iscale = skyiscale;
                tex_patch = R_CacheTextureCompositePatchNum (texture);
                offset = skycolumnoffset >> FRACBITS;

                for (x = pl->minx; x <= pl->maxx; x++)
                {
                    dc_yl = pl->top[x+1];
                    dc_yh = pl->bottom[x+1];

                    if (dc_yl <= dc_yh)
                    {
                        dc_x = x;
                        dc_source = R_GetTextureColumn(tex_patch, (((an + xtoviewangle[x]) ^ flip)
                                                       >> ANGLETOSKYSHIFT) + offset);
                        dc_texturefrac = R_CalcFrac ();
                        colfunc();
                    }
                }
                R_UnlockTextureCompositePatchNum (texture);
            }
Example #5
0
void gld_BindTexture(GLTexture *gltexture)
{
  const rpatch_t *patch;
  int i;
  unsigned char *buffer;

  if (gltexture==last_gltexture)
    return;
  last_gltexture=gltexture;
  if (!gltexture) {
    glBindTexture(GL_TEXTURE_2D, 0);
    last_gltexture = NULL;
    last_cm = -1;
    return;
  }
  if (gltexture->textype!=GLDT_TEXTURE)
  {
    glBindTexture(GL_TEXTURE_2D, 0);
    last_gltexture = NULL;
    last_cm = -1;
    return;
  }
  if (gltexture->glTexID[CR_DEFAULT]!=0)
  {
    glBindTexture(GL_TEXTURE_2D, gltexture->glTexID[CR_DEFAULT]);
    glGetTexParameteriv(GL_TEXTURE_2D,GL_TEXTURE_RESIDENT,&i);
#ifdef _DEBUG
    if (i!=GL_TRUE)
      lprintf(LO_INFO, "glGetTexParam: %i\n", i);
#endif
    if (i==GL_TRUE)
      return;
  }
  buffer=(unsigned char*)Z_Malloc(gltexture->buffer_size,PU_STATIC,0);
  if (!(gltexture->mipmap & use_mipmapping) & gl_paletted_texture)
    memset(buffer,transparent_pal_index,gltexture->buffer_size);
  else
    memset(buffer,0,gltexture->buffer_size);
  patch=R_CacheTextureCompositePatchNum(gltexture->index);
  gld_AddPatchToTexture(gltexture, buffer, patch,
                        0, 0,
                        CR_DEFAULT, !(gltexture->mipmap & use_mipmapping) & gl_paletted_texture);
  R_UnlockTextureCompositePatchNum(gltexture->index);

  if (gltexture->glTexID[CR_DEFAULT]==0)
    glGenTextures(1,&gltexture->glTexID[CR_DEFAULT]);

  glBindTexture(GL_TEXTURE_2D, gltexture->glTexID[CR_DEFAULT]);
#ifdef USE_GLU_MIPMAP
  if (gltexture->mipmap & use_mipmapping)
  {
    gluBuild2DMipmaps(GL_TEXTURE_2D, gl_tex_format,
                      gltexture->buffer_width, gltexture->buffer_height,
                      GL_RGBA, GL_UNSIGNED_BYTE, buffer);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, gl_tex_filter);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, gl_mipmap_filter);
    if (gl_texture_filter_anisotropic)
      glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, 2.0);
  }
  else
#endif /* USE_GLU_MIPMAP */
  {
#ifdef USE_GLU_IMAGESCALE
    if ((gltexture->buffer_width!=gltexture->tex_width) ||
        (gltexture->buffer_height!=gltexture->tex_height)
       )
    {
      unsigned char *scaledbuffer;

      scaledbuffer=(unsigned char*)Z_Malloc(gltexture->tex_width*gltexture->tex_height*4,PU_STATIC,0);
      if (scaledbuffer)
      {
        gluScaleImage(GL_RGBA,
                      gltexture->buffer_width, gltexture->buffer_height,
                      GL_UNSIGNED_BYTE,buffer,
                      gltexture->tex_width, gltexture->tex_height,
                      GL_UNSIGNED_BYTE,scaledbuffer);
        Z_Free(buffer);
        buffer=scaledbuffer;
        glTexImage2D( GL_TEXTURE_2D, 0, gl_tex_format,
                      gltexture->tex_width, gltexture->tex_height,
                      0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
      }
    }
    else
#endif /* USE_GLU_IMAGESCALE */
    {
      if (gl_paletted_texture) {
		I_Error("Paletted textures not supported");
		/*
        gld_SetTexturePalette(GL_TEXTURE_2D);
        glTexImage2D( GL_TEXTURE_2D, 0, GL_COLOR_INDEX8_EXT,
                      gltexture->buffer_width, gltexture->buffer_height,
                      0, GL_COLOR_INDEX, GL_UNSIGNED_BYTE, buffer); */
      } else {
        glTexImage2D( GL_TEXTURE_2D, 0, gl_tex_format,
                      gltexture->buffer_width, gltexture->buffer_height,
                      0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
      }
    }
	// Vladimir (i) -> (x)
    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, gl_tex_filter);
    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, gl_tex_filter);
  }
  Z_Free(buffer);
}