sys7.1-doc-wip/Toolbox/ComponentMgr/ThingFiles.c
2020-05-10 13:37:38 +08:00

283 lines
6.6 KiB
C
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/*
Hacks to match MacOS (most recent first):
<Sys7.1> 8/3/92 Elliot make this change
9/2/94 SuperMario ROM source dump (header preserved below)
*/
/*
File: ThingFiles.c
Copyright: © 1991-1993 by Apple Computer, Inc., all rights reserved.
Change History (most recent first):
<SM4> 8/5/93 JDR integrate Component Mgr from Reality
<8> 6/13/93 JDR Rolled in the ComponentMgr sources from QuickTime 1.6.
<7> 5/29/92 DCL Included TextUtils.h. RelString moved there for the New Inside
Mac.
<6> 12/12/91 DTY #1018054: If _HomeResFile returns 0 in _FSSpecFromResource, use
the file reference number in SysMap instead.
<5> 12/6/91 YK Removed System6 conditionals. Object compare identical to <4>.
<4> 12/5/91 YK Rolled in QuickTime GM:
<3> 11/6/91 YK Corrected comments. I misunderstood revision number.
<2> 11/6/91 YK Replaced code with System 7 trap. Added code for 'thng' in
System file. Removed unnecessary include statement.
<3> 5/18/91 dvb Thing->Component
<2> 5/2/91 BAL Updated to latest think headers
<1> 3/28/91 BAL first checked in
To Do:
*/
#include <Files.h>
#include <Resources.h>
#include <Memory.h>
#include <SysEqu.h>
#include <TextUtils.h>
#include <Errors.h>
#include <Icons.h>
#include "PrivateThingManager.h"
OSErr GrowRTFileTable(short growCount);
OSErr _FSSpecFromResource( Handle h, FSSpec *fileSpec )
{
OSErr error = 0;
FCBPBRec anFCB;
Str255 fName;
short fref;
fref = HomeResFile( h );
if (fref < 0) return ResError();
if (fref == 0) // <6> Convert a reference number
fref = *(short *)SysMap; // <6> of 0 to the system files refNum.
anFCB.ioCompletion = 0;
anFCB.ioVRefNum = 0;
anFCB.ioRefNum = fref;
anFCB.ioFCBIndx = 0;
fName[0] = 0;
anFCB.ioNamePtr = (StringPtr)fName;
if (error = PBGetFCBInfoSync( &anFCB )) goto bail;
error = FSMakeFSSpec( anFCB.ioFCBVRefNum, anFCB.ioFCBParID, anFCB.ioNamePtr, fileSpec);
bail:
return (error);
}
Boolean FSSpecEqual( register FSSpec *fileSpecA, register FSSpec *fileSpecB )
{
return ((fileSpecA->vRefNum == fileSpecB->vRefNum)
&& (fileSpecA->parID == fileSpecB->parID)
&& !RelString(fileSpecA->name,fileSpecB->name,false,true));
}
short AddComponentFSSpec( FSSpec *fspec )
{
register rtFile *rtFileList = ComponentManagerGlobals->rtFileTable;
register short i, empty;
register short count = ComponentManagerGlobals->rtFileTotalCount;
/* first check to see if it's already there */
for (i=0; i<count; i++) {
if (rtFileList->vRefNum)
{
// this entry contains an FSSpec handle, not a file id
if ( FSSpecEqual((FSSpec *)(&rtFileList->vRefNum), fspec) )
{
rtFileList->referenceCount++;
return i;
}
}
else
empty = i;
rtFileList++;
}
rtFileList = ComponentManagerGlobals->rtFileTable + empty;
BlockMove((Ptr)fspec, (Ptr)(&rtFileList->vRefNum), sizeof(FSSpec));
rtFileList->referenceCount = 1;
ComponentManagerGlobals->rtFileUsedCount++;
return empty;
}
OSErr GrowRTFileTable( short growCount )
/*
* Grow the table of registered thing files.
*/
{
register rtFile *aTable;
rtFile *oldTable, *newTable;
long oldTableSize;
oldTableSize = ComponentManagerGlobals->rtFileTotalCount * sizeof(rtFile);
oldTable = ComponentManagerGlobals->rtFileTable;
newTable = aTable = (rtFile *)NewPtrSysClear( oldTableSize + (long)growCount * sizeof(rtFile));
if (!aTable)
return MemError();
BlockMove((Ptr)oldTable, (Ptr)aTable, oldTableSize);
ComponentManagerGlobals->rtFileTable = newTable; /* begin using new table */
ComponentManagerGlobals->rtFileTotalCount += growCount;
if (oldTable)
DisposPtr((Ptr)oldTable); /* dump the old one */
return 0;
}
rtFileNum AddComponentResFile( Handle h )
{
FSSpec fspec;
if (ComponentManagerGlobals->rtFileUsedCount >= ComponentManagerGlobals->rtFileTotalCount) {
if(GrowRTFileTable(1)) return -1;
}
if (_FSSpecFromResource( h, &fspec ))
return -1;
return AddComponentFSSpec(&fspec);
}
OSErr RemoveComponentResFile( rtFileNum fn )
{
register rtFile *rtFileList;
/* first check to see if it's a valid file number */
if ((fn < 0) || (fn >= ComponentManagerGlobals->rtFileTotalCount))
return -1;
rtFileList = ComponentManagerGlobals->rtFileTable + fn;
if (!--rtFileList->referenceCount)
{
// since the reference count went to zero, this spot is free
rtFileList->vRefNum = 0;
ComponentManagerGlobals->rtFileUsedCount--;
}
return 0;
}
typedef struct getIconRecord {
Component c;
short resID;
} getIconRecord;
static pascal OSErr GetIconFromResource(ResType theType, Handle *theIcon, getIconRecord *refCon)
{
OSErr err;
Handle h;
if (!refCon->resID)
h = nil; // no icon suite, but fake it for the 1-bit icon case
else {
h = Get1Resource(theType, refCon->resID);
err = ResError();
}
if (!h || (err == -192)) {
if (theType == 'ICN#') {
// just get the old style component icon instead
Handle h = NewHandle(128);
GetComponentInfo(refCon->c, nil, nil, nil, h);
if (!h || !*h)
DisposHandle(h);
else
*theIcon = h;
}
return noErr;
}
if (err) return err;
LoadResource(h);
if (err = ResError()) return err;
DetachResource(h);
if (err = ResError()) return err;
*theIcon = h;
HNoPurge(*theIcon);
return noErr;
}
pascal OSErr __GetComponentIconSuite(Component aComponent, Handle *iconSuite)
{
register RegisteredComponent *rt;
OSErr err;
short resref = -1;
short saveRes;
short suiteID = 0;
getIconRecord refCon;
*iconSuite = nil;
if( ! (rt = ValidComponent(aComponent)) )
return invalidComponentID; /* error : not a valid component ID */
if (rt->rtFlags & rtfHasIconSuite) {
Handle h;
ComponentResourceExtension *cre;
// open the thing's resource file
saveRes = CurResFile();
resref = OpenComponentResFile(aComponent);
if (resref == -1)
return resNotFound;
// get the thing resource which points to the suite
h = Get1Resource(rt->rtResourceType, rt->rtResourceID);
if (err = ResError()) goto bail;
LoadResource(h);
if (err = ResError()) goto bail;
cre = (ComponentResourceExtension *)((long)*h + sizeof(ComponentResource));
suiteID = cre->componentIconFamily;
ReleaseResource(h); // we're done with this
}
// use the Icon Suite Manager stuff to load up the icon suite (can't use GetIconSuite
// because it won't detach the resources for us)
err = NewIconSuite(iconSuite);
if (err) goto bail;
refCon.resID = suiteID;
refCon.c = aComponent;
err = ForEachIconDo(*iconSuite, -1, (IconAction)GetIconFromResource, &refCon);
bail:
if (resref != -1) {
CloseComponentResFile(resref);
UseResFile(saveRes);
}
if (err && *iconSuite) {
DisposeIconSuite(*iconSuite, true);
*iconSuite = nil;
}
return err;
}