File indexing completed on 2025-11-09 07:56:17
0001 /* 0002 * This file is part of Krita 0003 * 0004 * SPDX-FileCopyrightText: 2015 Algorithmus <angelus.tenebrae@gmail.com> 0005 * SPDX-FileCopyrightText: 2015 beelzy <alvina.lee@innoactive.de> 0006 * SPDX-FileCopyrightText: 2020 L. E. Segovia <amy@amyspark.me> 0007 * 0008 * SPDX-License-Identifier: GPL-2.0-or-later 0009 * 0010 */ 0011 0012 /* clang-format off */ 0013 0014 //============================================================================== 0015 // 0016 // DO NO MODIFY THE CONTENT OF THIS FILE 0017 // 0018 // This file contains the generic CFPlug-in code necessary for your generator 0019 // To complete your generator implement the function in GenerateThumbnailForURL/GeneratePreviewForURL.c 0020 // 0021 //============================================================================== 0022 0023 0024 0025 0026 0027 0028 #include <CoreFoundation/CoreFoundation.h> 0029 #include <CoreFoundation/CFPlugInCOM.h> 0030 #include <CoreServices/CoreServices.h> 0031 #include <QuickLook/QuickLook.h> 0032 0033 // ----------------------------------------------------------------------------- 0034 // constants 0035 // ----------------------------------------------------------------------------- 0036 0037 // Don't modify this line 0038 #define PLUGIN_ID "292DC9CD-1640-49AE-B0C1-308ED88E6677" 0039 0040 // 0041 // Below is the generic glue code for all plug-ins. 0042 // 0043 // You should not have to modify this code aside from changing 0044 // names if you decide to change the names defined in the Info.plist 0045 // 0046 0047 0048 // ----------------------------------------------------------------------------- 0049 // typedefs 0050 // ----------------------------------------------------------------------------- 0051 0052 // The thumbnail generation function to be implemented in GenerateThumbnailForURL.c 0053 OSStatus GenerateThumbnailForURL(void *thisInterface, QLThumbnailRequestRef thumbnail, CFURLRef url, CFStringRef contentTypeUTI, CFDictionaryRef options, CGSize maxSize); 0054 void CancelThumbnailGeneration(void* thisInterface, QLThumbnailRequestRef thumbnail); 0055 0056 // The preview generation function to be implemented in GeneratePreviewForURL.c 0057 OSStatus GeneratePreviewForURL(void *thisInterface, QLPreviewRequestRef preview, CFURLRef url, CFStringRef contentTypeUTI, CFDictionaryRef options); 0058 void CancelPreviewGeneration(void *thisInterface, QLPreviewRequestRef preview); 0059 0060 // The layout for an instance of QuickLookGeneratorPlugIn 0061 typedef struct __QuickLookGeneratorPluginType 0062 { 0063 void *conduitInterface; 0064 CFUUIDRef factoryID; 0065 UInt32 refCount; 0066 } QuickLookGeneratorPluginType; 0067 0068 // ----------------------------------------------------------------------------- 0069 // prototypes 0070 // ----------------------------------------------------------------------------- 0071 // Forward declaration for the IUnknown implementation. 0072 // 0073 0074 QuickLookGeneratorPluginType *AllocQuickLookGeneratorPluginType(CFUUIDRef inFactoryID); 0075 void DeallocQuickLookGeneratorPluginType(QuickLookGeneratorPluginType *thisInstance); 0076 HRESULT QuickLookGeneratorQueryInterface(void *thisInstance,REFIID iid,LPVOID *ppv); 0077 void *QuickLookGeneratorPluginFactory(CFAllocatorRef allocator,CFUUIDRef typeID); 0078 ULONG QuickLookGeneratorPluginAddRef(void *thisInstance); 0079 ULONG QuickLookGeneratorPluginRelease(void *thisInstance); 0080 0081 // ----------------------------------------------------------------------------- 0082 // myInterfaceFtbl definition 0083 // ----------------------------------------------------------------------------- 0084 // The QLGeneratorInterfaceStruct function table. 0085 // 0086 static QLGeneratorInterfaceStruct myInterfaceFtbl = { 0087 NULL, 0088 QuickLookGeneratorQueryInterface, 0089 QuickLookGeneratorPluginAddRef, 0090 QuickLookGeneratorPluginRelease, 0091 NULL, 0092 NULL, 0093 NULL, 0094 NULL 0095 }; 0096 0097 0098 // ----------------------------------------------------------------------------- 0099 // AllocQuickLookGeneratorPluginType 0100 // ----------------------------------------------------------------------------- 0101 // Utility function that allocates a new instance. 0102 // You can do some initial setup for the generator here if you wish 0103 // like allocating globals etc... 0104 // 0105 QuickLookGeneratorPluginType *AllocQuickLookGeneratorPluginType(CFUUIDRef inFactoryID) 0106 { 0107 QuickLookGeneratorPluginType *theNewInstance; 0108 0109 theNewInstance = (QuickLookGeneratorPluginType *)malloc(sizeof(QuickLookGeneratorPluginType)); 0110 memset(theNewInstance,0,sizeof(QuickLookGeneratorPluginType)); 0111 0112 /* Point to the function table Malloc enough to store the stuff and copy the filler from myInterfaceFtbl over */ 0113 theNewInstance->conduitInterface = malloc(sizeof(QLGeneratorInterfaceStruct)); 0114 memcpy(theNewInstance->conduitInterface,&myInterfaceFtbl,sizeof(QLGeneratorInterfaceStruct)); 0115 0116 /* Retain and keep an open instance refcount for each factory. */ 0117 theNewInstance->factoryID = CFRetain(inFactoryID); 0118 CFPlugInAddInstanceForFactory(inFactoryID); 0119 0120 /* This function returns the IUnknown interface so set the refCount to one. */ 0121 theNewInstance->refCount = 1; 0122 return theNewInstance; 0123 } 0124 0125 // ----------------------------------------------------------------------------- 0126 // DeallocQuickLookGeneratorPluginType 0127 // ----------------------------------------------------------------------------- 0128 // Utility function that deallocates the instance when 0129 // the refCount goes to zero. 0130 // In the current implementation generator interfaces are never deallocated 0131 // but implement this as this might change in the future 0132 // 0133 void DeallocQuickLookGeneratorPluginType(QuickLookGeneratorPluginType *thisInstance) 0134 { 0135 CFUUIDRef theFactoryID; 0136 0137 theFactoryID = thisInstance->factoryID; 0138 /* Free the conduitInterface table up */ 0139 free(thisInstance->conduitInterface); 0140 0141 /* Free the instance structure */ 0142 free(thisInstance); 0143 if (theFactoryID){ 0144 CFPlugInRemoveInstanceForFactory(theFactoryID); 0145 CFRelease(theFactoryID); 0146 } 0147 } 0148 0149 // ----------------------------------------------------------------------------- 0150 // QuickLookGeneratorQueryInterface 0151 // ----------------------------------------------------------------------------- 0152 // Implementation of the IUnknown QueryInterface function. 0153 // 0154 HRESULT QuickLookGeneratorQueryInterface(void *thisInstance,REFIID iid,LPVOID *ppv) 0155 { 0156 CFUUIDRef interfaceID; 0157 0158 interfaceID = CFUUIDCreateFromUUIDBytes(kCFAllocatorDefault,iid); 0159 0160 if (CFEqual(interfaceID,kQLGeneratorCallbacksInterfaceID)){ 0161 /* If the Right interface was requested, bump the ref count, 0162 * set the ppv parameter equal to the instance, and 0163 * return good status. 0164 */ 0165 ((QLGeneratorInterfaceStruct *)((QuickLookGeneratorPluginType *)thisInstance)->conduitInterface)->GenerateThumbnailForURL = GenerateThumbnailForURL; 0166 ((QLGeneratorInterfaceStruct *)((QuickLookGeneratorPluginType *)thisInstance)->conduitInterface)->CancelThumbnailGeneration = CancelThumbnailGeneration; 0167 ((QLGeneratorInterfaceStruct *)((QuickLookGeneratorPluginType *)thisInstance)->conduitInterface)->GeneratePreviewForURL = GeneratePreviewForURL; 0168 ((QLGeneratorInterfaceStruct *)((QuickLookGeneratorPluginType *)thisInstance)->conduitInterface)->CancelPreviewGeneration = CancelPreviewGeneration; 0169 ((QLGeneratorInterfaceStruct *)((QuickLookGeneratorPluginType*)thisInstance)->conduitInterface)->AddRef(thisInstance); 0170 *ppv = thisInstance; 0171 CFRelease(interfaceID); 0172 return S_OK; 0173 }else{ 0174 /* Requested interface unknown, bail with error. */ 0175 *ppv = NULL; 0176 CFRelease(interfaceID); 0177 return E_NOINTERFACE; 0178 } 0179 } 0180 0181 // ----------------------------------------------------------------------------- 0182 // QuickLookGeneratorPluginAddRef 0183 // ----------------------------------------------------------------------------- 0184 // Implementation of reference counting for this type. Whenever an interface 0185 // is requested, bump the refCount for the instance. NOTE: returning the 0186 // refcount is a convention but is not required so don't rely on it. 0187 // 0188 ULONG QuickLookGeneratorPluginAddRef(void *thisInstance) 0189 { 0190 ((QuickLookGeneratorPluginType *)thisInstance )->refCount += 1; 0191 return ((QuickLookGeneratorPluginType*) thisInstance)->refCount; 0192 } 0193 0194 // ----------------------------------------------------------------------------- 0195 // QuickLookGeneratorPluginRelease 0196 // ----------------------------------------------------------------------------- 0197 // When an interface is released, decrement the refCount. 0198 // If the refCount goes to zero, deallocate the instance. 0199 // 0200 ULONG QuickLookGeneratorPluginRelease(void *thisInstance) 0201 { 0202 ((QuickLookGeneratorPluginType*)thisInstance)->refCount -= 1; 0203 if (((QuickLookGeneratorPluginType*)thisInstance)->refCount == 0){ 0204 DeallocQuickLookGeneratorPluginType((QuickLookGeneratorPluginType*)thisInstance ); 0205 return 0; 0206 }else{ 0207 return ((QuickLookGeneratorPluginType*) thisInstance )->refCount; 0208 } 0209 } 0210 0211 // ----------------------------------------------------------------------------- 0212 // QuickLookGeneratorPluginFactory 0213 // ----------------------------------------------------------------------------- 0214 void *QuickLookGeneratorPluginFactory(CFAllocatorRef allocator,CFUUIDRef typeID) 0215 { 0216 QuickLookGeneratorPluginType *result; 0217 CFUUIDRef uuid; 0218 0219 /* If correct type is being requested, allocate an 0220 * instance of kQLGeneratorTypeID and return the IUnknown interface. 0221 */ 0222 if (CFEqual(typeID,kQLGeneratorTypeID)){ 0223 uuid = CFUUIDCreateFromString(kCFAllocatorDefault,CFSTR(PLUGIN_ID)); 0224 result = AllocQuickLookGeneratorPluginType(uuid); 0225 CFRelease(uuid); 0226 return result; 0227 } 0228 /* If the requested type is incorrect, return NULL. */ 0229 return NULL; 0230 } 0231