Files
2026-05-30 02:50:21 -07:00

833 lines
24 KiB
C++

/*-----------------------------------------------------------------------**
** Diablo
**
** Palette file
**
** (C)1995 Condor, Inc. All rights reserved.
**-----------------------------------------------------------------------**
** $Header: /Diablo/PALETTE.CPP 2 1/23/97 12:21p Jmorin $
**-----------------------------------------------------------------------*/
#include "diablo.h"
#pragma hdrstop
#include "storm/h/storm.h"
#include "palette.h"
#include "engine.h"
#include <math.h>
#include "resource.h"
/*-----------------------------------------------------------------------**
** extern
**-----------------------------------------------------------------------*/
extern char gszProgKey[];
void ErrorDlg(int nDlgId,DWORD dwErr,const char * pszFile,int nLine);
/*-----------------------------------------------------------------------**
** File Variables
**-----------------------------------------------------------------------*/
static LONG sglGamma = lGAMMA_MAX;
static int sgnStaticColors2 = 0;
static PALETTEENTRY sgLoad[256]; // original loaded palette -- used as reference
// for gamma conversion
static PALETTEENTRY sgBase[256]; // palettized version of sgLoad
static PALETTEENTRY sgCurr[256]; // palette to be displayed -- includes rotations
static const char sgszGamma[] = "Gamma Correction";
static BYTE sgbFadedIn = TRUE;
extern "C" {
BYTE gbLevelTileEnhanceActive = FALSE;
BYTE gbLevelTileContrastTable[256];
BYTE gbLevelTileLumaTable[256];
BYTE gbLevelTileSharpenLightTable[256];
BYTE gbLevelTileAoTable[256];
BYTE gbLevelUnitContrastTable[256];
BYTE gbLevelUnitLumaTable[256];
BYTE gbLevelUnitSharpenLightTable[256];
BYTE gbLevelUnitAoTable[256];
BYTE gbTownWarmFlickerActive = FALSE;
BYTE gbTownWarmFlickerTable[4][256];
BYTE gbHudAnimateActive = FALSE;
BYTE gbHudHealthOrbTable[4][256];
BYTE gbHudManaOrbTable[4][256];
BYTE gbHudPotionHealthTable[4][256];
BYTE gbHudPotionManaTable[4][256];
BYTE gbHudPotionRejuvTable[4][256];
BYTE gbWorldGoldShimmerActive = FALSE;
BYTE gbWorldGoldShimmerTable[4][256];
int gnTownTileX = -1;
int gnTownTileY = -1;
int gnTownFlickerFrame = 0;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int PalClamp(int value, int max)
{
if (value < 0) return 0;
if (value > max) return max;
return value;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static LONG PalDistance(const PALETTEENTRY *a, int red, int green, int blue)
{
LONG dr, dg, db;
dr = (LONG)a->peRed - red;
dg = (LONG)a->peGreen - green;
db = (LONG)a->peBlue - blue;
return dr * dr + dg * dg + db * db;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static BYTE FindNearestPaletteColor(int red, int green, int blue)
{
int i;
BYTE best;
LONG dist, bestDist;
best = 1;
bestDist = PalDistance(&sgLoad[1], red, green, blue);
for (i = 2; i < 256; i++) {
dist = PalDistance(&sgLoad[i], red, green, blue);
if (dist < bestDist) {
bestDist = dist;
best = (BYTE)i;
}
}
return best;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void BuildLevelTileEnhanceTables()
{
int i, max, mid;
int red, green, blue, brightness;
max = 63;
for (i = 0; i < 256; i++) {
if (sgLoad[i].peRed > 63 || sgLoad[i].peGreen > 63 || sgLoad[i].peBlue > 63) {
max = 255;
break;
}
}
mid = max / 2;
gbLevelTileContrastTable[0] = 0;
gbLevelTileLumaTable[0] = 0;
gbLevelTileSharpenLightTable[0] = 0;
gbLevelTileAoTable[0] = 0;
gbLevelUnitContrastTable[0] = 0;
gbLevelUnitLumaTable[0] = 0;
gbLevelUnitSharpenLightTable[0] = 0;
gbLevelUnitAoTable[0] = 0;
for (i = 1; i < 256; i++) {
brightness = ((int)sgLoad[i].peRed * 30 + (int)sgLoad[i].peGreen * 59 + (int)sgLoad[i].peBlue * 11) / 100;
gbLevelTileLumaTable[i] = (BYTE)((brightness * 255) / max);
gbLevelUnitLumaTable[i] = gbLevelTileLumaTable[i];
red = (int)sgLoad[i].peRed + (((int)max - (int)sgLoad[i].peRed) * 6) / 100;
green = (int)sgLoad[i].peGreen + (((int)max - (int)sgLoad[i].peGreen) * 6) / 100;
blue = (int)sgLoad[i].peBlue + (((int)max - (int)sgLoad[i].peBlue) * 6) / 100;
gbLevelTileSharpenLightTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
red = ((int)sgLoad[i].peRed * 90) / 100;
green = ((int)sgLoad[i].peGreen * 90) / 100;
blue = ((int)sgLoad[i].peBlue * 90) / 100;
gbLevelTileAoTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
red = (int)sgLoad[i].peRed + (((int)max - (int)sgLoad[i].peRed) * 12) / 100;
green = (int)sgLoad[i].peGreen + (((int)max - (int)sgLoad[i].peGreen) * 12) / 100;
blue = (int)sgLoad[i].peBlue + (((int)max - (int)sgLoad[i].peBlue) * 12) / 100;
gbLevelUnitSharpenLightTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
red = ((int)sgLoad[i].peRed * 82) / 100;
green = ((int)sgLoad[i].peGreen * 82) / 100;
blue = ((int)sgLoad[i].peBlue * 82) / 100;
gbLevelUnitAoTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
if (brightness < max / 5 || brightness > (max * 4) / 5) {
gbLevelTileContrastTable[i] = (BYTE)i;
gbLevelUnitContrastTable[i] = (BYTE)i;
continue;
}
red = mid + (((int)sgLoad[i].peRed - mid) * 106) / 100;
green = mid + (((int)sgLoad[i].peGreen - mid) * 106) / 100;
blue = mid + (((int)sgLoad[i].peBlue - mid) * 106) / 100;
gbLevelTileContrastTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
red = mid + (((int)sgLoad[i].peRed - mid) * 108) / 100;
green = mid + (((int)sgLoad[i].peGreen - mid) * 108) / 100;
blue = mid + (((int)sgLoad[i].peBlue - mid) * 108) / 100;
gbLevelUnitContrastTable[i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int IsWarmTownLightColor(int red, int green, int blue, int brightness, int max)
{
if (brightness < max / 4)
return FALSE;
if (red < green || green < blue)
return FALSE;
if (red - blue < max / 7)
return FALSE;
if (green - blue < max / 12)
return FALSE;
return TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void BuildTownWarmFlickerTables()
{
int i, p, max;
int red, green, blue, brightness;
static const int sPhaseRed[4] = { 6, 14, 9, -3 };
static const int sPhaseGreen[4] = { 3, 8, 5, -2 };
static const int sPhaseBlue[4] = { -3, -6, -4, 0 };
max = 63;
for (i = 0; i < 256; i++) {
if (sgLoad[i].peRed > 63 || sgLoad[i].peGreen > 63 || sgLoad[i].peBlue > 63) {
max = 255;
break;
}
}
for (i = 0; i < 256; i++) {
brightness = ((int)sgLoad[i].peRed * 30 + (int)sgLoad[i].peGreen * 59 + (int)sgLoad[i].peBlue * 11) / 100;
for (p = 0; p < 4; p++) {
if (!IsWarmTownLightColor(sgLoad[i].peRed, sgLoad[i].peGreen, sgLoad[i].peBlue, brightness, max)) {
gbTownWarmFlickerTable[p][i] = (BYTE)i;
continue;
}
red = (int)sgLoad[i].peRed + (((int)max - (int)sgLoad[i].peRed) * sPhaseRed[p]) / 100;
green = (int)sgLoad[i].peGreen + (((int)max - (int)sgLoad[i].peGreen) * sPhaseGreen[p]) / 100;
if (sPhaseBlue[p] < 0)
blue = ((int)sgLoad[i].peBlue * (100 + sPhaseBlue[p])) / 100;
else
blue = (int)sgLoad[i].peBlue + (((int)max - (int)sgLoad[i].peBlue) * sPhaseBlue[p]) / 100;
gbTownWarmFlickerTable[p][i] = FindNearestPaletteColor(
PalClamp(red, max),
PalClamp(green, max),
PalClamp(blue, max));
}
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int IsHudHealthColor(int red, int green, int blue, int brightness, int max)
{
if (brightness < max / 5)
return FALSE;
if (red < green - max / 16)
return FALSE;
if (red < blue - max / 12)
return FALSE;
return TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int IsHudManaColor(int red, int green, int blue, int brightness, int max)
{
if (brightness < max / 5)
return FALSE;
if (blue < red - max / 16)
return FALSE;
if (blue < green - max / 12)
return FALSE;
return TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int IsHudRejuvColor(int red, int green, int blue, int brightness, int max)
{
if (brightness < max / 5)
return FALSE;
if (red < green + max / 14)
return FALSE;
if (blue < green + max / 14)
return FALSE;
return TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int HudShiftChannel(int value, int max, int percent)
{
if (percent >= 0)
return value + ((max - value) * percent) / 100;
return (value * (100 + percent)) / 100;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void BuildHudAnimTable(BYTE table[4][256], const int redPhase[4], const int greenPhase[4], const int bluePhase[4], int kind, int max)
{
int i, p;
int red, green, blue, brightness;
int useColor;
for (i = 0; i < 256; i++) {
red = sgLoad[i].peRed;
green = sgLoad[i].peGreen;
blue = sgLoad[i].peBlue;
brightness = (red * 30 + green * 59 + blue * 11) / 100;
useColor = FALSE;
if (kind == 0)
useColor = IsHudHealthColor(red, green, blue, brightness, max);
else if (kind == 1)
useColor = IsHudManaColor(red, green, blue, brightness, max);
else
useColor = IsHudRejuvColor(red, green, blue, brightness, max);
for (p = 0; p < 4; p++) {
if (!useColor) {
table[p][i] = (BYTE)i;
continue;
}
table[p][i] = FindNearestPaletteColor(
PalClamp(HudShiftChannel(red, max, redPhase[p]), max),
PalClamp(HudShiftChannel(green, max, greenPhase[p]), max),
PalClamp(HudShiftChannel(blue, max, bluePhase[p]), max));
}
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void BuildHudAnimateTables()
{
int i, max;
static const int sHealthOrbRed[4] = { 6, 16, 9, -4 };
static const int sHealthOrbGreen[4] = { 1, 4, 2, -2 };
static const int sHealthOrbBlue[4] = { -4, -10, -6, 0 };
static const int sManaOrbRed[4] = { -4, -10, -6, 0 };
static const int sManaOrbGreen[4] = { 2, 7, 4, -2 };
static const int sManaOrbBlue[4] = { 7, 18, 10, -4 };
static const int sHealthPotionRed[4] = { 3, 8, 5, -2 };
static const int sHealthPotionGreen[4] = { 0, 2, 1, -1 };
static const int sHealthPotionBlue[4] = { -2, -5, -3, 0 };
static const int sManaPotionRed[4] = { -2, -5, -3, 0 };
static const int sManaPotionGreen[4] = { 1, 4, 2, -1 };
static const int sManaPotionBlue[4] = { 4, 11, 6, -2 };
static const int sRejuvPotionRed[4] = { 4, 11, 6, -2 };
static const int sRejuvPotionGreen[4] = { -1, 1, 0, -1 };
static const int sRejuvPotionBlue[4] = { 4, 11, 6, -2 };
max = 63;
for (i = 0; i < 256; i++) {
if (sgLoad[i].peRed > 63 || sgLoad[i].peGreen > 63 || sgLoad[i].peBlue > 63) {
max = 255;
break;
}
}
BuildHudAnimTable(gbHudHealthOrbTable, sHealthOrbRed, sHealthOrbGreen, sHealthOrbBlue, 0, max);
BuildHudAnimTable(gbHudManaOrbTable, sManaOrbRed, sManaOrbGreen, sManaOrbBlue, 1, max);
BuildHudAnimTable(gbHudPotionHealthTable, sHealthPotionRed, sHealthPotionGreen, sHealthPotionBlue, 0, max);
BuildHudAnimTable(gbHudPotionManaTable, sManaPotionRed, sManaPotionGreen, sManaPotionBlue, 1, max);
BuildHudAnimTable(gbHudPotionRejuvTable, sRejuvPotionRed, sRejuvPotionGreen, sRejuvPotionBlue, 2, max);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static int IsWorldGoldColor(int red, int green, int blue, int brightness, int max)
{
if (brightness < max / 8)
return FALSE;
if (red < green - max / 5)
return FALSE;
if (green < blue + max / 24)
return FALSE;
if (red < blue + max / 12)
return FALSE;
return TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void BuildWorldGoldShimmerTables()
{
int i, p, max;
int red, green, blue, brightness;
static const int sGoldRed[4] = { 2, 22, 8, -8 };
static const int sGoldGreen[4] = { 1, 18, 6, -7 };
static const int sGoldBlue[4] = { -3, -16, -7, -4 };
max = 63;
for (i = 0; i < 256; i++) {
if (sgLoad[i].peRed > 63 || sgLoad[i].peGreen > 63 || sgLoad[i].peBlue > 63) {
max = 255;
break;
}
}
for (i = 0; i < 256; i++) {
red = sgLoad[i].peRed;
green = sgLoad[i].peGreen;
blue = sgLoad[i].peBlue;
brightness = (red * 30 + green * 59 + blue * 11) / 100;
for (p = 0; p < 4; p++) {
if (!IsWorldGoldColor(red, green, blue, brightness, max)) {
gbWorldGoldShimmerTable[p][i] = (BYTE)i;
continue;
}
gbWorldGoldShimmerTable[p][i] = FindNearestPaletteColor(
PalClamp(HudShiftChannel(red, max, sGoldRed[p]), max),
PalClamp(HudShiftChannel(green, max, sGoldGreen[p]), max),
PalClamp(HudShiftChannel(blue, max, sGoldBlue[p]), max));
}
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void SetPaletteEntries() {
if (! lpDDPal) return;
int nStart;
int nColors;
if (! fullscreen) {
nStart = sgnStaticColors2;
nColors = 256 - sgnStaticColors2*2;
}
else {
nStart = 0;
nColors = 256;
}
// HRESULT ddrval = lpDDPal->SetEntries(0,nStart,nColors,&sgCurr[nStart]);
// ddraw_assert(ddrval);
SDrawUpdatePalette(nStart,nColors,&sgCurr[nStart]);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void GammaPalette(PALETTEENTRY * pDst, const PALETTEENTRY * pSrc, int nNum) {
double gamma = sglGamma / 100.0;
for(int i = 0; i < nNum; i++,pDst++,pSrc++) {
pDst->peRed = (BYTE)(256.0*pow(((double)pSrc->peRed)/256.0, gamma));
pDst->peGreen = (BYTE)(256.0*pow(((double)pSrc->peGreen)/256.0, gamma));
pDst->peBlue = (BYTE)(256.0*pow(((double)pSrc->peBlue)/256.0, gamma));
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void SavePaletteSettings() {
SRegSaveValue(gszProgKey,sgszGamma,0,sglGamma);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void GetPaletteSettings() {
DWORD dwTemp = (DWORD) sglGamma;
if (! SRegLoadValue(gszProgKey,sgszGamma,0,&dwTemp))
dwTemp = lGAMMA_MAX;
sglGamma = (LONG) dwTemp;
if (sglGamma < lGAMMA_MIN)
sglGamma = lGAMMA_MIN;
else if (sglGamma > lGAMMA_MAX)
sglGamma = lGAMMA_MAX;
sglGamma -= sglGamma % lGAMMA_STEP;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void FixWindowsPal() {
int i;
// reserve all colors so no mapping occurs
for (i = 0; i < 256; i++)
sgCurr[i].peFlags = PC_NOCOLLAPSE | PC_RESERVED;
if (fullscreen) return;
// get static color count
HDC hDC = GetDC(NULL);
sgnStaticColors2 = GetDeviceCaps(hDC, NUMRESERVED) / 2;
// get the lower windows color set
GetSystemPaletteEntries(hDC, 0, sgnStaticColors2, &sgCurr[0]);
for (i = 0; i < sgnStaticColors2; i++) sgCurr[i].peFlags = 0;
// get the upper windows color set
i = 256 - sgnStaticColors2;
GetSystemPaletteEntries(hDC, i, sgnStaticColors2, &sgCurr[i]);
for ( ; i < 256; i++) sgCurr[i].peFlags = 0;
ReleaseDC(NULL, hDC);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void CreatePalette() {
GetPaletteSettings();
CopyMemory(sgCurr,sgLoad,sizeof(sgCurr));
FixWindowsPal();
HRESULT ddrval = lpDD->CreatePalette(DDPCAPS_8BIT | DDPCAPS_ALLOW256 | DDPCAPS_INITIALIZE,sgCurr,&lpDDPal,NULL);
if (ddrval != DD_OK) ErrorDlg(IDD_DDRAW_PAL_ERR,ddrval,__FILE__,__LINE__);
ddrval = lpDDSPrimary->SetPalette(lpDDPal);
if (ddrval != DD_OK) ErrorDlg(IDD_DDRAW_PAL_ERR,ddrval,__FILE__,__LINE__);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void LoadPalette(const char * pszFileName) {
struct RGB {
BYTE red;
BYTE green;
BYTE blue;
} pal[256];
HSFILE hFile;
app_assert(pszFileName);
patSFileOpenFile(pszFileName,&hFile);
patSFileReadFile(hFile,&pal[0],sizeof(pal));
patSFileCloseFile(hFile);
for (int i = 0; i < 256; i++) {
sgLoad[i].peRed = pal[i].red;
sgLoad[i].peGreen = pal[i].green;
sgLoad[i].peBlue = pal[i].blue;
sgLoad[i].peFlags = 0;
}
// GammaPalette(sgBase, sgLoad, 256);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void LoadRndLvlPal(int l) {
if (l == 0) {
LoadPalette("Levels\\TownData\\Town.pal");
}
else {
char filestr[MAX_PATH];
int palnum = random(0, 4) + 1;
sprintf(filestr, "Levels\\L%iData\\L%i_%i.PAL", l, l, palnum);
// JKE add our palettes here
if (l == 5)
sprintf(filestr, "NLevels\\L5Data\\L5Base.PAL");
if (l == 6)
{
if (!gbOurNest)
++palnum;
sprintf(filestr, "NLevels\\L%iData\\L%iBase%i.PAL", l, l, palnum);
}
LoadPalette(filestr);
}
BuildLevelTileEnhanceTables();
BuildTownWarmFlickerTables();
BuildHudAnimateTables();
BuildWorldGoldShimmerTables();
gbLevelTileEnhanceActive = TRUE;
gbTownWarmFlickerActive = (l == 0);
gbHudAnimateActive = FALSE;
gbWorldGoldShimmerActive = TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void ResetPal() {
if (lpDDSPrimary && lpDDSPrimary->IsLost() == DDERR_SURFACELOST)
if (DD_OK != lpDDSPrimary->Restore()) return;
SDrawRealizePalette();
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void GammaUp() {
if(sglGamma < lGAMMA_MAX) {
sglGamma += lGAMMA_STEP;
if (sglGamma > lGAMMA_MAX)
sglGamma = lGAMMA_MAX;
GammaPalette(sgCurr,sgBase,256);
SetPaletteEntries();
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void GammaDown() {
if(sglGamma > lGAMMA_MIN) {
sglGamma -= lGAMMA_STEP;
if (sglGamma < lGAMMA_MIN)
sglGamma = lGAMMA_MIN;
GammaPalette(sgCurr,sgBase,256);
SetPaletteEntries();
}
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
LONG GammaLevel(LONG lGamma) {
if (lGamma != lGAMMA_READ) {
// invert gamma hi/lo
sglGamma = lGAMMA_MAX - lGamma + lGAMMA_MIN;
GammaPalette(sgCurr,sgBase,256);
SetPaletteEntries();
}
// invert gamma hi/lo
return lGAMMA_MAX - sglGamma + lGAMMA_MIN;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
static void SetFadeLevel(int fadeval) {
if (! lpDD) return;
for (int i = 0; i < 255; i++) {
DWORD pv;
pv = sgBase[i].peRed * fadeval;
sgCurr[i].peRed = (BYTE) (pv/256);
pv = sgBase[i].peGreen * fadeval;
sgCurr[i].peGreen = (BYTE) (pv/256);
pv = sgBase[i].peBlue * fadeval;
sgCurr[i].peBlue = (BYTE) (pv/256);
}
// sgCurr[i].peRed = 0xff;
// sgCurr[i].peGreen = 0xff;
// sgCurr[i].peBlue = 0xff;
Sleep(3);
lpDD->WaitForVerticalBlank(DDWAITVB_BLOCKBEGIN,NULL);
SetPaletteEntries();
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void BlackPalette() {
SetFadeLevel(0);
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void PaletteFadeIn(int faderate) {
GammaPalette(sgBase,sgLoad,256);
for (int i = 0; i < 256; i += faderate)
SetFadeLevel(i);
SetFadeLevel(256);
// un-gamma-fy base palette
CopyMemory(sgBase,sgLoad,sizeof(sgBase));
sgbFadedIn = TRUE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void PaletteFadeOut(int faderate) {
if (! sgbFadedIn) return;
for (int i = 256; i > 0; i -= faderate)
SetFadeLevel(i);
SetFadeLevel(0);
sgbFadedIn = FALSE;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void LavaCycle() {
PALETTEENTRY temp = sgCurr[1];
for (int i = 1; i < 31; i++) {
sgCurr[i].peRed = sgCurr[i + 1].peRed;
sgCurr[i].peGreen = sgCurr[i + 1].peGreen;
sgCurr[i].peBlue = sgCurr[i + 1].peBlue;
// don't copy flags
}
sgCurr[i].peRed = temp.peRed;
sgCurr[i].peGreen = temp.peGreen;
sgCurr[i].peBlue = temp.peBlue;
// don't copy flags
SetPaletteEntries();
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
// JKE new cycle to do twin effects
void TwinCycleCrypt() {
int i;
static int toggle = 0;
static int toggle2 = 0;
PALETTEENTRY temp;
if (toggle2 > 1)
{
temp = sgCurr[15];
for (i = 15; i > 1; --i) {
sgCurr[i].peRed = sgCurr[i - 1].peRed;
sgCurr[i].peGreen = sgCurr[i - 1].peGreen;
sgCurr[i].peBlue = sgCurr[i - 1].peBlue;
// don't copy flags
}
sgCurr[i].peRed = temp.peRed;
sgCurr[i].peGreen = temp.peGreen;
sgCurr[i].peBlue = temp.peBlue;
// don't copy flags
toggle2 = 0;
}
else
++toggle2;
if (toggle > 0)
{
temp = sgCurr[31];
for (i = 31; i > 16; --i)
{
sgCurr[i].peRed = sgCurr[i - 1].peRed;
sgCurr[i].peGreen = sgCurr[i - 1].peGreen;
sgCurr[i].peBlue = sgCurr[i - 1].peBlue;
}
sgCurr[i].peRed = temp.peRed;
sgCurr[i].peGreen = temp.peGreen;
sgCurr[i].peBlue = temp.peBlue;
SetPaletteEntries();
++toggle;
}
else
toggle = 1;
}
void TwinCycleNest() {
int i;
static int toggle = 0;
static int toggle2 = 0;
PALETTEENTRY temp;
if (toggle2 == 2)
{
temp = sgCurr[8];
for (i = 8; i > 1; --i) {
sgCurr[i].peRed = sgCurr[i - 1].peRed;
sgCurr[i].peGreen = sgCurr[i - 1].peGreen;
sgCurr[i].peBlue = sgCurr[i - 1].peBlue;
// don't copy flags
}
sgCurr[i].peRed = temp.peRed;
sgCurr[i].peGreen = temp.peGreen;
sgCurr[i].peBlue = temp.peBlue;
// don't copy flags
toggle2 = 0;
}
else
++toggle2;
if (toggle == 2)
{
temp = sgCurr[15];
for (i = 15; i > 9; --i)
{
sgCurr[i].peRed = sgCurr[i - 1].peRed;
sgCurr[i].peGreen = sgCurr[i - 1].peGreen;
sgCurr[i].peBlue = sgCurr[i - 1].peBlue;
}
sgCurr[i].peRed = temp.peRed;
sgCurr[i].peGreen = temp.peGreen;
sgCurr[i].peBlue = temp.peBlue;
SetPaletteEntries();
toggle = 0;
}
else
++toggle;
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void UpdateLavaPalette() {
for (int i = 0; i < 32; i++)
sgBase[i] = sgLoad[i];
GammaPalette(sgCurr,sgBase,32);
SetPaletteEntries();
}
/*-----------------------------------------------------------------------**
**-----------------------------------------------------------------------*/
void MeshLavaPalette(int fadeval) {
int i;
for (i = 32 - fadeval; i >= 0; i--)
sgBase[i] = sgLoad[i];
GammaPalette(sgCurr, sgBase, 32);
SetPaletteEntries();
}