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.
CreateDirWCustIcon.c
/* |
File: CreateDirWithCustomIcon.c |
Description:This snippet demonstrates how to create a directory and how to steal a custom |
icon from another directory by CatMoving the "Icon\r" file from the other |
directory. |
Author: VMC |
Copyright: Copyright: © 1996-1999 by Apple Computer, Inc. |
all rights reserved. |
Disclaimer: You may incorporate this sample code into your applications without |
restriction, though the sample code has been provided "AS IS" and the |
responsibility for its operation is 100% yours. However, what you are |
not permitted to do is to redistribute the source as "DSC Sample Code" |
after having made changes. If you're going to re-distribute the source, |
we require that you make it clear in the source that the code was |
descended from Apple Sample Code, but that you've made changes. |
Change History (most recent first): |
6/25/99 Updated for Metrowerks Codewarror Pro 2.1(KG) |
*/ |
#include <StandardFile.h> |
#include <Script.h> |
#include "CreateDirWCustIcon.h" |
/***** globals *****/ |
Boolean gQuitTheApp = false; /* true = quit program */ |
/***** main() *****/ |
void main() |
{ |
short sleepTime = 60; |
EventRecord myEvent; |
initApp(); /* call initialization routine */ |
setUpMenus(); |
do |
{ |
if (WaitNextEvent(everyEvent, &myEvent, sleepTime, NIL)) |
switch (myEvent.what) |
{ |
case mouseDown: |
doMousedown(&myEvent); |
break; |
case keyDown: |
case autoKey: |
doKey(&myEvent); |
break; |
case kHighLevelEvent: |
doHighLevel(&myEvent); |
break; |
case activateEvt: |
break; |
case updateEvt: |
doUpdate(&myEvent); |
break; |
case diskEvt: |
break; |
case osEvt: /* I don't really care yet. */ |
break; |
} |
} while (!gQuitTheApp); |
} /* end of main */ |
/***** initApp() *****/ |
void initApp() |
{ |
/* Memory specific initializations. */ |
MaxApplZone(); /* grow the heap to its maximum size */ |
MoreMasters(); /* create more master pointers */ |
MoreMasters(); |
MoreMasters(); |
MoreMasters(); |
MoreMasters(); |
/* Initializing the ROM Managers */ |
InitGraf((Ptr) &qd.thePort); |
InitFonts(); |
InitWindows(); |
InitMenus(); |
FlushEvents(everyEvent,0); |
TEInit(); |
InitDialogs(NIL); |
InitCursor(); |
if (!checkGestaltFeatures()) |
ExitToShell(); |
/* Install the required Apple Event Handlers */ |
if (!installAEHandlers()) |
ExitToShell(); |
} /* end of initApp() */ |
/***** checkGestaltFeatures() *****/ |
Boolean checkGestaltFeatures() |
{ |
long gestaltFeature; |
OSErr myErr; |
myErr = Gestalt(gestaltSystemVersion, &gestaltFeature); /* which SysVersion present? */ |
if (myErr == noErr) |
{ |
gestaltFeature = (gestaltFeature >> 8) & 0xf; |
/* shift result over & mask out major version number */ |
if (gestaltFeature < 7) /* This is a System 7+ shell. We quit otherwise. */ |
{ |
StopAlert(BADSYSTEMID, nil); |
return(false); |
} |
} |
if (myErr == noErr) |
{ |
myErr = Gestalt(gestaltQuickdrawVersion, &gestaltFeature); |
/* we want color QD cuz we're spoiled */ |
if (myErr == noErr) |
{ |
if(gestaltFeature < gestalt32BitQD) |
{ |
StopAlert(BADQUICKDRAWID, nil); |
return(false); |
} |
} |
} |
if (myErr == noErr) |
{ |
myErr = Gestalt(gestaltAppleEventsAttr, &gestaltFeature); |
if (myErr == noErr) |
{ |
if (!(gestaltFeature & 0xf)) |
{ |
StopAlert(NOAPPLEEVENTS, nil); |
return(false); |
} |
} |
} |
if (!myErr) |
return(true); /* if there was an error we cannot continue */ |
else |
{ |
return(false); /* we made it through without a hitch */ |
} |
} |
/***** installAEHandlers *****/ |
Boolean installAEHandlers() |
{ |
OSErr myErr; |
myErr = AEInstallEventHandler ( kCoreEventClass, |
kAEOpenApplication, NewAEEventHandlerProc(DoOpenAppAE), 0L, false ); |
if (myErr == noErr) |
myErr = AEInstallEventHandler ( kCoreEventClass, |
kAEOpenDocuments, NewAEEventHandlerProc(DoOpenDocAE), 0L, false ); |
if (myErr == noErr) |
myErr = AEInstallEventHandler ( kCoreEventClass, |
kAEPrintDocuments, NewAEEventHandlerProc(DoPrintDocAE), 0L, false ); |
if (myErr == noErr) |
myErr = AEInstallEventHandler ( kCoreEventClass, |
kAEQuitApplication, NewAEEventHandlerProc(DoQuitAppAE), 0L, false ); |
if (myErr) |
return(false); |
else |
return(true); |
} |
/***** setUpMenus() |
This will put up our menus. Be sure to read the comments by the |
AppendMenu() and SetItem() calls to see how different options |
behave. |
*****/ |
void setUpMenus() |
{ |
short n; |
MenuHandle theMenu; |
for (n = 0; n < MAXMENUS; n++) |
{ |
theMenu = GetMenu(FIRSTMENUID + n); |
if (theMenu) |
InsertMenu(theMenu, 0); |
} |
theMenu = GetMenuHandle(APPLEMENU); |
if (theMenu) |
AppendResMenu(theMenu, 'DRVR'); |
DrawMenuBar(); |
return; |
} /* end of setUpMenus() */ |
/***** setUpWindow() *****/ |
void setUpWindow( void ) |
{ |
WindowPtr myWind; |
myWind = GetNewCWindow(WINDOWID, nil, PUTINFRONT); |
if (myWind != nil) |
{ |
ShowWindow(myWind); |
} |
} |
/***** doMousedown() |
We figure out where the user has clicked the mouse. If the user |
clicks anywhere but the menu bar, we beep. Otherwise, we figure |
out which menu they have clicked and dispatch. |
*****/ |
void doMousedown(EventRecord *eventRec) |
{ |
short windPart; |
WindowPtr myWind; |
long menuResult; |
windPart = FindWindow(eventRec->where, &myWind); |
switch(windPart) |
{ |
case inContent: |
SelectWindow(myWind); |
break; |
case inDrag: |
DragWindow( myWind, eventRec->where, &qd.screenBits.bounds ); |
break; |
case inMenuBar: |
menuResult = MenuSelect(eventRec->where); |
dispatch(menuResult); |
break; |
case inSysWindow: |
SystemClick( eventRec, myWind ); |
break; |
case inGoAway: |
gQuitTheApp = true; |
break; |
default: |
break; |
} |
return; |
} /* end of doMousedown */ |
/***** doKey() |
We ignore keys pressed unless they are accompanied by a |
command key. Then we dispatch. |
*****/ |
void doKey(EventRecord *eventRec) |
{ |
char keyPressed; |
long menuResult; |
keyPressed = (char) (eventRec->message & charCodeMask); |
if((eventRec->modifiers & cmdKey) != 0) |
{ |
menuResult = MenuKey(keyPressed); |
dispatch(menuResult); |
} |
return; |
} /* end of do_key */ |
/***** doHighLevel() *****/ |
void doHighLevel(EventRecord *eventRec) |
{ |
OSErr myErr; |
myErr = AEProcessAppleEvent(eventRec); |
} |
pascal OSErr DoOpenAppAE(AppleEvent theAppleEvent, AppleEvent reply, long refCon) |
{ |
#pragma unused(theAppleEvent, reply, refCon) |
setUpWindow(); |
return(noErr); |
} |
pascal OSErr DoOpenDocAE(AppleEvent theAppleEvent, AppleEvent reply, long refCon) |
{ |
#pragma unused(theAppleEvent, reply, refCon) |
return(noErr); |
} |
pascal OSErr DoPrintDocAE(AppleEvent theAppleEvent, AppleEvent reply, long refCon) |
{ |
#pragma unused(theAppleEvent, reply, refCon) |
return(noErr); |
} |
pascal OSErr DoQuitAppAE(AppleEvent theAppleEvent, AppleEvent reply, long refCon) |
{ |
#pragma unused(theAppleEvent, reply, refCon) |
gQuitTheApp = true; |
return(noErr); |
} |
/***** doUpdate() *****/ |
void doUpdate(EventRecord *eventRec) |
{ |
GrafPtr savedPort; |
WindowPtr theWindow; |
theWindow = (WindowPtr) eventRec->message; |
GetPort(&savedPort); |
SetPort((GrafPtr) theWindow); |
BeginUpdate(theWindow); |
EndUpdate(theWindow); |
SetPort(savedPort); |
} |
/***** dispatch() |
We determine which menu the user has chosen (either with mouse |
or with command keys) and jump to the routine that handles |
that menu's commands. |
*****/ |
void dispatch(long menuResult) |
{ |
short theMenu; /* menu selected */ |
short theItem; /* item selected */ |
theMenu = HiWord (menuResult); /* menuID selected */ |
theItem = LoWord (menuResult); /* item# selected */ |
switch (theMenu) |
{ |
case APPLEMENU: |
doAppleCmds(theItem); |
break; |
case FILEMENU: |
doFileCmds(theItem); |
break; |
case EDITMENU: |
break; |
case TESTMENU: |
doTestCmds(theItem); |
break; |
} |
HiliteMenu(0); |
} /* end of dispatch */ |
/***** doAppleCmds() |
When the user chooses the "About MyMenuText" item, we display the |
About box. If the user chooses a DA, we open the DA. |
*****/ |
void doAppleCmds(short theItem) |
{ |
MenuHandle myMenu; |
Str255 name; |
short dummy; |
if(theItem == appleABOUT) |
{ |
Alert(ABOUTID, (ModalFilterUPP) NIL); |
} |
else |
{ |
myMenu = GetMenuHandle (APPLEMENU); |
if (myMenu) |
{ |
GetMenuItemText(myMenu, theItem, name); |
dummy = OpenDeskAcc(name); |
} |
} |
return; |
} /* end of doAppleCmds */ |
/***** doFileCmds() |
When the user chooses Quit on the File menu, we quit. |
*****/ |
void doFileCmds (short theItem) |
{ |
switch (theItem) |
{ |
case fileQUIT: |
gQuitTheApp = true; |
break; |
} |
return; |
} /* end of doFileCmds */ |
/***** doTestCmds() |
When the user chooses the item in the Test menu, they |
will get to choose a folder with a custom icon |
*****/ |
void doTestCmds (short theItem) |
{ |
StandardFileReply reply; |
FSSpec spec; |
OSErr err; |
switch (theItem) |
{ |
case testDOTHETEST: |
//open a folder with a custom icon and choose the "Icon\r" file |
StandardGetFile(nil, -1, nil, &reply); |
if (reply.sfGood) |
{ |
//make an FSSpec to the "Icon\r" file |
err = FSMakeFSSpec(reply.sfFile.vRefNum, reply.sfFile.parID, |
reply.sfFile.name, &spec); |
if (!err) |
makeCustomIconFolder(&spec); |
} |
break; |
} |
return; |
} /* end of doTestCmds */ |
#define HAS_CUST_ICON 0x0400 |
#define HAS_BEEN_INIT 0x0100 |
void makeCustomIconFolder(FSSpec *iconFileSpec) |
{ |
OSErr err; |
FSSpec foldSpec; |
long dirID; |
CInfoPBRec pb; |
/* |
Make an FSSpec for the directory we're creating |
For demo purposes, we'll put this in the root directory |
of the boot volume. |
*/ |
err = FSMakeFSSpec(-1, fsRtDirID, "\pNew Folder", &foldSpec); |
/* Since the folder doesn't exist, we should get fnfErr */ |
if (err == fnfErr) |
{ |
//create the the directory |
err = FSpDirCreate(&foldSpec, smSystemScript, &dirID); |
if (!err) |
{ |
pb.dirInfo.ioCompletion = nil; |
pb.dirInfo.ioNamePtr = "\pNew Folder"; // we care about file names |
pb.dirInfo.ioVRefNum = foldSpec.vRefNum; |
pb.dirInfo.ioFDirIndex = 0; // use ioNamePtr |
pb.dirInfo.ioDrDirID = foldSpec.parID; |
err = PBGetCatInfoSync(&pb); |
//set the custom icon flag bit in the DInfo record for the new folder |
if (!err) |
{ |
if ( (pb.dirInfo.ioDrUsrWds.frFlags & HAS_CUST_ICON) == 0) |
{ |
pb.dirInfo.ioDrUsrWds.frFlags |= HAS_CUST_ICON; |
/* turn this bit on */ |
pb.dirInfo.ioDrUsrWds.frFlags &= ~HAS_BEEN_INIT; |
/* turn this bit off */ |
} |
/* |
PBGetCatInfo messes up the dirID field in parameter block |
so we have to reset it. |
*/ |
pb.dirInfo.ioDrDirID = foldSpec.parID; |
err = PBSetCatInfoSync(&pb); // set the hasCustomIcon flag |
//Move the icon file into the new folder |
if (!err) |
{ |
/* |
Move our invisible Icon file ("\pIcon\r") |
into our new folder. |
*/ |
err = FSpCatMove(iconFileSpec, &foldSpec); |
if (!err) |
{ |
/* |
Do a Mod Date Bump to get Finder to update cache |
Note: Because the Finder caches information about |
open windows, you might need to use the BumpDate |
routine from MoreFiles |
*/ |
} |
} |
} |
} |
} |
return; |
} |
Copyright © 2003 Apple Computer, Inc. All Rights Reserved. Terms of Use | Privacy Policy | Updated: 2003-07-22