objective-c - 如何使用Mavericks API全屏显示您的应用

标签 objective-c macos cocoa

我目前正在OS X中开发应用程序,而只是试图将应用程序设置为全屏。我做了一些研究,发现我需要从放置在sharedApplication方法中的applicationDidFinishLaunching对象调用一个函数。

[[NSApplication sharedApplication] setPresentationOptions:NSApplicationPresentationFullScreen];


但是,在运行该应用程序时,我收到此消息记录。

setPresentationOptions called with NSApplicationPresentationFullScreen when there is no visible fullscreen window; this call will be ignored.


我找不到解决方案,有人可以解释我如何解决此问题吗?
这是我从消息中了解到的信息,如果我的窗口最初不是全屏的,则无法将我的应用设置为全屏,这对我来说没有意义,因为我需要有一个较小的窗口供我使用最大化。发生了什么?

更新1:
这是重新创建错误的视频链接。
Please do watch this其时长为4分钟。

最佳答案

好的,我希望这是一个有用的答案。

首先,我将讨论iOS和Mac之间的基本应用程序开发差异,并将继续介绍如何使用NSWindowController,然后尝试解释为什么您所做的操作会导致意外行为!

iOS和Mac之间的差异

笔尖

因此,在Mac开发中(我也来自iOS开发)有趣的是,AppKit中没有相同的函数调用UIApplicationMain;那是有一个功能NSApplicationMain;但是它们的签名是不同的。在iOS中,可以为应用程序指定UIApplication子类和UIApplicationDelegate类,但在Mac中,不能指定NSApplication子类和NSApplicationDelegate类。话虽如此,人们可能会混淆AppDelegate的工作方式或使用自定义NSApplication的方式。首先,在Info.plist中有一个键NSPrincipalClass,它告诉系统该应用程序使用哪个NSApplication子类。不幸的是,委托并不是那么简单。 Info.plist还有另一个键NSMainNibFile,它告诉系统最初使用的笔尖。它以应用程序的所有者的身份加载该笔尖,并自动添加一些默认连接:


应用程序代表:这是设置您的应用程序代表的位置。如果您发现该对象具有类AppDelegate(或PREFIXAppDelegate)。因此,这里笔尖将自动分配这些类之一,并将委托连接分配给文件所有者,从而在NSApplication上设置委托。
字体管理器:这将代表Mac上共享的NSFontManager。它为菜单项添加了一些连接,这些连接与选择字体的系统用户体验保持一致。
主菜单:这是您看到的顶部菜单。如果您想自定义此功能,可以在此笔尖中进行。


笔尖的论点

那么为什么要使用笔尖呢?就像我提到的那样,我个人来自iOS,个人也不总是喜欢笔尖。用代码来做所有事情,事情变得更加灵活。在Mac应用程序中,我觉得您在使用笔尖时不会失去灵活性。笔尖通常是创建mac应用程序的标准(据我所知)(标准通常是有原因的)。此外,创建Mac应用程序的一个相当关键的方面是设置NSMainNibFile键来加载笔尖!

以编程方式

如果现在您遵循的是“ ya ya,但仍然,笔尖,ew!”那么我会尝试在这里指导您。快速警告,自从我尝试以编程方式完成所有操作以来已有一段时间了,因此某些信息可能会歪斜!有了这个说,让我们深入研究吧!

我至少可以相信,您可以将NSPrincipalClass中的Info.plist键设置为自定义子类。然后在该子类中重写-init *以将NSApplication的委托设置为您的自定义委托类。在这里,您的代表将正常工作,并且您的应用程序应可按预期运行(因此不需要笔尖)。还要注意,您可以简单地将NSApplication子类化,或者将自身设置为它自己的委托(从设计POV来看,这有点奇怪),也可以不设置委托而仅重写某些方法(在某些情况下调用super)。除了代替一起使用委托,您还可以实例化一个通知侦听器对象,该对象仅侦听NSApplicationDidFinishLaunchingNotification之类的通知。

NSWindowController

窗口控制器本质上是窗口化应用程序的基类(请确保可以反驳,但这是一个很好的起点)。如您所知,您只是将NSWindowController子类化,然后为其分配一个实例并调用-showWindow:

笔尖

正如文档所述,您不需要与NSWindowController一起使用的笔尖,但是“窗口控制器和笔尖文件之间的关系很重要”(引自文档)。您只需创建一个以NSWindowController作为所有者的笔尖,然后添加一个窗口对象,然后将所有者的window属性分配为要说的窗口,就可以了(注意将窗口的委托设置为所有者)同样也是一个不错的主意-可能有必要!)!当然,如果在创建子类时选中“自动为我创建笔尖”复选框,则会为您创建该笔尖。

笔尖的论点

苹果的文档从本质上说“使用它,就像用电;您不必使用它,但使用起来非常不错”。

以编程方式

所以你想成为阿米什eh? (恶作剧,对不起)。任何人,要以编程方式创建其中一个,首先需要对其进行子类化,然后手动设置window属性(可能在-init中)或在调用函数/方法中进行设置。

为什么您的项目不起作用?

好吧,当您删除MainMenu.nib时,您将删除对委托的引用。因此,从未分配您的委托人,因此也永远不会为委托消息调用它。这就是为什么窗口从不显示-从不调用代码的原因。如果删除笔尖内的窗口对象,但保留其余的连接,则代码/应该/可以工作(我刚刚进行了测试,然后我对模板做了一些调整,因此我的测试可能不准确)。

如何全屏显示

创建window controller后,先调用-showWindow:,然后再调用[windowController.window toggleFullscreen:nil]。这应该使窗口进入全屏状态(再次测试并为我工作)。

创造艺术

因此,您的最后一个问题是关于重新创建该应用程序的信息。我个人并没有出色的教程来创建一个平面Mac应用程序,但是我学到了一些一般性的原则:


很多子类。与iOS相比,我注意到获得了更深层次的自定义,我需要对更多类进行子类化。例如,NSView本质上不具有backgroundColor属性,因此要添加此属性,您需要对其进行子类化,添加该属性,然后实施-drawRect:方法以填充该颜色(请注意,这不是/ only /,这将我们带到下一个要点)。
是否支持图层? Mac应用程序中的NSViews本质上在视图的背后并没有CALayer。为了添加图层,您需要在要放置图层的NSView上指定-setWantsLayer:YES。请注意,根据我的经验,仅从子类中的YES返回- (BOOL)wantsLayer是不够的,您实际上需要发送消息。如果您对带有图层的子类化NSView感兴趣,还可以检出- (BOOL)wantsUpdateLayer,它告诉系统在重绘视图时调用- (void)updateLayer而不是- (void)drawrect:(NSRect)r
忍耐。我注意到我可以很快创建一个外观相当不错的iOS应用。从经验来看,UIKit或其他形式的魔术是未知的。但是,在与AppKit一起创建Mac应用程序时,要花更长的时间才能创建外观和感觉很好的东西。我的信念是,由于您可以使用更多屏幕,可以使用更精确的控件,并且通常可以使用更大的环境,因此可以使用更多选项来探索创建应用程序。因此,该基础应用程序相当简单,因此可以根据自己的需求对其进行自定义!


编辑:添加了一些链接。通常,对于Mac开发,不要忘记阅读this

*我记得在10.7 / 8中以这种方式进行操作,但没有尝试在10.9中进行此操作

敬请注意:如果您在这篇文章中发现错误(由于时间过长,我假设我说了些愚蠢的话),请在下面认真地纠正我。我鼓励更正,但是我希望他们能受到尊重!

关于objective-c - 如何使用Mavericks API全屏显示您的应用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23533433/

相关文章:

ios - 解析 URL 字符串以获取键值的最佳方法?

python - 使用 Python 脚本输出发送电子邮件并使用 crontab 每周发送一次

cocoa - NSView 框架通过 -setFrame : following autoresizing 以外的方式设置

cocoa - 如何在 Cocoa 中单击按钮打开启动 NSWindow

objective-c - 在 cocoa 屏幕保护程序中禁用鼠标移动退出并构建 UI?

Objective-C 计算字符串值

iphone - 如何子类化 UITextField 并覆盖 drawPlaceholderInRect 以更改占位符颜色

objective-c - 模态视图 Controller 调用其他的 "viewDidLoad"

swift - 如何在 macOS 上使用 swift 在下载文件夹中创建目录?权限异常。

linux - 如何在 ansible 中根据操作系统类型运行 playbook 任务?