Objective c 如何使用Cocoa标记文件和文件夹
我想用一些颜色(图像)标记文件和文件夹。如何做到这一点 我尝试了图标服务,它适用于文件,但不适用于文件夹 我看到这个行为在起作用(10.4、10.5和10.6)-这是怎么做到的 这篇博文对我来说非常贴切,但并没有达到预期效果Objective c 如何使用Cocoa标记文件和文件夹,objective-c,cocoa,macos,Objective C,Cocoa,Macos,我想用一些颜色(图像)标记文件和文件夹。如何做到这一点 我尝试了图标服务,它适用于文件,但不适用于文件夹 我看到这个行为在起作用(10.4、10.5和10.6)-这是怎么做到的 这篇博文对我来说非常贴切,但并没有达到预期效果 除了图标服务还有其他解决方案吗?您可以使用NSWorkspace上的-setIcon:forFile:options:方法执行此操作,该方法允许您在指定的路径上指定要应用于文件/文件夹的NSImage。以下函数是我找到的解决此问题的方法 BOOL AddBadgeToIte
除了图标服务还有其他解决方案吗?您可以使用NSWorkspace上的
-setIcon:forFile:options:
方法执行此操作,该方法允许您在指定的路径上指定要应用于文件/文件夹的NSImage。以下函数是我找到的解决此问题的方法
BOOL AddBadgeToItem(NSString* path,NSData* tag)
{
FSCatalogInfo info;
FSRef par;
FSRef ref;
Boolean dir = false;
if (tag&&(FSPathMakeRef([path fileSystemRepresentation],&par,&dir)==noErr))
{
HFSUniStr255 fork = {0,{0}};
sint16 refnum = kResFileNotOpened;
FSGetResourceForkName(&fork);
if (dir)
{
NSString *name = @"Icon\r";
memset(&info,0,sizeof(info));
((FileInfo*)(&info.finderInfo))->finderFlags = kIsInvisible;
OSErr error = FSCreateResourceFile(&par,[name lengthOfBytesUsingEncoding:NSUTF16LittleEndianStringEncoding],(UniChar*)[name cStringUsingEncoding:NSUTF16LittleEndianStringEncoding],kFSCatInfoFinderXInfo,&info,fork.length, fork.unicode,&ref,NULL);
if( error == dupFNErr )
{
// file already exists; prepare to try to open it
const char *iconFileSystemPath = [[path stringByAppendingPathComponent:@"\000I\000c\000o\000n\000\r"] fileSystemRepresentation];
OSStatus status = FSPathMakeRef((const UInt8 *)iconFileSystemPath, &ref, NULL);
if (status != noErr)
{
fprintf(stderr, "error: FSPathMakeRef() returned %d for file \"%s\"\n", (int)status, iconFileSystemPath);
}
}else if ( error != noErr)
{
return NO;
}
}
else
{
BlockMoveData(&par,&ref,sizeof(FSRef));
if (FSCreateResourceFork(&ref,fork.length,fork.unicode,0)!=noErr)
{
//test
if (FSOpenResourceFile(&ref,fork.length,fork.unicode,fsRdWrPerm,&refnum)!=noErr) {
return NO;
}
if (refnum!=kResFileNotOpened) {
UpdateResFile(refnum);
CloseResFile(refnum);
if (FSGetCatalogInfo(&par,kFSCatInfoFinderXInfo,&info,NULL,NULL,NULL)==noErr) {
((ExtendedFileInfo*)(&info.extFinderInfo))->extendedFinderFlags = kExtendedFlagsAreInvalid;
FSSetCatalogInfo(&par,kFSCatInfoFinderXInfo,&info);
}
}
//Test end
return NO;
}
}
OSErr errorr = FSOpenResourceFile(&ref,fork.length,fork.unicode,fsRdWrPerm,&refnum);
if (errorr!=noErr) {
return NO;
}
if (refnum!=kResFileNotOpened) {
CustomBadgeResource* cbr;
int len = [tag length];
Handle h = NewHandle(len);
if (h) {
BlockMoveData([tag bytes],*h,len);
AddResource(h,kIconFamilyType,128,"\p");
WriteResource(h);
ReleaseResource(h);
}
h = NewHandle(sizeof(CustomBadgeResource));
if (h) {
cbr = (CustomBadgeResource*)*h;
memset(cbr,0,sizeof(CustomBadgeResource));
cbr->version = kCustomBadgeResourceVersion;
cbr->customBadgeResourceID = 128;
AddResource(h,kCustomBadgeResourceType,kCustomBadgeResourceID,"\p");
WriteResource(h);
ReleaseResource(h);
}
UpdateResFile(refnum);
CloseResFile(refnum);
if (FSGetCatalogInfo(&par,kFSCatInfoFinderXInfo,&info,NULL,NULL,NULL)==noErr) {
((ExtendedFileInfo*)(&info.extFinderInfo))->extendedFinderFlags = kExtendedFlagHasCustomBadge;
FSSetCatalogInfo(&par,kFSCatInfoFinderXInfo,&info);
}
}
}
return NO;
}
预期的方法是创建一个。我得到了解决方案:为文件夹中的徽章图标添加一个资源叉,并将其作为文件夹图标的徽章加载。注意:资源分叉名称应以“\r”结尾。您介意添加一个答案并显示您所做的吗?我很想看看。谢谢@Dave DeLong请找到我的解决方案,给出以下信息,传递您想要标记的文件夹路径,并从标记图标中获取数据。如果您希望此代码在PPC中工作,则此代码仅在intel中工作。请替换对PPC使用“NSUTF16LittleEndianStringEncoding”。希望你觉得这段代码有用。嗨,女孩,我正试图用一个附件图标徽章来标记finder中的文件夹,但到目前为止没有成功。我尝试了这段代码,但结果是文件夹中有一个名为“Icon”的文件。知道我做错了什么吗?谢谢@Joe Ricioppo:图标文件资源分叉作为徽章文件夹的一部分创建。@JoeRicioppo我也面临同样的问题。代码运行时没有任何错误,但什么也没有发生。你是如何解决这个问题的???仍然对它感到好奇,你们知道它是有效的吗?