- 浏览: 12491 次
- 性别:
- 来自: 大连
-
最新评论
从上周正式开始学习Extjs。刚开始看老大推荐的Extjs in action英文版,边看边敲代码,虽然都是一些简单小程序,但是看着它跑起来还是很欢脱。但是,第一次通过英文书学技术的我感到非常痛恨英语,别扭的逻辑经常把自己搞糊涂。由于书是extjs3.x的,大神建议“直截了当”,从sencha上直接学习最新技术。sencha官网的extjs4.2.1docs真的是非常优秀的教材。(好吧,我也不知道前面这一大段废话有什么用途,很少写日志,但是,作为一名程序员,和一名正在奔向一名优秀而出色的程序员的程序员,写博客是必须要有的好习惯,于是,啰里八嗦的开启这篇里程碑日记)
sencha-concept:MVC Architecture
这篇今天看了一天,到最后向server传输json数据失败了,于是来整理一下这篇文章学到的技术:
大型的客户端应用一直很难开发,组织和维护。当你增添更多的功能和开发者到这个项目上时,它就可能会失控。Ext JS4 带来了一个新的应用架构,不仅可以组织代码还可以减少你的代码书写量。
我们的应用架构第一次引入Models,Controller类似一种MVC的模式。计算机世界里有很多MVC架构,大多数之间都有细微的不同。以下是我们的定义:
◆Model:是一个域和它的数据的集合(例如:一个user model有用户名和密码域)。Models知道如何在数据包之间存储,并且能够通过关系被链接到其他model中。Model的工作方式与Ext JS 3 Record class非常相似, 并且通常和Stores一起使用来将数据呈现到grids和其他组件类(componets class)中。
◆View:是任何形式的组件(component)-grids,trees panels都是views.
◆Controllers:是用来放置所有app work的代码的特殊地方-无论是渲染视图,实例模型或是任何其他app逻辑。 =>就是有许多控制view行为的方法。
/*还是中国字儿好,中文才是最美丽的语言 哼~*/
在这篇指南中我们将会创建一个非常简单的应用来管理用户数据。到结束的时候你会知道怎么用Ext JS 4应用框架将简单的应用整合在一起。
应用架构和实际类与框架代码一样多为供给结构和连贯性。下面的协议包括很多重要的好处:
每一个应用都以同样的方式工作,所以你只需要学习一次。
在app之间很容易分享代码因为他们都以同样的原理工作。
你可以用我们的编译工具来创建供你的产品使用的最优化的(optimized)应用版本。
File Structure
Ext JS 4应用有一个统一的(unified)目录结构,即每一个app目录都是一样的。请检查一下开始手册中对一个应用的基本文件结构的详细解释。在MVClayout中,所有的类都放在app/文件夹下,该文件夹相应的(in turn)也包括从子文件夹到你的models,views,controllers和stores的命名空间。以下是这个简单的小例子的文件夹结构:
在这个例子中,我们在一个名为'account_manager'的文件夹中囊括了整个应用。Ext JS 4 SDK中的重要文件都被放在ext-4/文件中。因此 index.html中的内容看上去像这样:
Creating the application in app.js
每一个 Ext JS 4 应用都从一个应用类实例开始。这个Application包括你的应用中所有的设置(如:app的名字),同时维护着所有应用于app上的models,views和controllers的参考(references)。一个Application同样包括一个启动方法(launch function),它可以当一切被加载完成时自动的跑起来。
让我们一起来创建一个简单的账户管理app,它会帮助我们管理用户账户。首先我们需要为应用选一个全局命名空间。所有的Ext JS 4 应用都应该之用一个单独的全局变量,带着全部应用的类嵌套(nested inside it)在他其中。通常我们想要一个简短的全局变量,所以我们将使用"AM"。
有几件事情要在这里说一下。首先我们借助(invoked)Ext.application来为给予名字为'AM'的命名空间(?)创建一个新的Application class实例,这个自动为我们建立一个全局AM变量,并且将命名空间注册到 Ext.Loader上同时通过 appFolder 配置选项(config option)完成'app'路径绑定设置。我们同样提供一个简单的启动方法仅仅创建了将会充满全屏的一个包括单独Panel的Viewport。
Defining a Controller
Controllers是将application连接到一起的粘合剂。他们所有要做的就是监听所有事件(通常来自views)和采取一些行动。接着我们的账户管理应用,让我们来建立一个controller。创建一个叫做app/controller/Users.js的文件,写入以下代码:
现在让我们将新创建的Users controller添加的应用配置文件app.js中:
当我们通过访问index.html加载我们的应用到浏览器,Users controller是被自动加载的(应为我们在上面的Application定义中指定出来了),并且它的init方法正是在Application的启动方法之前被调用l
init方法是一个很棒的地方来定义你的controller和view如何交互,同时常常被用来连接(conjunction)另一个Controller方法-control. control方法使监听到你的view类上的事件变得容易,并且用一个handler方法采取一些措施。让我们更新一下我们的Users controller来告诉我们panel何时被渲染:
我们已经更新了init方法来使用this.control来家里我们application上的views的监听器。control方法用到了组件查询机制(ComponentQuery engine)来方便快捷的得到页面上的组件的引用。如果你对组件查询还不太熟悉,确保查看一下组件查询文件得到完整解释。简而言之,他允许我们通过类似css选择器的方式找到每一个匹配的组件并传到页面上。
在我们上面的init方法我们提供了'viewport > panel',翻译过来就是“给我找到每一个是一个Viewport直接子类的Panel”。我们然后提供了一个对象映射(maps)事件名称(就是这里的render)到handler方法。整体的效果是,无论什么时候任何组件和我们的选择器匹配时都会开启一个render事件,我们的onPanelRendered方法被调用。
当我们跑一下这个应用时我看到如下效果:
虽然这不是最令人兴奋的应用,但是它展示了从管理代码开始是多么容易。让我们来通过加一个网格(grid)使app更饱满。
Defining a View
直到现在我们的应用才之后几行并且仅包含在两个文件中-app.js和app/controller/Users.js。既然我们想要添加一个网格来展示系统中所有用户,就是时候更好的管理我们的逻辑,开始使用views。
一个View只不过是一个组件,通常被定义成一个Ext JS组件的子类。我们现在要通过新建一个叫做app/view/user/List.js 文件建立我们的Users grid,并且写入以下内容:
我们的View class不过是一个普通类。这里我们正好继承了Grid Component并且建立了一个别名,因此我们可以把它用作一个xtype(更多的时候)。我们也传入了store配置和网格应该渲染的列。
下一步我们需要把这个view加入到我们的Users controller。因为我们用特殊的'widget'格式设置一个换名,我们现在可以用'userlist'作为一个xtype,就好像我们之前用过的'panel'。
然后通过修改app.js中的启动方法将它渲染到主viewport中:
唯一的另一件事要强调的是我们在views array中指定的'user.List'。这告诉应用自动去加载那个文件因此当我们启动时可以用它。这个应用使用Ext JS 4的新动态加载系统,自动的从服务器获取文件(pull this file from the server)。以下是我们现在刷新网页会看到的效果:
Controlling the grid
注意我们的onPanelRendered方法是一直被调用的。这个是因为我们的网格类一直和'view > panel'选择器匹配。其中的原因是我们的类继承自Grid,其也继承自Panel。
这是,我们为这个选择器添加的监听器实际上将会为每一个是viewport的直接子类的Panel或Panel的子类所调用,所以让我们稍微收紧使用我们新的xtype。让我们以在网格的行上双击代替,这样我们可以之后编辑那个User:
注意我们改变了 ComponentQuery选择器(简称为'userlist'),事件的名字(to 'itemdblclick'),handler方法名字(to 'editUser')。现在我们登出我们刚刚双击的User名:
登入控制台非常顺利但是我们很想要编辑我们的Users。让我们现在就做,从一个 app/view/user/Edit.js中新的view开始:
再一次我们定义一个已经存在的component的子类-这次是Ext.window.Window.再一次我们使用initComponent来指定复杂对象items 和 buttons。我们用一个'fit'layout和一个表格作为单独的item,他们包括可编辑姓名和邮箱地址的域。最终我们创建了两个按钮,一个用于关闭窗口,另一个用于保存我们的改变。
所有我们要做的是将view加入的controller中,渲染它并且在其中加载User:
首先我们用方便的 Ext.widget方法创建view,它等同于Ext.create('widget.useredit').。然后我们再一次促使ComponentQuery改变(leveraged)来快速得到一个引用来编辑窗口的表格。每一个在Ext JS 4中的组件都有一个down方法,用来接受一个ComponentQuery选择器来快速找到任何一个子组件(component)。
现在在我们的网格中双击一行会产生如下效果:
Creating a Model and a Store
既然我们已经有了编辑表格,是时候开始编辑我们的users和保存那些改变了。在我们这么做之前,我们应该对我们的代码稍作重构(refactor)。
此刻AM.view.user.List组件创建一个内联Store。这个工作的很好但是我们想要能够引用在应用中其他地方的Store因而可以更新那里的数据。我们将通过把Store放入他自己的文件- app/store/Users.js开始:
现在我们将要做两个小的改变-首先我们要让我们的Users controller加载时包括这个Store:
然后我们将用id更新app/view/user/List.js来简单的引用Store:
通过包括stores我们的Users controller关心它的定义,他们是自动加载到页面上并且被给予一个存储id,这使他们在我们的views引用变得真的很容易。(通过简单的配置store:在这个例子里是'Users')。
此时我们已经定义了我们的域('name'和'fields')内联在store中。这个运行的足够好但是在Ext JS 4中我们有一个强大的Ext.data.Model类,我们喜欢当它编辑我们的Users是利用它。我们将完成这部分通过重构我们的Store来使用一个Model,我们将向app/model/User.js写入:
这些就是我们需要做的来定义我们的Model.现在我们将要更新我们的Store来引用Model名字而不是提供内联域:
我们将要询问Users controller来返回一个引用到User model上:
我们的重构将要使下一个奔赴更容易但是不应该影响当前应用的行为。如果我们现在重新加载页面,在行上双击我们看到编辑用户窗口仍然如期待一样的显示。现在是时候完成编辑方法了:
Saving data with the Model
既然我们让我们的用户网格加载数据并打开一个编辑窗口,当我们双击每一行,我们想要保存用户做的修改。在上面定义的Edit User窗口,包括一个表格(有带有名字和邮箱的域),和一个保存按钮。首先让我们更新我们的controller的init方法来监听保存按钮的单击动作。
我们第二次将ComponentQuery选择器加入我们的this.control调用-这一次是 'useredit button[action=save]'。它和第一个选择器以同样的原理工作-它使用'useredit' xtype ,我们在之前定义过的来聚焦到我们的编辑用户窗口,并且然后寻找任何带有'save'行为的按钮,这使得给我们提供了一个锁定按钮的简单的途径。
我们能够满足我们自己,当我们点击保存按钮updateUser方法被调用。:
既然我们已经看到我们的handler被正确的绑定到保存按钮的点击时间,那么让我们为updateUser方法添加真正的逻辑。在这个方法中我们需要从表格中获取数据,用它更新我们的User,然后将它保存回上面建好的Users store中。让我们看一下我们应该怎样做:
让我们分解一下现在发生的事情。我们的点击事件通过用户点击给我们了一个对按钮的引用,但是我们真正想要从表格中获得的是包括数据和窗口本身。为了让事情快速起效,我们将仅再次使用ComponentQuery,首先使用button.up('window')来得到一个参考用户编辑窗口,然后使用win.down('form')来的到一个表格。
在这之后,我们简单的取回记录,这记录是目前载入表格中的并且将用户输入的任何内容更新到表格中。最后,我们关闭窗口来将关注点回到网格。这就是我们将要看到的我们的app再次跑起来的效果,将名字域改成'Ed Spencer'并保存。
Saving to the server
非常方便。让我们现在通过让它和我们的服务器端交互来把它完成。现在我们正在努力将两个User记录编写到Users Store中,是哦一让我们开始阅读那些ajax:
这里我们去掉了'data'属性并把它替换为一个Proxy。Proxies在Ext JS 4 中是从一个Store或一个Model加载和保存数据的一种方法。有proxies for AJAX, JSON-P and HTML5 localStorage among others. 这里我们已经使用了一个简单的AJAX proxy,我们已经告知它从'data/users.json'地址载入数据。
我们也将一个 Reader和 Proxy关联了起来。reader主要负责将服务器端响应解码到一种Store可以理解的格式。这是我们使用一个 JSON Reader和指定一个根目录和 successProperty配置参数。最后我们将创建我们的 data/users.json文件,并且将之前的数据粘进去:
唯一的一个我们对Store进行的其他的改变是将autoLoad设置为true,这意味着Store将询问它的Proxy来立即加载数据。如果我们现在刷新页面,我们将会看到和之前同样的结果,除了现在我们不再硬编码到我们的应用中。
最后,我们想要做的是将我们的改变传回服务器。举个例子,我们正在在服务器端使用一个静态JSON文件,所以我们不会看到任何数据库的改变但是我们至少能够核实每一件事都被正确的连接在一起。第一我们将对我们的新proxy做一点小改变来告诉它将更新内容发送到一个不同的url:
我们仍然从users.json中读取数据,但是任何一次更新将会被发送到updateUsers.json。这正如我们知道的事情正在以不重写测试数据方式工作。之后更新一个记录, updateUsers.json文件刚好包括{"success": true}。由于它通过一个http端口指令更新,你可能不得不闯进一个空文件来避免接收一个404错误。
另一个我们需要做的改变是告诉我们的Store在编辑之后经自己同步,这个通过我们在 updateUser方法中额外增加一行,它现在看上去是这样:
现在我们能够跑完我们的完整示例,并确保一切都在工作。我们将编辑一行,点击保存按钮,会看到请就被正确的发送到了 updateUser.json中。
sencha-concept:MVC Architecture
这篇今天看了一天,到最后向server传输json数据失败了,于是来整理一下这篇文章学到的技术:
大型的客户端应用一直很难开发,组织和维护。当你增添更多的功能和开发者到这个项目上时,它就可能会失控。Ext JS4 带来了一个新的应用架构,不仅可以组织代码还可以减少你的代码书写量。
我们的应用架构第一次引入Models,Controller类似一种MVC的模式。计算机世界里有很多MVC架构,大多数之间都有细微的不同。以下是我们的定义:
◆Model:是一个域和它的数据的集合(例如:一个user model有用户名和密码域)。Models知道如何在数据包之间存储,并且能够通过关系被链接到其他model中。Model的工作方式与Ext JS 3 Record class非常相似, 并且通常和Stores一起使用来将数据呈现到grids和其他组件类(componets class)中。
◆View:是任何形式的组件(component)-grids,trees panels都是views.
◆Controllers:是用来放置所有app work的代码的特殊地方-无论是渲染视图,实例模型或是任何其他app逻辑。 =>就是有许多控制view行为的方法。
/*还是中国字儿好,中文才是最美丽的语言 哼~*/
在这篇指南中我们将会创建一个非常简单的应用来管理用户数据。到结束的时候你会知道怎么用Ext JS 4应用框架将简单的应用整合在一起。
应用架构和实际类与框架代码一样多为供给结构和连贯性。下面的协议包括很多重要的好处:
每一个应用都以同样的方式工作,所以你只需要学习一次。
在app之间很容易分享代码因为他们都以同样的原理工作。
你可以用我们的编译工具来创建供你的产品使用的最优化的(optimized)应用版本。
File Structure
Ext JS 4应用有一个统一的(unified)目录结构,即每一个app目录都是一样的。请检查一下开始手册中对一个应用的基本文件结构的详细解释。在MVClayout中,所有的类都放在app/文件夹下,该文件夹相应的(in turn)也包括从子文件夹到你的models,views,controllers和stores的命名空间。以下是这个简单的小例子的文件夹结构:

在这个例子中,我们在一个名为'account_manager'的文件夹中囊括了整个应用。Ext JS 4 SDK中的重要文件都被放在ext-4/文件中。因此 index.html中的内容看上去像这样:
<html> <head> <title>Account Manager</title> <link rel="stylesheet" type="text/css" href="ext-4/resources/css/ext-all.css"> <script type="text/javascript" src="ext-4/ext-debug.js"></script> <script type="text/javascript" src="app.js"></script> </head> <body></body> </html>
Creating the application in app.js
每一个 Ext JS 4 应用都从一个应用类实例开始。这个Application包括你的应用中所有的设置(如:app的名字),同时维护着所有应用于app上的models,views和controllers的参考(references)。一个Application同样包括一个启动方法(launch function),它可以当一切被加载完成时自动的跑起来。
让我们一起来创建一个简单的账户管理app,它会帮助我们管理用户账户。首先我们需要为应用选一个全局命名空间。所有的Ext JS 4 应用都应该之用一个单独的全局变量,带着全部应用的类嵌套(nested inside it)在他其中。通常我们想要一个简短的全局变量,所以我们将使用"AM"。
Ext.application({ requires: ['Ext.container.Viewport'], name: 'AM', appFolder: 'app', launch: function() { Ext.create('Ext.container.Viewport', { layout: 'fit', items: [ { xtype: 'panel', title: 'Users', html : 'List of users will go here' } ] }); } });
有几件事情要在这里说一下。首先我们借助(invoked)Ext.application来为给予名字为'AM'的命名空间(?)创建一个新的Application class实例,这个自动为我们建立一个全局AM变量,并且将命名空间注册到 Ext.Loader上同时通过 appFolder 配置选项(config option)完成'app'路径绑定设置。我们同样提供一个简单的启动方法仅仅创建了将会充满全屏的一个包括单独Panel的Viewport。

Defining a Controller
Controllers是将application连接到一起的粘合剂。他们所有要做的就是监听所有事件(通常来自views)和采取一些行动。接着我们的账户管理应用,让我们来建立一个controller。创建一个叫做app/controller/Users.js的文件,写入以下代码:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', init: function() { console.log('Initialized Users! This happens before the Application launch function is called'); } });
现在让我们将新创建的Users controller添加的应用配置文件app.js中:
Ext.application({ ... controllers: [ 'Users' ], ... });
当我们通过访问index.html加载我们的应用到浏览器,Users controller是被自动加载的(应为我们在上面的Application定义中指定出来了),并且它的init方法正是在Application的启动方法之前被调用l
init方法是一个很棒的地方来定义你的controller和view如何交互,同时常常被用来连接(conjunction)另一个Controller方法-control. control方法使监听到你的view类上的事件变得容易,并且用一个handler方法采取一些措施。让我们更新一下我们的Users controller来告诉我们panel何时被渲染:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', init: function() { this.control({ 'viewport > panel': { render: this.onPanelRendered } }); }, onPanelRendered: function() { console.log('The panel was rendered'); } });
我们已经更新了init方法来使用this.control来家里我们application上的views的监听器。control方法用到了组件查询机制(ComponentQuery engine)来方便快捷的得到页面上的组件的引用。如果你对组件查询还不太熟悉,确保查看一下组件查询文件得到完整解释。简而言之,他允许我们通过类似css选择器的方式找到每一个匹配的组件并传到页面上。
在我们上面的init方法我们提供了'viewport > panel',翻译过来就是“给我找到每一个是一个Viewport直接子类的Panel”。我们然后提供了一个对象映射(maps)事件名称(就是这里的render)到handler方法。整体的效果是,无论什么时候任何组件和我们的选择器匹配时都会开启一个render事件,我们的onPanelRendered方法被调用。
当我们跑一下这个应用时我看到如下效果:

虽然这不是最令人兴奋的应用,但是它展示了从管理代码开始是多么容易。让我们来通过加一个网格(grid)使app更饱满。
Defining a View
直到现在我们的应用才之后几行并且仅包含在两个文件中-app.js和app/controller/Users.js。既然我们想要添加一个网格来展示系统中所有用户,就是时候更好的管理我们的逻辑,开始使用views。
一个View只不过是一个组件,通常被定义成一个Ext JS组件的子类。我们现在要通过新建一个叫做app/view/user/List.js 文件建立我们的Users grid,并且写入以下内容:
Ext.define('AM.view.user.List' ,{ extend: 'Ext.grid.Panel', alias: 'widget.userlist', title: 'All Users', initComponent: function() { this.store = { fields: ['name', 'email'], data : [ {name: 'Ed', email: 'ed@sencha.com'}, {name: 'Tommy', email: 'tommy@sencha.com'} ] }; this.columns = [ {header: 'Name', dataIndex: 'name', flex: 1}, {header: 'Email', dataIndex: 'email', flex: 1} ]; this.callParent(arguments); } });
我们的View class不过是一个普通类。这里我们正好继承了Grid Component并且建立了一个别名,因此我们可以把它用作一个xtype(更多的时候)。我们也传入了store配置和网格应该渲染的列。
下一步我们需要把这个view加入到我们的Users controller。因为我们用特殊的'widget'格式设置一个换名,我们现在可以用'userlist'作为一个xtype,就好像我们之前用过的'panel'。
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', views: [ 'user.List' ], init: ... onPanelRendered: ... });
然后通过修改app.js中的启动方法将它渲染到主viewport中:
Ext.application({ ... launch: function() { Ext.create('Ext.container.Viewport', { layout: 'fit', items: { xtype: 'userlist' } }); } });
唯一的另一件事要强调的是我们在views array中指定的'user.List'。这告诉应用自动去加载那个文件因此当我们启动时可以用它。这个应用使用Ext JS 4的新动态加载系统,自动的从服务器获取文件(pull this file from the server)。以下是我们现在刷新网页会看到的效果:

Controlling the grid
注意我们的onPanelRendered方法是一直被调用的。这个是因为我们的网格类一直和'view > panel'选择器匹配。其中的原因是我们的类继承自Grid,其也继承自Panel。
这是,我们为这个选择器添加的监听器实际上将会为每一个是viewport的直接子类的Panel或Panel的子类所调用,所以让我们稍微收紧使用我们新的xtype。让我们以在网格的行上双击代替,这样我们可以之后编辑那个User:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', views: [ 'user.List' ], init: function() { this.control({ 'userlist': { itemdblclick: this.editUser } }); }, editUser: function(grid, record) { console.log('Double clicked on ' + record.get('name')); } });
注意我们改变了 ComponentQuery选择器(简称为'userlist'),事件的名字(to 'itemdblclick'),handler方法名字(to 'editUser')。现在我们登出我们刚刚双击的User名:

登入控制台非常顺利但是我们很想要编辑我们的Users。让我们现在就做,从一个 app/view/user/Edit.js中新的view开始:
Ext.define('AM.view.user.Edit', { extend: 'Ext.window.Window', alias: 'widget.useredit', title: 'Edit User', layout: 'fit', autoShow: true, initComponent: function() { this.items = [ { xtype: 'form', items: [ { xtype: 'textfield', name : 'name', fieldLabel: 'Name' }, { xtype: 'textfield', name : 'email', fieldLabel: 'Email' } ] } ]; this.buttons = [ { text: 'Save', action: 'save' }, { text: 'Cancel', scope: this, handler: this.close } ]; this.callParent(arguments); } });
再一次我们定义一个已经存在的component的子类-这次是Ext.window.Window.再一次我们使用initComponent来指定复杂对象items 和 buttons。我们用一个'fit'layout和一个表格作为单独的item,他们包括可编辑姓名和邮箱地址的域。最终我们创建了两个按钮,一个用于关闭窗口,另一个用于保存我们的改变。
所有我们要做的是将view加入的controller中,渲染它并且在其中加载User:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', views: [ 'user.List', 'user.Edit' ], init: ... editUser: function(grid, record) { var view = Ext.widget('useredit'); view.down('form').loadRecord(record); } });
首先我们用方便的 Ext.widget方法创建view,它等同于Ext.create('widget.useredit').。然后我们再一次促使ComponentQuery改变(leveraged)来快速得到一个引用来编辑窗口的表格。每一个在Ext JS 4中的组件都有一个down方法,用来接受一个ComponentQuery选择器来快速找到任何一个子组件(component)。
现在在我们的网格中双击一行会产生如下效果:

Creating a Model and a Store
既然我们已经有了编辑表格,是时候开始编辑我们的users和保存那些改变了。在我们这么做之前,我们应该对我们的代码稍作重构(refactor)。
此刻AM.view.user.List组件创建一个内联Store。这个工作的很好但是我们想要能够引用在应用中其他地方的Store因而可以更新那里的数据。我们将通过把Store放入他自己的文件- app/store/Users.js开始:
Ext.define('AM.store.Users', { extend: 'Ext.data.Store', fields: ['name', 'email'], data: [ {name: 'Ed', email: 'ed@sencha.com'}, {name: 'Tommy', email: 'tommy@sencha.com'} ] });
现在我们将要做两个小的改变-首先我们要让我们的Users controller加载时包括这个Store:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', stores: [ 'Users' ], ... });
然后我们将用id更新app/view/user/List.js来简单的引用Store:
Ext.define('AM.view.user.List' ,{ extend: 'Ext.grid.Panel', alias: 'widget.userlist', title: 'All Users', // we no longer define the Users store in the `initComponent` method store: 'Users', initComponent: function() { this.columns = [ ... });
通过包括stores我们的Users controller关心它的定义,他们是自动加载到页面上并且被给予一个存储id,这使他们在我们的views引用变得真的很容易。(通过简单的配置store:在这个例子里是'Users')。
此时我们已经定义了我们的域('name'和'fields')内联在store中。这个运行的足够好但是在Ext JS 4中我们有一个强大的Ext.data.Model类,我们喜欢当它编辑我们的Users是利用它。我们将完成这部分通过重构我们的Store来使用一个Model,我们将向app/model/User.js写入:
Ext.define('AM.model.User', { extend: 'Ext.data.Model', fields: ['name', 'email'] });
这些就是我们需要做的来定义我们的Model.现在我们将要更新我们的Store来引用Model名字而不是提供内联域:
Ext.define('AM.store.Users', { extend: 'Ext.data.Store', model: 'AM.model.User', data: [ {name: 'Ed', email: 'ed@sencha.com'}, {name: 'Tommy', email: 'tommy@sencha.com'} ] });
我们将要询问Users controller来返回一个引用到User model上:
Ext.define('AM.controller.Users', { extend: 'Ext.app.Controller', stores: ['Users'], models: ['User'], ... });
我们的重构将要使下一个奔赴更容易但是不应该影响当前应用的行为。如果我们现在重新加载页面,在行上双击我们看到编辑用户窗口仍然如期待一样的显示。现在是时候完成编辑方法了:

Saving data with the Model
既然我们让我们的用户网格加载数据并打开一个编辑窗口,当我们双击每一行,我们想要保存用户做的修改。在上面定义的Edit User窗口,包括一个表格(有带有名字和邮箱的域),和一个保存按钮。首先让我们更新我们的controller的init方法来监听保存按钮的单击动作。
Ext.define('AM.controller.Users', { ... init: function() { this.control({ 'viewport > userlist': { itemdblclick: this.editUser }, 'useredit button[action=save]': { click: this.updateUser } }); }, ... updateUser: function(button) { console.log('clicked the Save button'); } ... });
我们第二次将ComponentQuery选择器加入我们的this.control调用-这一次是 'useredit button[action=save]'。它和第一个选择器以同样的原理工作-它使用'useredit' xtype ,我们在之前定义过的来聚焦到我们的编辑用户窗口,并且然后寻找任何带有'save'行为的按钮,这使得给我们提供了一个锁定按钮的简单的途径。
我们能够满足我们自己,当我们点击保存按钮updateUser方法被调用。:

既然我们已经看到我们的handler被正确的绑定到保存按钮的点击时间,那么让我们为updateUser方法添加真正的逻辑。在这个方法中我们需要从表格中获取数据,用它更新我们的User,然后将它保存回上面建好的Users store中。让我们看一下我们应该怎样做:
updateUser: function(button) { var win = button.up('window'), form = win.down('form'), record = form.getRecord(), values = form.getValues(); record.set(values); win.close(); }
让我们分解一下现在发生的事情。我们的点击事件通过用户点击给我们了一个对按钮的引用,但是我们真正想要从表格中获得的是包括数据和窗口本身。为了让事情快速起效,我们将仅再次使用ComponentQuery,首先使用button.up('window')来得到一个参考用户编辑窗口,然后使用win.down('form')来的到一个表格。
在这之后,我们简单的取回记录,这记录是目前载入表格中的并且将用户输入的任何内容更新到表格中。最后,我们关闭窗口来将关注点回到网格。这就是我们将要看到的我们的app再次跑起来的效果,将名字域改成'Ed Spencer'并保存。

Saving to the server
非常方便。让我们现在通过让它和我们的服务器端交互来把它完成。现在我们正在努力将两个User记录编写到Users Store中,是哦一让我们开始阅读那些ajax:
Ext.define('AM.store.Users', { extend: 'Ext.data.Store', model: 'AM.model.User', autoLoad: true, proxy: { type: 'ajax', url: 'data/users.json', reader: { type: 'json', root: 'users', successProperty: 'success' } } });
这里我们去掉了'data'属性并把它替换为一个Proxy。Proxies在Ext JS 4 中是从一个Store或一个Model加载和保存数据的一种方法。有proxies for AJAX, JSON-P and HTML5 localStorage among others. 这里我们已经使用了一个简单的AJAX proxy,我们已经告知它从'data/users.json'地址载入数据。
我们也将一个 Reader和 Proxy关联了起来。reader主要负责将服务器端响应解码到一种Store可以理解的格式。这是我们使用一个 JSON Reader和指定一个根目录和 successProperty配置参数。最后我们将创建我们的 data/users.json文件,并且将之前的数据粘进去:
{ "success": true, "users": [ {"id": 1, "name": 'Ed', "email": "ed@sencha.com"}, {"id": 2, "name": 'Tommy', "email": "tommy@sencha.com"} ] }
唯一的一个我们对Store进行的其他的改变是将autoLoad设置为true,这意味着Store将询问它的Proxy来立即加载数据。如果我们现在刷新页面,我们将会看到和之前同样的结果,除了现在我们不再硬编码到我们的应用中。
最后,我们想要做的是将我们的改变传回服务器。举个例子,我们正在在服务器端使用一个静态JSON文件,所以我们不会看到任何数据库的改变但是我们至少能够核实每一件事都被正确的连接在一起。第一我们将对我们的新proxy做一点小改变来告诉它将更新内容发送到一个不同的url:
proxy: { type: 'ajax', api: { read: 'data/users.json', update: 'data/updateUsers.json' }, reader: { type: 'json', root: 'users', successProperty: 'success' } }
我们仍然从users.json中读取数据,但是任何一次更新将会被发送到updateUsers.json。这正如我们知道的事情正在以不重写测试数据方式工作。之后更新一个记录, updateUsers.json文件刚好包括{"success": true}。由于它通过一个http端口指令更新,你可能不得不闯进一个空文件来避免接收一个404错误。
另一个我们需要做的改变是告诉我们的Store在编辑之后经自己同步,这个通过我们在 updateUser方法中额外增加一行,它现在看上去是这样:
updateUser: function(button) { var win = button.up('window'), form = win.down('form'), record = form.getRecord(), values = form.getValues(); record.set(values); win.close(); // synchronize the store after editing the record this.getUsersStore().sync(); }
现在我们能够跑完我们的完整示例,并确保一切都在工作。我们将编辑一行,点击保存按钮,会看到请就被正确的发送到了 updateUser.json中。

相关推荐
本讲将带你开启ExtJS的探索之旅,通过四个部分的学习,你将逐步掌握其核心概念和实践技巧。 首先,"初识ExtJS" 部分会介绍ExtJS的基本理念和架构,包括MVC(Model-View-Controller)设计模式的应用,以及如何利用这...
### 让我们开始EXTJS之旅 #### 2.1 认识ExtJS的开发包 在深入了解ExtJS之前,首先需要获取其开发包。官方推荐的下载途径是通过官方网站(www.ExtJS.com),确保能够得到最新的版本。下载链接通常位于...
开始ExtJs梦想之旅 第三讲.ExtJS工具栏、菜单栏 第四讲.ExtJS最常用的表单之textfield控件 第五讲.ExtJs最常用表单组件Number、CheckBox、Radio 第六讲.ExtJs最常用表单组件ComboBox、time、date 第七讲.ExtJS...
2、开始ExtJs梦想之旅# n8 }: ~+ d4 X+ V1 c 3、ExtJS工具栏、菜单栏0 Q' y0 E. y E 4、ExtJS最常用的表单之textfield控件4 |4 ]8 ~/ d3 Y& k# X 5、ExtJs最常用表单组件Number、CheckBox、Radio* s, r% ~+ k; y# W ...
根据提供的文件信息,我们可以归纳出一系列与ExtJS相关的学习资源及知识点。这些资源涵盖了ExtJS的基础到高级应用,包括视频教程、PDF文档以及PPT演示文稿...希望这些资料能帮助你在ExtJS的学习之旅上取得更大的进步!
《Extjs4.0学习指南》 Extjs4.0是一个强大的JavaScript框架,主要用于构建富客户端Web应用程序。其丰富的组件库、优雅的API和高度可定制性,使其成为开发复杂前端...希望这个指南能帮助你顺利开始Extjs4.0的学习之旅。
ExtJS 4.0是Sencha公司开发的一款强大的JavaScript前端框架,主要用于构建富客户端Web应用程序。...在ext-4.0.0这个压缩包中,包含了完整的框架文件和资源,开发者可以直接引入使用,开始自己的项目开发之旅。
下载并解压后,根据提供的说明文档或在线帮助,用户可以开始安装和使用这个工具,从而开启EXTJS的可视化开发之旅。通过深入学习和实践,开发者可以利用EXTJS的强大功能构建出高效、美观且功能丰富的Web应用。
为了开启ExtJS的学习之旅,首先需要获取其开发包。该开发包可从Sencha官网(http://www.sencha.com/)下载,确保能够获得最新版本。下载链接位于http://www.sencha.com/products/extjs/download/,下载文件名为`ext-...
综上,这个项目利用SpringMVC处理请求和控制流,MyBatis负责数据库操作,而ExtJS则构建前端交互界面。通过合理的集成和配置,可以实现一个功能完善的权限管理系统,为企业的后台操作提供安全保障。
EXTJS是一种基于JavaScript的前端框架,专用于构建...无论你是初学者还是有经验的开发者,这些教程都能为你的EXTJS之旅提供有力的支持。通过深入学习和实践,你将能够运用EXTJS构建出功能强大、用户体验优良的Web应用。
综上所述,ExtJS 6 不仅是一个功能强大的前端开发框架,还提供了一系列实用的工具和服务来支持整个开发周期。无论是初学者还是经验丰富的开发者,都可以从这本书中找到有价值的信息,帮助他们更好地掌握和运用这一...
- **组件学习之旅**:开启学习Extjs组件的旅程。 - **按钮**:介绍Extjs中按钮组件的各种特性和样式。 - **日期选择器Ext.DatePicker**:学习如何使用日期选择器组件。 #### 第十章:数据与ComboBox - **数据概念**...
在IT行业中,Web应用开发是一项核心技能,而ExtJS与.NET框架的结合使用可以构建出高效、用户友好的企业级应用程序。本实例旨在为新手提供一个学习平台,通过实际操作...希望这个实例能帮助你开启精彩纷呈的IT开发之旅。
#### 一、开始组件学习之旅 标志着从基本组件的学习开始,逐步构建更复杂的用户界面。 #### 二、被设计得面目全非的按钮 介绍了ExtJS中按钮组件的高级定制功能,包括图标、文本、工具提示等。 #### 三、日期选择器...
五、结论:从零开始的ExtJS之旅 无论是对于希望深入了解ExtJS的初学者,还是寻求.NET与前端技术融合方案的开发者,“Ext+net开发实例(殷良胜-完整版)”都是一份宝贵的资源。它不仅提供了详细的理论知识,还分享了...
EXTJS是一种基于JavaScript的前端框架,用于构建富客户端应用程序。EXTJS的核心是其强大的组件模型,它提供了丰富的...EXT简单案例作为入门资源,将帮助你快速上手EXTJS,理解其工作原理,并开始你的EXTJS开发之旅。
### GWT-Ext体验之旅知识点解析 #### 一、GWT-Ext简介 - **定义**: GWT-Ext是一款基于Google Web Toolkit (GWT) 和 ExtJS 的网页开发控件库,它为纯Java语言的富互联网应用提供了一个快速开发平台。 - **特点**: ...
《FMSoft UniGUI Beta 0.94.0.1024 安装程序详解》 FMSoft UniGUI 是一款基于Delphi开发的组件库,专为构建跨平台的Web应用程序而...通过安装这两个组件,开发者可以获得完整的开发环境,从而开启他们的Web开发之旅。
它采用先进的前端技术【Extjs】与后端服务器端包含SSI(Server Side Includes)框架相结合的方式,提供了高效、用户友好的界面以及强大的功能。 【Extjs】是一个JavaScript库,专为构建桌面级的Web应用而设计。它...