Backbone.js - 在哪里存储状态信息?
Posted
技术标签:
【中文标题】Backbone.js - 在哪里存储状态信息?【英文标题】:Backbone.js - where to store state information? 【发布时间】:2011-10-26 13:11:58 【问题描述】:我是Backbone.js 的新手,我正试图找出状态变量应该放在哪里。我的用例:
我有一个为一本书提供阅读界面的应用程序(我知道,经典示例,对吗?)。我的模型是Book
和Page
,每个模型都有集合类。应用程序的结构大致如下(原谅 ASCII visio):
+------------+
| Controller |
+------------+
| Views Models
| +--------------+ +----------------+
|-| IndexView |------| BookCollection |
| +--------------+ +----------------+
| |
| +--------------+ +----------------+
+-| BookView |------| Book |
+--------------+ +----------------+
| |
| +--------------+ |
|-| TitleView |-+ |
| +--------------+ | +----------------+
| +-| Page |
| +--------------+ | +----------------+
+-| PageView |-+
+--------------+
也就是说,Controller
实例化并协调两个视图,IndexView
和 BookView
,由模型支持。 BookView
实例化和协调一组子视图(实际上比这里显示的更多)。
状态信息包括:
当前图书(指针或 ID) 当前页面(指针或 ID) 其他 UI 状态变量,例如页面上的图像是否可见,其他小部件是否打开或关闭等。我的问题是,这个状态信息应该放在哪里?可能的选项包括:
模型,可以感知状态。这是有道理的,因为它们旨在存储数据,并且视图可以监听状态变化,但这似乎不符合预期的 Backbone.js 模式,并且并不总是有意义(例如,在PageView
应该适用于所有页面,而不仅仅是当前页面)
用于保存状态信息的特殊单例模型。同样,这很有意义,易于收听,所有视图都可以绑定到它 - 但同样,这似乎超出了标准 MVC。
视图,负责 UI 状态 - 但这需要视图相互了解才能获取状态信息,这似乎不正确
控制器,应该在状态之间路由应用程序 - 这是有道理的,但它意味着有点奇怪的往返,例如User selects "Show Images" --> View event listener is called --> View informs Controller --> Controller updates state --> Controller updates View
(而不是更简单的User selects "Show Images" --> View event listener is called --> View updates
)
我想在某些方面这是一个通用的 MVC 问题,但我很难理解它。 应用程序的哪个部分应该负责保存当前状态?
更新:为了将来参考,我使用了一个全局单例状态模型来解决这个问题。 UI 流程是这样的:
-
视图 UI 处理程序除了更新
app.State
什么都不做
我的路由器除了更新 app.State
之外什么也不做 - 它们本质上是专门的视图,用于显示和响应 URL 更改
视图监听 app.State
上的更改并相应更新
我的应用是开源的 - 你可以看到code on Github。这里的相关部分是State model,我已经对其进行了扩展以处理 URL 的(反)序列化状态。
【问题讨论】:
主干0.5中没有Controller
嗯,是的,我有一个路由器类,我正在调用Controller
。它仍然基本上是为了执行控制器的功能,对吧?
并非如此。就经典 MVC 而言,您应该将 View
视为经典的 Controller
。做主干的时候最好不要去想经典的MVC。就您的问题而言,当前书籍进入AppView
,当前页面进入Book
,其余进入AppView
。 AppView
是一个特殊的单例视图,如果你愿意的话
按照这个逻辑,当前页面不会进入BookView
,而不是Book
吗?
【参考方案1】:
Don't limit your Backbone apps to Backbone constructs。如果您发现您的应用需要某些功能,但不能很好地融入其中一种 Backbone 结构,请不要为了将所有内容都保留在 Backbone 中而将其硬塞进一个结构中。
我发现backbone boilerplate 在这方面很有帮助。它为您设置模块并为您提供扩展 Backbone.Events 的应用程序对象(如之前链接的文章中所示)。此应用程序对象可用于存储实例化模型、视图和控制器/路由器,您应该随意将自己的非主干模块添加到应用程序对象,以处理不完全适合其中之一的职责骨干结构。
【讨论】:
感谢您的链接。这实际上与我所做的并不太远 - 例如请参阅my app initialization,这与链接的内容非常相似。但就事件和侦听器而言,Backbone确实有助于状态模型。你可以看到my implementation here。【参考方案2】:为什么不创建一个状态模型来存储和描述当前状态呢?我不认为这是错误的。由于当前状态涉及多个模型,我认为创建一个状态模型来存储和接收当前状态是合理的。
然后控制器可以与状态模型通信以获取当前状态。 UI 状态应该存储在相应的模型中。状态模型知道哪本书和哪一页,然后书籍和页面模型会跟踪它们当前的 UI 状态。
【讨论】:
这或多或少是我决定采用的方式,但我完全放弃了控制器 - 视图更新 UI 事件的状态模型,然后侦听状态更新以更新 UI,并且路由器对 URL 执行相同的操作。 酷。我在 Rails 应用程序中遇到了类似的问题。不真正适合任何现有模型或控制器的功能已通过新模型解决,这也有助于应用保持“RESTful”。以上是关于Backbone.js - 在哪里存储状态信息?的主要内容,如果未能解决你的问题,请参考以下文章
Backbone.js - 在视图处于活动状态时添加 keydown 事件?