Retired Document
Important: This sample code may not represent best practices for current development. The project may use deprecated symbols and illustrate technologies and techniques that are no longer recommended.
Source/Misc.c
/****************************/ |
/* MISC ROUTINES */ |
/* By Brian Greenstone */ |
/****************************/ |
/***************/ |
/* EXTERNALS */ |
/***************/ |
#include <Events.h> |
#include <Dialogs.h> |
#include <Processes.h> |
#include <NumberFormatting.h> |
#include <QD3D.h> |
#include <QD3DErrors.h> |
#include <timer.h> |
#include <math.h> |
#include "myglobals.h" |
#include "misc.h" |
#include "main.h" |
/****************************/ |
/* CONSTANTS */ |
/****************************/ |
#define ERROR_ALERT_ID 401 |
/**********************/ |
/* VARIABLES */ |
/**********************/ |
KeyMap gKeyMap,gOldKeyMap; |
unsigned long gTick = 0; |
unsigned long seed0 = 0, seed1 = 0, seed2 = 0; |
/****************** DO SYSTEM ERROR ***************/ |
void ShowSystemErr(long err) |
{ |
Str255 numStr; |
NumToString(err, numStr); |
DoAlert (numStr); |
CleanQuit(); |
} |
/*********************** DO ALERT *******************/ |
void DoAlert(Str255 s) |
{ |
ParamText(s,NIL_STRING,NIL_STRING,NIL_STRING); |
NoteAlert(ERROR_ALERT_ID,NIL_POINTER); |
} |
/*********************** DO FATAL ALERT *******************/ |
void DoFatalAlert(Str255 s) |
{ |
ParamText(s,NIL_STRING,NIL_STRING,NIL_STRING); |
NoteAlert(ERROR_ALERT_ID,NIL_POINTER); |
CleanQuit(); |
} |
/************ CLEAN QUIT ***************/ |
void CleanQuit(void) |
{ |
ExitToShell(); |
} |
/********************** WAIT **********************/ |
void Wait(long ticks) |
{ |
long start; |
start = TickCount(); |
while ((TickCount()-start) < ticks) |
; |
} |
/**************************** LOAD A FILE *******************/ |
Handle LoadAFile(Str255 fileName, short volumeRefNum, long *fileSize) |
{ |
OSErr iErr; |
short fRefNum; |
Handle fileHandle; |
/* OPEN THE FILE */ |
iErr = FSOpen(fileName,volumeRefNum,&fRefNum); // open file |
if (iErr != noErr) |
DoFatalAlert("\pCant Open File!"); |
/* GET MEMORY FOR FILE */ |
if (GetEOF(fRefNum,fileSize) != noErr) // get size of text file |
DoFatalAlert("\pError reading File!"); |
if ((fileHandle = NewHandle(*fileSize)) == NIL_POINTER) |
DoFatalAlert ("\pNo Memory for File!"); |
HLock(fileHandle); |
/* READ THE DATA */ |
iErr = FSRead(fRefNum,fileSize,*fileHandle); |
if (iErr != noErr) |
DoFatalAlert ("\pError Reading File!"); |
/* CLOSE THE FILE */ |
iErr = FSClose(fRefNum); |
if (iErr != noErr) |
DoFatalAlert ("\pCant close file!"); |
return (fileHandle); |
} |
/***************** NUM TO HEX *****************/ |
// |
// NumToHex - fixed length, returns a C string |
// |
unsigned char *NumToHex(unsigned short n) |
{ |
static unsigned char format[] = "0xXXXX"; // Declare format static so we can return a pointer to it. |
char *conv = "0123456789ABCDEF"; |
short i; |
for (i = 0; i < 4; n >>= 4, ++i) |
format[5 - i] = conv[n & 0xf]; |
return format; |
} |
/***************** NUM TO HEX 2 **************/ |
// |
// NumToHex2 -- allows variable length, returns a ++PASCAL++ string. |
// |
unsigned char *NumToHex2(unsigned long n, short digits) |
{ |
static unsigned char format[] = "\p$XXXXXXXX"; // Declare format static so we can return a pointer to it |
char *conv = "0123456789ABCDEF"; |
unsigned long i; |
if (digits > 8 || digits < 0) |
digits = 8; |
format[0] = digits + 1; // adjust length byte of output string |
for (i = 0; i < digits; n >>= 4, ++i) |
format[(digits + 1) - i] = conv[n & 0xf]; |
return format; |
} |
/*************** NUM TO DECIMAL *****************/ |
// |
// NumToDecimal -- returns a ++PASCAL++ string. |
// |
unsigned char *NumToDec(unsigned long n) |
{ |
static unsigned char format[] = "\pXXXXXXXX"; // Declare format static so we can return a pointer to it |
char *conv = "0123456789"; |
short i,digits; |
unsigned long temp; |
if (n < 10) // fix digits |
digits = 1; |
else if (n < 100) |
digits = 2; |
else if (n < 1000) |
digits = 3; |
else if (n < 10000) |
digits = 4; |
else if (n < 100000) |
digits = 5; |
else |
digits = 6; |
format[0] = digits; // adjust length byte of output string |
for (i = 0; i < digits; ++i) |
{ |
temp = n/10; |
format[digits-i] = conv[n-(temp*10)]; |
n = n/10; |
} |
return format; |
} |
/*************** ABSOLUTE ********************/ |
float Absolute(float f) |
{ |
if (f < 0) |
return(-f); |
else |
return(f); |
} |
/******************** REGULATE SPEED ***************/ |
void RegulateSpeed(long speed) |
{ |
while ((TickCount() - gTick) < speed) // wait for 1 tick |
; |
gTick = TickCount(); // remember current time |
} |
/******************** MY RANDOM LONG **********************/ |
// |
// My own random number generator that returns a LONG |
// |
// NOTE: call this instead of MyRandomShort if the value is going to be |
// masked or if it just doesnt matter since this version is quicker |
// without the 0xffff at the end. |
// |
unsigned long MyRandomLong(void) |
{ |
return seed2 ^= (((seed1 ^= (seed2>>5)*1568397607UL)>>7)+ |
(seed0 = (seed0+1)*3141592621UL))*2435386481UL; |
} |
/**************** SET MY RANDOM SEED *******************/ |
void SetMyRandomSeed(unsigned long seed) |
{ |
seed0 = seed; |
seed1 = 0; |
seed2 = 0; |
} |
/************************* RANDOM RANGE *************************/ |
unsigned short RandomRange(unsigned short min, unsigned short max) |
{ |
register unsigned short qdRdm; // treat return value as 0-65536 |
register unsigned long range, t; |
qdRdm = MyRandomLong()&0xffff; |
range = max+1 - min; |
t = (qdRdm * range)>>16; // now 0 <= t <= range |
return( t+min ); |
} |
/******************* FLOAT TO STRING *******************/ |
void FloatToString(float num, Str255 string) |
{ |
Str255 sf; |
long i,f; |
i = num; // get integer part |
f = (fabs(num)-fabs((float)i)) * 10000; // reduce num to fraction only & move decimal --> 5 places |
if ((i==0) && (num < 0)) // special case if (-), but integer is 0 |
{ |
string[0] = 2; |
string[1] = '-'; |
string[2] = '0'; |
} |
else |
NumToString(i,string); // make integer into string |
NumToString(f,sf); // make fraction into string |
string[++string[0]] = '.'; // add "." into string |
if (f >= 1) |
{ |
if (f < 1000) |
string[++string[0]] = '0'; // add 1000's zero |
if (f < 100) |
string[++string[0]] = '0'; // add 100's zero |
if (f < 10) |
string[++string[0]] = '0'; // add 10's zero |
} |
for (i = 0; i < sf[0]; i++) |
{ |
string[++string[0]] = sf[i+1]; // copy fraction into string |
} |
} |
/****************** ALLOC HANDLE ********************/ |
Handle AllocHandle(long size) |
{ |
Handle hand; |
OSErr err; |
hand = NewHandle(size); // alloc in APPL |
if (hand == nil) |
{ |
hand = TempNewHandle(size,&err); // try TEMP mem |
if (hand == nil) |
{ |
return(NewHandleSys(size)); // use SYS |
} |
else |
return(hand); // use TEMP |
} |
else |
return(hand); // use APPL |
} |
/****************** ALLOC PTR ********************/ |
Ptr AllocPtr(long size) |
{ |
Ptr pr; |
pr = NewPtr(size); // alloc in APPL |
if (pr == nil) |
{ |
return(NewPtrSys(size)); // alloc in SYS |
} |
else |
return(pr); |
} |
/***************** ANGLE TO VECTOR ******************/ |
// |
// Returns a normalized 2D vector based on a radian angle |
// |
void AngleToVector(float angle, TQ3Vector2D *theVector) |
{ |
theVector->x = -sin(angle); |
theVector->y = -cos(angle); |
} |
/************************** VECTORS ARE CLOSE ENOUGH ****************************/ |
Boolean VectorsAreCloseEnough(TQ3Vector3D *v1, TQ3Vector3D *v2) |
{ |
if (fabs(v1->x - v2->x) < 0.04) |
if (fabs(v1->y - v2->y) < 0.04) |
if (fabs(v1->z - v2->z) < 0.04) |
return(true); |
return(false); |
} |
/************************** POINTS ARE CLOSE ENOUGH ****************************/ |
Boolean PointsAreCloseEnough(TQ3Point3D *v1, TQ3Point3D *v2) |
{ |
if (fabs(v1->x - v2->x) < 0.04) |
if (fabs(v1->y - v2->y) < 0.04) |
if (fabs(v1->z - v2->z) < 0.04) |
return(true); |
return(false); |
} |
/************************** UVS ARE CLOSE ENOUGH ****************************/ |
Boolean UVsAreCloseEnough(TQ3Param2D *v1, TQ3Param2D *v2) |
{ |
if (fabs(v1->u - v2->u) < 0.01) |
if (fabs(v1->v - v2->v) < 0.01) |
return(true); |
return(false); |
} |
/************* COPY PSTR **********************/ |
void CopyPStr(ConstStr255Param inSourceStr, StringPtr outDestStr) |
{ |
short dataLen = inSourceStr[0] + 1; |
BlockMoveData(inSourceStr, outDestStr, dataLen); |
outDestStr[0] = dataLen - 1; |
} |
Copyright © 2003 Apple Computer, Inc. All Rights Reserved. Terms of Use | Privacy Policy | Updated: 2003-01-14