Ios 用Quartz解析PDF文档

Ios 用Quartz解析PDF文档,ios,objective-c,pdf,quartz-2d,Ios,Objective C,Pdf,Quartz 2d,我试图用Quartz框架解析PDF文档,并将Apple文档中的代码片段复制粘贴到我的源代码中。 不幸的是,它无法检索任何数据。它只是迭代页面,将当前页面的编号记录到控制台,最后崩溃。 你知道代码有什么问题吗 static void op_MP (CGPDFScannerRef s, void *info) { const char *name; if (!CGPDFScannerPopName(s, &name)) return; printf

我试图用Quartz框架解析PDF文档,并将Apple文档中的代码片段复制粘贴到我的源代码中。 不幸的是,它无法检索任何数据。它只是迭代页面,将当前页面的编号记录到控制台,最后崩溃。 你知道代码有什么问题吗

static void op_MP (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;

    printf("MP /%s\n", name);
}

static void op_DP (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;

     NSLog(@"DP /%s\n", name);
}

static void op_BMC (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;

    NSLog(@"BMC /%s\n", name);
}

static void op_BDC (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;
     NSLog(@"BDC /%s\n", name);
}

static void op_EMC (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;

     NSLog(@"EMC /%s\n", name);
}

static void op_TJ (CGPDFScannerRef s, void *info)
{
    const char *name;

    if (!CGPDFScannerPopName(s, &name))
        return;

     NSLog(@"TJ /%s\n", name);
}

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    CGPDFDocumentRef myDocument;
    NSString *urlAddress = [[NSBundle mainBundle] pathForResource:@"test" ofType:@"pdf"];
    NSURL *fileUrl = [NSURL fileURLWithPath:urlAddress];
    CFURLRef url = (__bridge CFURLRef)fileUrl;
    myDocument = CGPDFDocumentCreateWithURL(url);

    CFRelease (url);

    if (myDocument == NULL) {// 2
        NSLog(@"can't open `%@'.", fileUrl);
     }
    if (!CGPDFDocumentIsUnlocked (myDocument)) {// 4
         CGPDFDocumentRelease(myDocument);
    }
    else if (CGPDFDocumentGetNumberOfPages(myDocument) == 0) {// 5
        CGPDFDocumentRelease(myDocument);
    }
    else {
        CGPDFOperatorTableRef myTable;
        myTable = CGPDFOperatorTableCreate();

        CGPDFOperatorTableSetCallback (myTable, "MP", &op_MP);
        CGPDFOperatorTableSetCallback (myTable, "DP", &op_DP);
        CGPDFOperatorTableSetCallback (myTable, "BMC", &op_BMC);
        CGPDFOperatorTableSetCallback (myTable, "BDC", &op_BDC);
        CGPDFOperatorTableSetCallback (myTable, "EMC", &op_EMC);
        CGPDFOperatorTableSetCallback (myTable, "Tj", &op_TJ);

        int k;
        CGPDFPageRef myPage;
        CGPDFScannerRef myScanner;
        CGPDFContentStreamRef myContentStream;

        int numOfPages = CGPDFDocumentGetNumberOfPages (myDocument);// 1
        for (k = 0; k < numOfPages; k++) {
            myPage = CGPDFDocumentGetPage (myDocument, k + 1 );// 2
            myContentStream = CGPDFContentStreamCreateWithPage (myPage);// 3
            myScanner = CGPDFScannerCreate (myContentStream, myTable, NULL);// 4
            CGPDFScannerScan (myScanner);// 5
            CGPDFPageRelease (myPage);// 6
            CGPDFScannerRelease (myScanner);// 7
            CGPDFContentStreamRelease (myContentStream);// 8
            NSLog(@"processed page %i",k);
        }
        CGPDFOperatorTableRelease(myTable);
        CGPDFDocumentRelease(myDocument);
    }

    return YES;
}
static void op\u MP(CGPDFScannerRef s,void*info)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
printf(“MP/%s\n”,名称);
}
静态无效操作DP(CGPDFScannerRef s,无效*信息)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
NSLog(@“DP/%s\n”,名称);
}
静态无效操作单元BMC(CGPDFScannerRef s,无效*信息)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
NSLog(@“BMC/%s\n”,名称);
}
静态无效操作BDC(CGPDFScannerRef s,无效*信息)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
NSLog(@“BDC/%s\n”,名称);
}
静态void op_EMC(CGPDFScannerRef s,void*info)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
NSLog(@“EMC/%s\n”,名称);
}
静态无效操作(CGPDFScannerRef s,无效*信息)
{
常量字符*名称;
如果(!CGPDFScannerPopName,&name))
返回;
NSLog(@“TJ/%s\n”,名称);
}
-(BOOL)应用程序:(UIApplication*)应用程序使用选项完成启动:(NSDictionary*)启动选项
{
CGPDFDocumentRef myDocument;
NSString*urlAddress=[[NSBundle mainBundle]pathForResource:@“test”类型:@“pdf”];
NSURL*fileUrl=[NSURL fileURLWithPath:urlAddress];
CFURLRef url=(uu桥CFURLRef)文件url;
myDocument=CGPDFDocumentCreateWithURL(url);
CFRelease(url);
如果(myDocument==NULL){//2
NSLog(@“无法打开“%@.”,fileUrl);
}
如果(!CGPDFDocumentIsUnlocked(myDocument)){//4
CGPDFDocumentRelease(myDocument);
}
else如果(CGPDFDocumentGetNumberOfPages(myDocument)==0{//5
CGPDFDocumentRelease(myDocument);
}
否则{
CGPDFOOperatorTableRef myTable;
myTable=CGPDFOperatorTableCreate();
cgpdfopperatortablesetcallback(myTable,“MP”和op_-MP);
CGPDFOOperatorTableSetCallback(myTable,“DP”和op_DP);
CGPDFOOperatorTableSetCallback(myTable,“BMC”和op_BMC);
CGPDFOOperatorTableSetCallback(myTable,“BDC”和op_BDC);
CGPDFOOperatorTableSetCallback(myTable,“EMC”和op_EMC);
CGPDFOOperatorTableSetCallback(myTable,“Tj”和op_Tj);
int k;
CGPDFPageRef myPage;
CGPDFScannerRef myScanner;
CGPDFContentStreamRef myContentStream;
int numopages=CGPDFDocumentGetNumberOfPages(myDocument);//1
对于(k=0;k
虽然我无法为您的示例代码崩溃提供解决方案,但上次我们需要这样做时,我们将解析器基于PDFKitten

如果您对解析代码感兴趣,那么有趣的内容位于Scanner.m:


考虑到PDF解析的复杂性,我建议以这个库为基础,并从那里开始。如果您在截止日期前需要一个完善的实现,那么PSPDFKit可能是开发最完善(但最昂贵)的包。

虽然我无法为您的示例代码崩溃提供解决方案,但上次我们需要这样做时,我们的解析器基于PDFKitten

如果您对解析代码感兴趣,那么有趣的内容位于Scanner.m:


考虑到PDF解析的复杂性,我建议以这个库为基础,并从那里开始。如果您在截止日期前需要一个完善的实现,那么PSPDFKit可能是开发最完善(但最昂贵)的包。

我没有运行代码,但前5个操作符可能不存在于您的页面内容中。另外,其中一些具有名称操作数,一些没有任何操作数(如EMC)。Tj运算符还有一个字符串操作数,而不是名称。

删除所有pop name方法,只保留日志记录,您可能会得到一些输出。然后查看PDF规范,查看每个运算符的确切操作数,并相应地更新代码。

我没有运行代码,但前5个运算符可能不存在于页面内容中。另外,其中一些具有名称操作数,一些没有任何操作数(如EMC)。Tj运算符还有一个字符串操作数,而不是名称。

删除所有pop name方法,只保留日志记录,您可能会得到一些输出。然后查看PDF规范,查看每个运算符的确切操作数,并相应地更新代码。

这是关于
CFRelease(url)
。删除它就可以了


“(_桥T)op将操作数强制转换为目标类型T。如果T是可保留的对象指针类型,则op必须具有不可保留的指针类型。”

这是关于
CFRelease(url)
。删除它就可以了


“(_桥T)op将操作数强制转换为目标类型T。如果T是可保留的对象指针类型,则op必须具有不可保留的指针类型。”

我需要搜索以特定格式嵌入的字符串(例如,所有标题或粗体字符串)。为此,您建议采用哪种框架?我的箱子太贵了,我会