4

作为实验的一部分,我需要创建一个 iOS 应用程序,它可以截取其他应用程序、视频等的屏幕截图。我愿意使用私有 API,因为我不会将应用程序发布到应用程序商店。我可以成功地使用 GetUIScreenImage() 方法拍摄当前屏幕(应用程序屏幕)的快照。

但是,由于沙盒限制,我无法在后台截取屏幕截图。我收到错误消息 - “应用程序处于后台时无法调用 CreateUIScreenImage()”。

我参考了这篇文章——iOS 应用 Display Recorder 如何在不使用私有 API 的情况下录制屏幕?建议使用 IOMobileFramebuffer 和 IOSurface 绕过沙箱限制,还有这个链接 - http://www.iphonesheep.com/2009/11/25/iphone%E2%80%99s-framebuffer-secrets-revealed/。但我无法获得创建和转移表面的流程。非常感谢有关此主题的任何帮助。

另外,有没有办法在越狱设备的后台调用 UIGetScreenImage() ?

更新:
我能够掌握主屏幕表面并将其放在应用程序层上,但我的用例是能够打开其他应用程序并能够通过我创建的应用程序记录它们。然而,我粘贴在我的应用层上的表面是静态的。

编辑
这里是我的理解- 附加到主显示层的主屏幕表面需要放在当前层上。这样做之后,我应该能够浏览其他应用程序,从刚刚粘贴的表面打开它们。

这是代码(它将主屏幕表面放在应用程序层的顶部,但我无法使用该表面,即打开应用程序等):

IOMobileFramebufferConnection connect;
kern_return_t result;
CoreSurfacebufferRef screenSurface = NULL;
io_service_t framebufferService = IOServiceGetMatchingService (kIOMasterPortDefault, IOServiceMatching ("AppleH1CLCD"));
if(!framebufferService)
        io_service_t framebufferService = IOServiceGetMatchingService (kIOMasterPortDefault, IOServiceMatching ("AppleM2CLCD"));
if(!framebufferService)
        io_service_t framebufferService = IOServiceGetMatchingService (kIOMasterPortDefault, IOServiceMatching ("AppleCLCD"));
result = IOMobileFramebufferOpen( framebufferService, mach_task_self(), 0 , &connect);
result = IOMobileFramebufferGetLayerDefaultSurface(connect, 0, &screenSurface);

CALayer *Layer;
Layer = [CALayer layer];
[Layer setFrame: CGRectMake(0, 0, 768, 1024)];
[Layer setOpaque:YES];
IOSurfaceLock(screenSurface, 0, NULL);
[Layer setContents: (_bridge id)(screenSurface)];
IOSurfaceUnlock(screenSurface, 0, NULL);
[self.view.layer addSublayer:Layer];

我知道我错过了一些东西并且做错了什么。如果您能指出这一点,那将是很大的帮助。

更新
我认为我的基本假设可能是错误的。
1. 我的假设 -> 应用程序交换表面(或层),以便用户现在可以在主屏幕上浏览。该应用程序永远不会移动到后台。
2. 什么听起来更正确 -> 应用程序移至后台。获取屏幕上最顶部的表面,从中创建图像并保存。请说清楚。

4

1 回答 1

3

“获得创建和转移表面的流程”究竟是什么问题?您能否发布正在使用的代码并指出哪一行不起作用。

对于越狱设备:

转到 /Application/XCode/Content/Developer/Platforms 并将它的 grep 用于句子“Cannot call CreateUIScreenImage() while the app is in background”。你会在一些框架中找到它(我假设是 UIKit)。接下来,您可以对其进行反汇编,您会发现一些在后台进行屏幕截图所需的权利。

您可以在这里查看如何将权利与 ldid 一起用于越狱设备: iOS 如何使用 Entitlement.plist 指定我的应用程序的属性

于 2012-12-12T19:12:26.650 回答