Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include "emu.h"
- #include "includes/n64.h"
- #include "video/n64.h"
- namespace N64
- {
- namespace RDP
- {
- #define RELATIVE(x, y) ((((x) >> 3) - (y)) << 3) | (x & 7);
- void TexturePipe::SetMachine(running_machine &machine)
- {
- _n64_state *state = machine.driver_data<_n64_state>();
- m_machine = &machine;
- m_rdp = &state->m_rdp;
- m_other_modes = m_rdp->GetOtherModes();
- m_misc_state = m_rdp->GetMiscState();
- }
- void TexturePipe::Mask(INT32* S, INT32* T, INT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- if (tile[num].mask_s)
- {
- INT32 wrap = *S >> (tile[num].mask_s > 10 ? 10 : tile[num].mask_s);
- wrap &= 1;
- if (tile[num].ms && wrap)
- {
- *S = (~(*S));
- }
- *S &= m_maskbits_table[tile[num].mask_s];
- }
- if (tile[num].mask_t)
- {
- INT32 wrap = *T >> (tile[num].mask_t > 10 ? 10 : tile[num].mask_t);
- wrap &= 1;
- if (tile[num].mt && wrap)
- {
- *T = (~(*T));
- }
- *T &= m_maskbits_table[tile[num].mask_t];
- }
- }
- void TexturePipe::MaskCoupled(INT32* S, INT32* S1, INT32* T, INT32* T1, INT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- if (tile[num].mask_s)
- {
- INT32 maskbits_s = m_maskbits_table[tile[num].mask_s];
- if (tile[num].ms)
- {
- INT32 swrapthreshold = tile[num].mask_s > 10 ? 10 : tile[num].mask_s;
- INT32 wrap = (*S >> swrapthreshold) & 1;
- INT32 wrap1 = (*S1 >> swrapthreshold) & 1;
- if (wrap)
- {
- *S = (~(*S));
- }
- if (wrap1)
- {
- *S1 = (~(*S1));
- }
- }
- *S &= maskbits_s;
- *S1 &= maskbits_s;
- }
- if (tile[num].mask_t)
- {
- INT32 maskbits_t = m_maskbits_table[tile[num].mask_t];
- if (tile[num].mt)
- {
- INT32 twrapthreshold = tile[num].mask_t > 10 ? 10 : tile[num].mask_t;
- INT32 wrap = (*T >> twrapthreshold) & 1;
- INT32 wrap1 = (*T1 >> twrapthreshold) & 1;
- if (wrap)
- {
- *T = (~(*T));
- }
- if (wrap1)
- {
- *T1 = (~(*T1));
- }
- }
- *T &= maskbits_t;
- *T1 &= maskbits_t;
- }
- }
- void TexturePipe::ShiftCycle(INT32* S, INT32* T, INT32* maxs, INT32* maxt, UINT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- *S = SIGN16(*S);
- *T = SIGN16(*T);
- if (tile[num].shift_s < 11)
- {
- *S >>= tile[num].shift_s;
- }
- else
- {
- *S <<= (16 - tile[num].shift_s);
- }
- *S = SIGN16(*S);
- if (tile[num].shift_t < 11)
- {
- *T >>= tile[num].shift_t;
- }
- else
- {
- *T <<= (16 - tile[num].shift_t);
- }
- *T = SIGN16(*T);
- *maxs = ((*S >> 3) >= tile[num].sh);
- *maxt = ((*T >> 3) >= tile[num].th);
- }
- void TexturePipe::ShiftCopy(INT32* S, INT32* T, UINT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- *S = SIGN16(*S);
- *T = SIGN16(*T);
- if (tile[num].shift_s < 11)//?-? tcu_tile
- {
- *S >>= tile[num].shift_s;
- }
- else
- {
- *S <<= (16 - tile[num].shift_s);
- }
- *S = SIGN16(*S);
- if (tile[num].shift_t < 11)
- {
- *T >>= tile[num].shift_t;
- }
- else
- {
- *T <<= (16 - tile[num].shift_t);
- }
- *T = SIGN16(*T);
- }
- void TexturePipe::ClampCycle(INT32* S, INT32* T, INT32* SFRAC, INT32* TFRAC, INT32 maxs, INT32 maxt, INT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- int dos = tile[num].cs || !tile[num].mask_s;
- int dot = tile[num].ct || !tile[num].mask_t;
- if (dos)
- {
- if (*S & 0x10000)
- {
- *S = 0;
- *SFRAC = 0;
- }
- else if (maxs)
- {
- *S = m_clamp_s_diff[num];
- *SFRAC = 0;
- }
- else
- {
- *S = (SIGN17(*S) >> 5) & 0x1fff;
- }
- }
- else
- {
- *S = (SIGN17(*S) >> 5) & 0x1fff;
- }
- if (dot)
- {
- if (*T & 0x10000)
- {
- *T = 0;
- *TFRAC = 0;
- }
- else if (maxt)
- {
- *T = m_clamp_t_diff[num];
- *TFRAC = 0;
- }
- else
- {
- *T = (SIGN17(*T) >> 5) & 0x1fff;
- }
- }
- else
- {
- *T = (SIGN17(*T) >> 5) & 0x1fff;
- }
- }
- void TexturePipe::ClampCycleLight(INT32* S, INT32* T, bool maxs, bool maxt, INT32 num)
- {
- Tile* tile = m_rdp->GetTiles();
- int dos = tile[num].cs || !tile[num].mask_s;
- int dot = tile[num].ct || !tile[num].mask_t;
- if (dos)
- {
- if (*S & 0x10000)
- {
- *S = 0;
- }
- else if (maxs)
- {
- *S = m_clamp_s_diff[num];
- }
- else
- {
- *S = (SIGN17(*S) >> 5) & 0x1fff;
- }
- }
- else
- {
- *S = (SIGN17(*S) >> 5) & 0x1fff;
- }
- if (dot)
- {
- if (*T & 0x10000)
- {
- *T = 0;
- }
- else if (maxt)
- {
- *T = m_clamp_t_diff[num];
- }
- else
- {
- *T = (SIGN17(*T) >> 5) & 0x1fff;
- }
- }
- else
- {
- *T = (SIGN17(*T) >> 5) & 0x1fff;
- }
- }
- void TexturePipe::Cycle(Color* TEX, Color* prev, INT32 SSS, INT32 SST, UINT32 tilenum, UINT32 cycle)
- {
- Tile* tile = m_rdp->GetTiles();
- #define TRELATIVE(x, y) ((((x) >> 3) - (y)) << 3) | (x & 7);
- INT32 bilerp = cycle ? m_other_modes->bi_lerp1 : m_other_modes->bi_lerp0;
- int convert = m_other_modes->convert_one && cycle;
- Color t0;
- Color t1;
- Color t2;
- Color t3;
- if (m_other_modes->sample_type)
- {
- int sss1, sst1, sss2, sst2;
- INT32 invsf = 0;
- INT32 invtf = 0;
- int center = 0;
- sss1 = SSS;
- sst1 = SST;
- INT32 maxs;
- INT32 maxt;
- ShiftCycle(&sss1, &sst1, &maxs, &maxt, tilenum);
- sss1 = TRELATIVE(sss1, tile[tilenum].sl);
- sst1 = TRELATIVE(sst1, tile[tilenum].tl);
- INT32 sfrac = sss1 & 0x1f;
- INT32 tfrac = sst1 & 0x1f;
- ClampCycle(&sss1, &sst1, &sfrac, &tfrac, maxs, maxt, tilenum);
- sss2 = sss1 + 1;
- sst2 = sst1 + 1;
- MaskCoupled(&sss1, &sss2, &sst1, &sst2, tilenum);
- bool upper = ((sfrac + tfrac) >= 0x20);
- if (upper)
- {
- invsf = 0x20 - sfrac;
- invtf = 0x20 - tfrac;
- }
- center = (sfrac == 0x10) && (tfrac == 0x10) && m_other_modes->mid_texel;
- invsf <<= 3;
- invtf <<= 3;
- sfrac <<= 3;
- tfrac <<= 3;
- t0.c = Fetch(sss1, sst1, tilenum);
- if (bilerp)
- {
- t1.c = Fetch(sss2, sst1, tilenum);
- t2.c = Fetch(sss1, sst2, tilenum);
- t3.c = Fetch(sss2, sst2, tilenum);
- if (!center)
- {
- if (upper)
- {
- TEX->i.r = t3.i.r + (((invsf * (t2.i.r - t3.i.r)) + (invtf * (t1.i.r - t3.i.r)) + 0x80) >> 8);
- TEX->i.g = t3.i.g + (((invsf * (t2.i.g - t3.i.g)) + (invtf * (t1.i.g - t3.i.g)) + 0x80) >> 8);
- TEX->i.b = t3.i.b + (((invsf * (t2.i.b - t3.i.b)) + (invtf * (t1.i.b - t3.i.b)) + 0x80) >> 8);
- TEX->i.a = t3.i.a + (((invsf * (t2.i.a - t3.i.a)) + (invtf * (t1.i.a - t3.i.a)) + 0x80) >> 8);
- }
- else
- {
- TEX->i.r = t0.i.r + (((sfrac * (t1.i.r - t0.i.r)) + (tfrac * (t2.i.r - t0.i.r)) + 0x80) >> 8);
- TEX->i.g = t0.i.g + (((sfrac * (t1.i.g - t0.i.g)) + (tfrac * (t2.i.g - t0.i.g)) + 0x80) >> 8);
- TEX->i.b = t0.i.b + (((sfrac * (t1.i.b - t0.i.b)) + (tfrac * (t2.i.b - t0.i.b)) + 0x80) >> 8);
- TEX->i.a = t0.i.a + (((sfrac * (t1.i.a - t0.i.a)) + (tfrac * (t2.i.a - t0.i.a)) + 0x80) >> 8);
- }
- TEX->i.r &= 0x1ff;
- TEX->i.g &= 0x1ff;
- TEX->i.b &= 0x1ff;
- TEX->i.a &= 0x1ff;
- }
- else//tf.c,24
- {
- TEX->i.r = (t0.i.r + t1.i.r + t2.i.r + t3.i.r) >> 2;
- TEX->i.g = (t0.i.g + t1.i.g + t2.i.g + t3.i.g) >> 2;
- TEX->i.b = (t0.i.b + t1.i.b + t2.i.b + t3.i.b) >> 2;
- TEX->i.a = (t0.i.a + t1.i.a + t2.i.a + t3.i.a) >> 2;
- }
- }
- else
- {
- INT32 newk0 = SIGN9(m_rdp->GetK0());
- INT32 newk1 = SIGN9(m_rdp->GetK1());
- INT32 newk2 = SIGN9(m_rdp->GetK2());
- INT32 newk3 = SIGN9(m_rdp->GetK3());
- INT32 invk0 = ~newk0;
- INT32 invk1 = ~newk1;
- INT32 invk2 = ~newk2;
- INT32 invk3 = ~newk3;
- if (convert)
- {
- t0 = *prev;
- }
- t0.i.r = SIGN9(t0.i.r); t0.i.g = SIGN9(t0.i.g); t0.i.b = SIGN9(t0.i.b);
- TEX->i.r = t0.i.b + (((newk0 - invk0) * t0.i.g + 0x80) >> 8);
- TEX->i.g = t0.i.b + (((newk1 - invk1) * t0.i.r + (newk2 - invk2) * t0.i.g + 0x80) >> 8);
- TEX->i.b = t0.i.b + (((newk3 - invk3) * t0.i.r + 0x80) >> 8);
- TEX->i.a = t0.i.b;
- TEX->i.r &= 0x1ff;
- TEX->i.g &= 0x1ff;
- TEX->i.b &= 0x1ff;
- TEX->i.a &= 0x1ff;
- }
- }
- else
- {
- INT32 sss1 = SSS;
- INT32 sst1 = SST;
- INT32 maxs;
- INT32 maxt;
- ShiftCycle(&sss1, &sst1, &maxs, &maxt, tilenum);
- sss1 = TRELATIVE(sss1, tile[tilenum].sl);
- sst1 = TRELATIVE(sst1, tile[tilenum].tl);
- ClampCycleLight(&sss1, &sst1, maxs, maxt, tilenum);
- Mask(&sss1, &sst1, tilenum);
- t0.c = Fetch(sss1, sst1, tilenum);
- if (bilerp)
- {
- *TEX = t0;
- }
- else
- {
- INT32 newk0 = SIGN9(m_rdp->GetK0());
- INT32 newk1 = SIGN9(m_rdp->GetK1());
- INT32 newk2 = SIGN9(m_rdp->GetK2());
- INT32 newk3 = SIGN9(m_rdp->GetK3());
- INT32 invk0 = ~newk0;
- INT32 invk1 = ~newk1;
- INT32 invk2 = ~newk2;
- INT32 invk3 = ~newk3;
- if (convert)
- {
- t0 = *prev;
- }
- t0.i.r = SIGN9(t0.i.r);
- t0.i.g = SIGN9(t0.i.g);
- t0.i.b = SIGN9(t0.i.b);
- TEX->i.r = t0.i.b + (((newk0 - invk0) * t0.i.g + 0x80) >> 8);
- TEX->i.g = t0.i.b + (((newk1 - invk1) * t0.i.r + (newk2 - invk2) * t0.i.g + 0x80) >> 8);
- TEX->i.b = t0.i.b + (((newk3 - invk3) * t0.i.r + 0x80) >> 8);
- TEX->i.a = t0.i.b;
- TEX->i.r &= 0x1ff;
- TEX->i.g &= 0x1ff;
- TEX->i.b &= 0x1ff;
- TEX->i.a &= 0x1ff;
- }
- }
- }
- void TexturePipe::Copy(Color* TEX, INT32 SSS, INT32 SST, UINT32 tilenum)
- {
- Tile* tile = m_rdp->GetTiles();
- INT32 sss1 = SSS;
- INT32 sst1 = SST;
- ShiftCopy(&sss1, &sst1, tilenum);
- sss1 = TRELATIVE(sss1, tile[tilenum].sl);
- sst1 = TRELATIVE(sst1, tile[tilenum].tl);
- sss1 = (SIGN17(sss1) >> 5) & 0x1fff;
- sst1 = (SIGN17(sst1) >> 5) & 0x1fff;
- Mask(&sss1, &sst1, tilenum);
- TEX->c = Fetch(sss1, sst1, tilenum);
- }
- void TexturePipe::LOD1Cycle(INT32* sss, INT32* sst, INT32 s, INT32 t, INT32 w, INT32 dsinc, INT32 dtinc, INT32 dwinc)
- {
- INT32 nextsw = (w + dwinc) >> 16;
- INT32 nexts = (s + dsinc) >> 16;
- INT32 nextt = (t + dtinc) >> 16;
- if (m_other_modes->persp_tex_en)
- {
- m_rdp->TCDiv(nexts, nextt, nextsw, &nexts, &nextt);
- }
- else
- {
- m_rdp->TCDivNoPersp(nexts, nextt, nextsw, &nexts, &nextt);
- }
- m_start_span = false;
- m_precomp_s = nexts;
- m_precomp_t = nextt;
- int tempanded;
- if (*sss & 0x40000)
- {
- *sss = 0x7fff;
- }
- else if (*sss & 0x20000)
- {
- *sss = 0x8000;
- }
- else
- {
- tempanded = *sss & 0x18000;
- if (tempanded == 0x8000)
- {
- *sss = 0x7fff;
- }
- else if (tempanded == 0x10000)
- {
- *sss = 0x8000;
- }
- else
- {
- *sss &= 0xffff;
- }
- }
- if (*sst & 0x40000)
- {
- *sst = 0x7fff;
- }
- else if (*sst & 0x20000)
- {
- *sst = 0x8000;
- }
- else
- {
- tempanded = *sst & 0x18000;
- if (tempanded == 0x8000)
- {
- *sst = 0x7fff;
- }
- else if (tempanded == 0x10000)
- {
- *sst = 0x8000;
- }
- else
- {
- *sst &= 0xffff;
- }
- }
- }
- void TexturePipe::LOD2Cycle(INT32* sss, INT32* sst, INT32 s, INT32 t, INT32 w, INT32 dsinc, INT32 dtinc, INT32 dwinc, INT32 prim_tile, INT32* t1, INT32* t2)
- {
- INT32 nextsw = (w + dwinc) >> 16;
- INT32 nexts = (s + dsinc) >> 16;
- INT32 nextt = (t + dtinc) >> 16;
- if (m_other_modes->persp_tex_en)
- {
- m_rdp->TCDiv(nexts, nextt, nextsw, &nexts, &nextt);
- }
- else
- {
- m_rdp->TCDivNoPersp(nexts, nextt, nextsw, &nexts, &nextt);
- }
- m_start_span = false;
- m_precomp_s = nexts;
- m_precomp_t = nextt;
- INT32 lodclamp = (((*sst & 0x60000) > 0) | ((nextt & 0x60000) > 0)) || (((*sss & 0x60000) > 0) | ((nexts & 0x60000) > 0));
- INT32 horstep = SIGN17(nexts & 0x1ffff) - SIGN17(*sss & 0x1ffff);
- INT32 vertstep = SIGN17(nextt & 0x1ffff) - SIGN17(*sst & 0x1ffff);
- if (horstep & 0x20000)
- {
- horstep = ~horstep & 0x1ffff;
- }
- if (vertstep & 0x20000)
- {
- vertstep = ~vertstep & 0x1ffff;
- }
- INT32 lod = (horstep >= vertstep) ? horstep : vertstep;
- INT32 temp_anded;
- if (*sss & 0x40000)
- {
- *sss = 0x7fff;
- }
- else if (*sss & 0x20000)
- {
- *sss = 0x8000;
- }
- else
- {
- temp_anded = *sss & 0x18000;
- if (temp_anded == 0x8000)
- {
- *sss = 0x7fff;
- }
- else if (temp_anded == 0x10000)
- {
- *sss = 0x8000;
- }
- else
- {
- *sss &= 0xffff;
- }
- }
- if (*sst & 0x40000)
- {
- *sst = 0x7fff;
- }
- else if (*sst & 0x20000)
- {
- *sst = 0x8000;
- }
- else
- {
- temp_anded = *sst & 0x18000;
- if (temp_anded == 0x8000)
- {
- *sst = 0x7fff;
- }
- else if (temp_anded == 0x10000)
- {
- *sst = 0x8000;
- }
- else
- {
- *sst &= 0xffff;
- }
- }
- if ((lod & 0x4000) || lodclamp)
- {
- lod = 0x7fff;
- }
- else if (lod < m_misc_state->m_min_level)
- {
- lod = m_misc_state->m_min_level;
- }
- bool magnify = (lod < 32);
- INT32 l_tile = m_rdp->GetLog2((lod >> 5) & 0xff);
- bool distant = ((lod & 0x6000) || (l_tile >= m_misc_state->m_max_level));
- m_rdp->SetLODFrac(((lod << 3) >> l_tile) & 0xff);
- if(!m_other_modes->sharpen_tex_en && !m_other_modes->detail_tex_en)
- {
- if (distant)
- {
- m_rdp->SetLODFrac(0xff);
- }
- else if (magnify)
- {
- m_rdp->SetLODFrac(0);
- }
- }
- if(m_other_modes->sharpen_tex_en && magnify)
- {
- m_rdp->SetLODFrac(m_rdp->GetLODFrac() | 0x100);
- }
- if (m_other_modes->tex_lod_en)
- {
- if (distant)
- {
- l_tile = m_misc_state->m_max_level;
- }
- if (!m_other_modes->detail_tex_en)
- {
- *t1 = (prim_tile + l_tile) & 7;
- if (!(distant || (!m_other_modes->sharpen_tex_en && magnify)))
- {
- *t2 = (*t1 + 1) & 7;
- }
- else
- {
- *t2 = *t1; // World Driver Championship, Stunt Race 64, Beetle Adventure Racing
- }
- }
- else // Beetle Adventure Racing, World Driver Championship (ingame_, NFL Blitz 2001, Pilotwings
- {
- if (!magnify)
- {
- *t1 = (prim_tile + l_tile + 1);
- }
- else
- {
- *t1 = (prim_tile + l_tile);
- }
- *t1 &= 7;
- if (!distant && !magnify)
- {
- *t2 = (prim_tile + l_tile + 2) & 7;
- }
- else
- {
- *t2 = (prim_tile + l_tile + 1) & 7;
- }
- }
- }
- }
- void TexturePipe::LOD2CycleLimited(INT32* sss, INT32* sst, INT32 s, INT32 t, INT32 w, INT32 dsinc, INT32 dtinc, INT32 dwinc, INT32 prim_tile, INT32* t1)
- {
- INT32 nextsw = (w + dwinc) >> 16;
- INT32 nexts = (s + dsinc) >> 16;
- INT32 nextt = (t + dtinc) >> 16;
- if (m_other_modes->persp_tex_en)
- {
- m_rdp->TCDiv(nexts, nextt, nextsw, &nexts, &nextt);
- }
- else
- {
- m_rdp->TCDivNoPersp(nexts, nextt, nextsw, &nexts, &nextt);
- }
- INT32 lodclamp = (((*sst & 0x60000) > 0) | ((nextt & 0x60000) > 0)) || (((*sss & 0x60000) > 0) | ((nexts & 0x60000) > 0));
- INT32 horstep = SIGN17(nexts & 0x1ffff) - SIGN17(*sss & 0x1ffff);
- INT32 vertstep = SIGN17(nextt & 0x1ffff) - SIGN17(*sst & 0x1ffff);
- if (horstep & 0x20000)
- {
- horstep = ~horstep & 0x1ffff;
- }
- if (vertstep & 0x20000)
- {
- vertstep = ~vertstep & 0x1ffff;
- }
- INT32 lod = (horstep >= vertstep) ? horstep : vertstep;
- INT32 tempanded;
- if (*sss & 0x40000)
- {
- *sss = 0x7fff;
- }
- else if (*sss & 0x20000)
- {
- *sss = 0x8000;
- }
- else
- {
- tempanded = *sss & 0x18000;
- if (tempanded == 0x8000)
- {
- *sss = 0x7fff;
- }
- else if (tempanded == 0x10000)
- {
- *sss = 0x8000;
- }
- else
- {
- *sss &= 0xffff;
- }
- }
- if (*sst & 0x40000)
- {
- *sst = 0x7fff;
- }
- else if (*sst & 0x20000)
- {
- *sst = 0x8000;
- }
- else
- {
- tempanded = *sst & 0x18000;
- if (tempanded == 0x8000)
- {
- *sst = 0x7fff;
- }
- else if (tempanded == 0x10000)
- {
- *sst = 0x8000;
- }
- else
- {
- *sst &= 0xffff;
- }
- }
- if ((lod & 0x4000) || lodclamp)
- {
- lod = 0x7fff;
- }
- else if (lod < m_misc_state->m_min_level)
- {
- lod = m_misc_state->m_min_level;
- }
- bool magnify = (lod < 32);
- INT32 l_tile = m_rdp->GetLog2((lod >> 5) & 0xff);
- bool distant = (lod & 0x6000) || (l_tile >= m_misc_state->m_max_level);
- if (m_other_modes->tex_lod_en)
- {
- if (distant)
- {
- l_tile = m_misc_state->m_max_level;
- }
- if (!m_other_modes->detail_tex_en)
- {
- *t1 = (prim_tile + l_tile) & 7;
- }
- else
- {
- if (!magnify)
- {
- *t1 = (prim_tile + l_tile + 1);
- }
- else
- {
- *t1 = (prim_tile + l_tile);
- }
- *t1 &= 7;
- }
- }
- }
- void TexturePipe::CalculateClampDiffs(UINT32 prim_tile)
- {
- Tile* tile = m_rdp->GetTiles();
- if (m_other_modes->cycle_type == CYCLE_TYPE_2)
- {
- if (m_other_modes->tex_lod_en)
- {
- int start = 0;
- int end = 7;
- for (; start <= end; start++)
- {
- m_clamp_s_diff[start] = (tile[start].sh >> 2) - (tile[start].sl >> 2);
- m_clamp_t_diff[start] = (tile[start].th >> 2) - (tile[start].tl >> 2);
- }
- }
- else
- {
- int start = prim_tile;
- int end = (prim_tile + 1) & 7;
- m_clamp_s_diff[start] = (tile[start].sh >> 2) - (tile[start].sl >> 2);
- m_clamp_t_diff[start] = (tile[start].th >> 2) - (tile[start].tl >> 2);
- m_clamp_s_diff[end] = (tile[end].sh >> 2) - (tile[end].sl >> 2);
- m_clamp_t_diff[end] = (tile[end].th >> 2) - (tile[end].tl >> 2);
- }
- }
- else//1-cycle or copy
- {
- m_clamp_s_diff[prim_tile] = (tile[prim_tile].sh >> 2) - (tile[prim_tile].sl >> 2);
- m_clamp_t_diff[prim_tile] = (tile[prim_tile].th >> 2) - (tile[prim_tile].tl >> 2);
- }
- }
- UINT32 TexturePipe::Fetch(INT32 s, INT32 t, INT32 tilenum)
- {
- Tile* tile = m_rdp->GetTiles();
- Color color;
- UINT32 tbase = (tile[tilenum].line * t) & 0x1ff;
- UINT32 tformat = tile[tilenum].format;
- UINT32 tsize = tile[tilenum].size;
- tbase += tile[tilenum].tmem;
- UINT32 tpal = tile[tilenum].palette;
- if (tformat == FORMAT_I && tsize > PIXEL_SIZE_8BIT)
- {
- tformat = FORMAT_RGBA; // Used by Supercross 2000 (in-game)
- }
- if (tformat == FORMAT_CI && tsize > PIXEL_SIZE_8BIT)
- {
- tformat = FORMAT_RGBA; // Used by Clay Fighter - Sculptor's Cut
- }
- if (tformat == FORMAT_RGBA && tsize < PIXEL_SIZE_16BIT)
- {
- tformat = FORMAT_CI; // Used by Exterem-G2, Madden Football 64, and Rat Attack
- }
- UINT16 *tc16 = m_rdp->GetTMEM16();
- switch (tformat)
- {
- case FORMAT_RGBA:
- {
- switch (tsize)
- {
- case PIXEL_SIZE_4BIT:
- break;
- case PIXEL_SIZE_8BIT:
- break;
- case PIXEL_SIZE_16BIT:
- {
- int taddr = (tbase << 2) + s;
- taddr ^= ((t & 1) ? WORD_XOR_DWORD_SWAP : WORD_ADDR_XOR);
- taddr &= 0x7ff;
- if (!m_other_modes->en_tlut)
- {
- UINT16 c = tc16[taddr];
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- UINT16 c = tc16[taddr];
- c = m_rdp->GetTLUT()[(c >> 8) << 2];
- if (m_other_modes->tlut_type == 0) // Used by Goldeneye 007 (ocean in Frigate)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else // Used by Beetle Adventure Racing (Mount Mayhem level)
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- break;
- }
- case PIXEL_SIZE_32BIT:
- {
- UINT32 *tc = m_rdp->GetTMEM32();
- int taddr = (tbase << 2) + s;
- taddr ^= ((t & 1) ? WORD_XOR_DWORD_SWAP : WORD_ADDR_XOR);
- if (!m_other_modes->en_tlut)
- {
- taddr &= 0x3ff;
- UINT32 c = tc16[taddr];
- color.i.r = (c >> 8) & 0xff;
- color.i.g = c & 0xff;
- c = tc16[taddr | 0x400];
- color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- else // Used by California Speed, attract mode
- {
- taddr &= 0x3ff;
- UINT32 c = tc[taddr];
- c = m_rdp->GetTLUT()[(c >> 24) << 2];
- if (m_other_modes->tlut_type == 0)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- break;
- }
- default:
- fatalerror("FETCH_TEXEL: unknown RGBA texture size %d\n", tsize);
- break;
- }
- break;
- }
- case FORMAT_YUV: // Used by: Bottom of the 9th, Pokemon Stadium, Ogre Battle, Major League Baseball, Ken Griffey Jr.'s Slugfest, Vigilante 8 Second Offense
- {
- switch(tsize)
- {
- case PIXEL_SIZE_16BIT:
- {
- UINT16 *tc = m_rdp->GetTMEM16();
- int taddr = (tbase << 3) + s;
- int taddrlow = taddr >> 1;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddrlow ^= ((t & 1) ? WORD_XOR_DWORD_SWAP : WORD_ADDR_XOR);
- taddr &= 0x7ff;
- taddrlow &= 0x3ff;
- UINT16 c = tc[taddrlow];
- INT32 y = m_rdp->GetTMEM()[taddr | 0x800];
- INT32 u = c >> 8;
- INT32 v = c & 0xff;
- v ^= 0x80; u ^= 0x80;
- if (v & 0x80)
- {
- v |= 0x100;
- }
- if (u & 0x80)
- {
- u |= 0x100;
- }
- color.i.r = u;
- color.i.g = v;
- color.i.b = y;
- color.i.a = y;
- break;
- }
- default:
- fatalerror("FETCH_TEXEL: unknown YUV texture size %d\n",tsize);
- break;
- }
- break;
- }
- case FORMAT_CI:
- {
- switch (tsize)
- {
- case PIXEL_SIZE_4BIT: // Madden Football 64, Bust-A-Move 2
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = ((tbase << 4) + s) >> 1;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (m_other_modes->en_tlut)
- {
- taddr &= 0x7ff;
- UINT8 p = (s & 1) ? (tc[taddr] & 0xf) : (tc[taddr] >> 4);
- UINT16 c = m_rdp->GetTLUT()[((tpal << 4) | p) << 2];
- if (m_other_modes->tlut_type == 0)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- else
- {
- UINT8 p = (s & 1) ? (tc[taddr] & 0xf) : (tc[taddr] >> 4);
- p = (tpal << 4) | p;
- color.i.r = color.i.g = color.i.b = color.i.a = p;
- }
- break;
- }
- case PIXEL_SIZE_8BIT:
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = (tbase << 3) + s;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (m_other_modes->en_tlut)
- {
- taddr &= 0x7ff;
- UINT8 p = tc[taddr];
- UINT16 c = m_rdp->GetTLUT()[p << 2];
- if (m_other_modes->tlut_type == 0)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- else
- {
- UINT8 p = tc[taddr];
- color.i.r = p;
- color.i.g = p;
- color.i.b = p;
- color.i.a = p;
- }
- break;
- }
- default:
- fatalerror("FETCH_TEXEL: unknown CI texture size %d\n", tsize);
- break;
- }
- break;
- }
- case FORMAT_IA:
- {
- switch (tsize)
- {
- case PIXEL_SIZE_4BIT:
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = ((tbase << 4) + s) >> 1;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (!m_other_modes->en_tlut)
- {
- UINT8 p = ((s) & 1) ? (tc[taddr] & 0xf) : (tc[taddr] >> 4);
- UINT8 i = p & 0xe;
- i = (i << 4) | (i << 1) | (i >> 2);
- color.i.r = i;
- color.i.g = i;
- color.i.b = i;
- color.i.a = (p & 0x1) ? 0xff : 0;
- }
- else
- {
- taddr &= 0x7ff;
- UINT8 p = ((s) & 1) ? (tc[taddr] & 0xf) : (tc[taddr] >> 4);
- UINT16 c = m_rdp->GetTLUT()[((tpal << 4) | p) << 2];
- if (!m_other_modes->tlut_type)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- break;
- }
- case PIXEL_SIZE_8BIT:
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = (tbase << 3) + s;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (!m_other_modes->en_tlut)
- {
- UINT8 p = tc[taddr];
- UINT8 i = p & 0xf0;
- i |= (i >> 4);
- color.i.r = i;
- color.i.g = i;
- color.i.b = i;
- color.i.a = ((p & 0xf) << 4) | (p & 0xf);
- }
- else
- {
- UINT8 p = tc[taddr & 0x7ff];
- UINT16 c = m_rdp->GetTLUT()[p << 2];
- if (!m_other_modes->tlut_type)
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (c >> 8) & 0xff;
- color.i.a = c & 0xff;
- }
- }
- break;
- }
- case PIXEL_SIZE_16BIT:
- {
- UINT16 *tc = m_rdp->GetTMEM16();
- int taddr = (tbase << 2) + s;
- taddr ^= ((t & 1) ? WORD_XOR_DWORD_SWAP : WORD_ADDR_XOR);
- taddr &= 0x7ff;
- if (!m_other_modes->en_tlut)
- {
- UINT16 c = tc[taddr];
- UINT8 i = (c >> 8);
- color.i.r = i;
- color.i.g = i;
- color.i.b = i;
- color.i.a = c & 0xff;
- }
- else
- {
- UINT16 c = tc[taddr & 0x3ff];
- c = m_rdp->GetTLUT()[(c >> 8) << 2];
- if (m_other_modes->tlut_type == 1)
- {
- color.i.r = c >> 8;
- color.i.g = c >> 8;
- color.i.b = c >> 8;
- color.i.a = c & 0xff;
- }
- else
- {
- color.i.r = GET_HI_RGBA16_TMEM(c);
- color.i.g = GET_MED_RGBA16_TMEM(c);
- color.i.b = GET_LOW_RGBA16_TMEM(c);
- color.i.a = (c & 1) ? 0xff : 0;
- }
- }
- break;
- }
- default:
- color.i.r = color.i.g = color.i.b = color.i.a = 0xff;
- fatalerror("FETCH_TEXEL: unknown IA texture size %d\n", tsize);
- break;
- }
- break;
- }
- case FORMAT_I:
- {
- switch (tsize)
- {
- case PIXEL_SIZE_4BIT:
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = ((tbase << 4) + s) >> 1;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (!m_other_modes->en_tlut)
- {
- UINT8 byteval = tc[taddr];
- UINT8 c = ((s & 1)) ? (byteval & 0xf) : ((byteval >> 4) & 0xf);
- c |= (c << 4);
- color.i.r = c;
- color.i.g = c;
- color.i.b = c;
- color.i.a = c;
- }
- else
- {
- UINT8 byteval = tc[taddr & 0x7ff];
- UINT8 c = ((s & 1)) ? (byteval & 0xf) : ((byteval >> 4) & 0xf);
- UINT16 k = m_rdp->GetTLUT()[((tpal << 4) | c) << 2];
- if (!m_other_modes->tlut_type)
- {
- color.i.r = GET_HI_RGBA16_TMEM(k);
- color.i.g = GET_MED_RGBA16_TMEM(k);
- color.i.b = GET_LOW_RGBA16_TMEM(k);
- color.i.a = (k & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (k >> 8) & 0xff;
- color.i.a = k & 0xff;
- }
- }
- break;
- }
- case PIXEL_SIZE_8BIT:
- {
- UINT8 *tc = m_rdp->GetTMEM();
- int taddr = (tbase << 3) + s;
- taddr ^= ((t & 1) ? BYTE_XOR_DWORD_SWAP : BYTE_ADDR_XOR);
- taddr &= 0xfff;
- if (!m_other_modes->en_tlut)
- {
- UINT8 c = tc[taddr];
- color.i.r = c;
- color.i.g = c;
- color.i.b = c;
- color.i.a = c;
- }
- else
- {
- UINT8 c = tc[taddr & 0x7ff];
- UINT16 k = m_rdp->GetTLUT()[c << 2];
- if (!m_other_modes->tlut_type)
- {
- color.i.r = GET_HI_RGBA16_TMEM(k);
- color.i.g = GET_MED_RGBA16_TMEM(k);
- color.i.b = GET_LOW_RGBA16_TMEM(k);
- color.i.a = (k & 1) ? 0xff : 0;
- }
- else
- {
- color.i.r = color.i.g = color.i.b = (k >> 8) & 0xff;
- color.i.a = k & 0xff;
- }
- }
- break;
- }
- default:
- fatalerror("FETCH_TEXEL: unknown I texture size %d\n", tsize);
- break;
- }
- break;
- }
- default:
- {
- fatalerror("FETCH_TEXEL: unknown texture format %d, tilenum %d\n", tformat, tilenum);
- break;
- }
- }
- return color.c;
- }
- } // namespace RDP
- } // namespace N64
Add Comment
Please, Sign In to add comment