循环遍历描述按键后应在屏幕上执行的操作的实体

Looping through entities which describe what action should be taken on screen after keypresses

如果我没有很好地描述这个问题,请原谅我,我是使用 Swift 编写 MacOS 应用程序的新手。我知道我处理这件事的方法可能是错误的,我只需要有人告诉我正确的方法。

My main app screen

我有一个 Core Data 应用程序,它存储一个有序的实体列表,称为 Items。这些项目旨在描述 activity 中的单个步骤,该步骤描述屏幕上应该发生的事情。如果您知道 Mac 应用程序 QLab,每个项目就像 QLab 中的一个提示。

我创建了一个 Activity class,旨在通读每个项目以确定项目类型及其相关信息。一旦确定了 Item 类型,Activity class 需要呈现一个包含与该特定 Item 相关的信息的视图,然后等待直到用户按下向右箭头键,然后继续到下一个 Item核心数据存储在其中重复该过程,直到所有项目都被读取。每次在循环中读取一个新的 Item 时,屏幕上的信息应该在用户每次按下右箭头后发生变化。

问题是我不知道如何以编程方式来解决这个问题。我有将项目数组检索为 NSFetchRequest 的代码:

let moc = (NSApplication.shared.mainWindow?.contentViewController?.representedObject as! NSPersistentDocument).managedObjectContext!
    let fetchRequest : NSFetchRequest = Item.fetchRequest()
    do {
        let items = try moc.fetch(fetchRequest)
        print("Found " + String(items.count) + " items to use in the activity.")
        for item in items {
            print(item.itemType)
    // How do I pause this loop for a user keypress after using data from this Item to display?
        }
    } catch {
        print("Error retrieving Items")
    }

我可以使用 NSEvent.addLocalMonitorForEvents(matching: .keyDown) 检索按键事件,我还可以创建视图控制器以在第二个屏幕上显示信息。我只是不知道我应该如何创建 'main loop',可以这么说,以便显示信息然后应用程序等待,直到用户按下一个键继续...

如果需要更多信息,我可以分享我的项目代码,非常感谢任何能启发我的人...:)

您可以尝试使用 NSPageController。在您的 NSPageController 中,您添加一个 ContainerView,它将显示显示每个项目信息的 ViewControllers。每个 ViewController 都需要一个故事板标识符,例如ViewController项目 1.

您的 NSPageController class 必须符合 NSPageControllerDelegate 协议并包含要显示的 ViewController 数组。

override func viewDidLoad() {
    super.viewDidLoad()
    delegate = self
    arrangedObjects = ["ViewControllerItem1", "ViewControllerItem2", "...","ViewControllerItemN" ]
}

NSPageController 文档中关于 arrangedObjects 的注意事项:包含页面控制器视图中显示的对象的数组。

然后你实现 NSPageControllers viewControllerForIdentifier 到 return 你当前想要在 ContainerView 中显示的 ViewController。

func pageController(_ pageController: NSPageController, viewControllerForIdentifier identifier: String) -> NSViewController {

switch identifier {
    case "ViewControllerItem1":
        return mainStoryboard().instantiateController(withIdentifier:"ViewControllerItem1") as? ViewControllerItem1
    case "...":
    default:
    }
}

在您实现的按键按下事件的操作处理程序中。

self.navigateForward(sender) or self.navigateBack(sender)

我也实现了这个方法,但我不记得是否需要它。

func pageControllerDidEndLiveTransition(_ pageController: NSPageController) {
    self.completeTransition()
}