• CMS:文章管理之视图(1)


    文章管理的视图与文件管理区别不大,都是分左右两部分。文章管理的左边是树状的分类列表,右边以Grid形式显示的文章列表。基本上重复劳动比较多,使用Sencha Architect这个可视化工具来做这方面的设计,是不错的选择,如果公司收益好,强烈建议使用,一个开发包的价格是399美金,大约2800人民币,还是很划得来的,起码比请多个程序员划得来。

    废话又有点多了,转回正题,在Scripts\app\view目录下,创建一个Content目录,用来存放文章管理需要用到的视图,主要的视图包括文章管理的主视图、分类编辑窗口和文章编辑窗口。

    接着,在Content目录下创建一个名称为View.js的文件,用来定义主视图,基本结构代码如下:

    Ext.define('SimpleCMS.view.Content.View',{

        extend: 'Ext.container.Container',

        alias: 'widget.contentview',

        layout:"border",

     

        initComponent: function () {

            var me = this;

     

            me.callParent(arguments);

        }

     

    });

    接下来就是一步步添加组件了,先完成树的定义,代码如下:

    me.tree= Ext.widget("treepanel", {

        title: "文章类别", region: "west", collapsible: true, rootVisible:true, store: "CategoriesTree",

        200, minWidth: 100, split: true

    });

    接着是Grid,代码如下:

    me.grid= Ext.widget("grid", {

        title: "文章列表", region: "center",

        store: "Contents",

        selType: "checkboxmodel",

        selModel: { checkOnly: false, mode:"MULTI" },

        columns: [

                { text: '编号', dataIndex: 'ContentId', 80},

                { text: '标题', dataIndex: 'Title', flex: 1 },

            {xtype: "datecolumn", text: '创建时间', dataIndex: 'Created', format: "Y-m-d H:i:s", 150},

                { text: '排序序数', dataIndex: 'SortOrder', 80},

                { text: '点击量', dataIndex: 'Hits', 80 },

            { text: '标签', dataIndex: 'Tags',150 }

         ]

    });

    Grid使用了复选框作为选择行的方式,也是一向习惯了。其它方面,应该问题不大。

    最后是将树和Grid放到容器里,代码如下:

    me.items = [me.tree, me.grid];

    现在,可以测试一下效果了,不过,这还有修改控制器,切换到文章管理的控制器,在init方法内创建视图,并添加到面板里,这个应该很熟悉了,在用户管理和图片管理已经做过了。忘记了就直接复制过来修改一下创建的视图就行了,具体代码如下:

    var me= this,

        panel = me.getContentPanel(),

        view = Ext.widget("contentview");

    panel.add(view);

    代码的panel用到了getContentPanel方法,返回文章管理的面板,因而要添加引用,代码如下:

    refs: [

         { ref: "ContentPanel", selector:"#contentPanel" },

    ],

    当然了,不要忘记在views配置项内添加视图了,代码如下:

    views:[

        'Content.View'

    ],

    在浏览器打开后,屏幕居然什么都没显示出来,而在Firebug居然显示两个“Layout run failed”错误,说明布局有问题。这个在之前也碰到过了,就是主面板定义中,没定义文章管理面板的布局,现在切换到主面板的视图,在文章管理的面板定义上加回布局定义,布局使用Fitlayout。

    刷新一下浏览器,就可看到如图40的效果了。

     

    图40 文章管理的界面

    现在来完成分类树的功能,先完成树的显示。在完成前,先要用实体框架,将数据库中的表转换为对象。在解决方案内添加一个新项,然后如图41所示,在添加新项窗口中,先选择数据模版,然后在中间选择ADO.NET实体数据模型,将名称修改为SimpleCMS.edmx后,单击添加按钮。

     

    图41 添加实体框架

    在弹出的如图42所示的实体数据模型向导窗口中,选择从数据库生成,然后单击下一步。

     

    图42 实体数据模型向导窗口

    在切换到如图43所示的选择您的数据连接窗口中,可以单击新建连接按钮新建一个连接。在不过,默认的ApplicationServices连接是在配置文件中定义好的连接,可以直接使用,就不必再创建新的了。选上“是,在连接字符串中包括敏感数据”后,单击下一步按钮。当然,如果不喜欢在Web.Config文件包含用户名和密码这些敏感数据,可以另行处理。

     

    图43 选择数据连接

    在如图44所示的选择数据库对象窗口中,展开树中的表,然后如图那样选择以“T_”开头的4个表格,然后单击完成按钮结束向导。

     

    图44 选择数据库对象

    等待生成完成后,会在解决方案中看到如图45所示的数据结构图。

     

    图45 生成的数据结构图

    看到图,一定会疑惑,为什么刚才选择了4个表格,怎么在这里只看到3个对象?这是因为连接表T_Content和T_Tag的关联表在对象中只是一种多对多关系,隐含在对象中了,因而,不需要像数据库那样,显式的表示成一个对象。

    这里还要为T_Category添加一个关联,让父节点可以找到它的子节点。在T_Category 的图中单击鼠标右键,在右键菜单中选择添加>关联,在如图46所示的添加关联对话框中,修改右边的实体为T_Category,接着修改左边的多重性为“0...1(零或一个)”。接着修改左边的导航属性为Childs,这样,就可通过childs属性访问子节点了。然后将右边的导航属性修改为Parent,这样,通过Parent属性就可访问到父节点了。把复选框的勾去掉后,单击确定按钮完成添加关联操作。

    图46 添加关联对话框

    接着在右边的属性列表中,编辑引用约束,在如图47的引用约束对话框中,选择主体为T_Category,然后在表格中将CategoryId的依赖属性设置为ParentId。

    图47 引用约束对话框

    保存一下解决方案,然后新建一个服务器端的控制器Category,添加必要的引用后,添加一个只读的私有变量dc,用来访问SimpleCMSEntities的实例,代码如下:

    private readonly SimpleCMSEntities dc = newSimpleCMSEntities();

    分类树的Store调用的是List方法,因而将Index方法修改为List方法,并加入相应的权限、返回对象和基本结构代码,代码如下:

    [AjaxAuthorize(Roles= "普通用户,系统管理员")]

    publicJObject List()

    {

        bool success = false;

        string msg = "";

        JArray ja = new JArray();

        int total = 0;

        try

        {

            success = true;

     

        }

        catch (Exception e)

        {

            msg = e.Message;

        }

        returnHelper.MyFunction.WriteJObjectResult(success, total, msg, ja);

    }

    树展开一个节点,都会以node作为参数将该节点的id提交,因而,在提取数据是,首先要做的是先从node提取id,代码如下:

    intid=-1;

    int.TryParse(Request["node"], out id);

    因为在定义Store时,根节点的id为-1,因而这里要分两种情况处理搜索结果,代码如下:

    IQueryable<T_Category>q = null;

    if (id== -1)

    {

        q = dc.T_Category.Where(m =>m.Hierarchylevel == 0 & m.State == 0).OrderBy(m=>m.Title);

    }

    else

    {

        q = dc.T_Category.Where(m => m.ParentId== id & m.State == 0).OrderBy(m => m.Title);

    }

    代码中,当id为-1时,就搜索层数为0的记录,否则,则搜索ParentId的等于id的记录。

    这里有个问题,因为记录根据标题进行了排序,因而未分类这个类别就不知道跑到那个位置去了,因而,为了保持为分类在顶部,在查询的时候最好把它排除出去,另外再添加到结果中,代码修改如下:

    q =dc.T_Category.Where(m => m.Hierarchylevel == 0 & m.CategoryId!=10000& m.State == 0).OrderBy(m=>m.Title);

    现在要写数据到ja里面了,因为要多次写相同格式的对象,因而,把写对象独立为一个方法比较好,代码如下:

    privateJObject writeNode(int id, string text, int parentId, bool isLeaf)

    {

        JObject jo = new JObject

        {

            new JProperty("id",id),

            new JProperty("text",text),

            newJProperty("parentId",parentId),

            new JProperty("leaf",newJValue(isLeaf))

        };

        if (!isLeaf)

        {

            jo.Add(new JProperty("children",new JArray()));

        }

        return jo;

    }

    从代码可以看到,方法带4个参数,前3个参数就是返回节点所需的id、text和parentId的字段。而isLeaf的作用就是判断节点是否有子节点,如果有,就添加一个children属性,这样在客户端就能看到一个加号,可以展开。

    现在,先在id等于-1时的查询语句下添加以下两个节点:

    ja.Add(writeNode(-99,"全部", -1,true));

    ja.Add(writeNode(10000, "未分类", -1, true));

    添加全部节点,目的是为了方便查看数据,如果不喜,可不要。未分类这个是必须的。注意两个节点的id。

    接着就是在判断语句后用循环输出节点了,代码如下:

    foreach(var c in q)

    {

        bool leaf = c.Childs.Count() > 0 ? false: true;

        int pid = c.ParentId == null ? -1 :(int)c.ParentId;

        ja.Add(writeNode(c.CategoryId, c.Title,pid, leaf));

    }

    在代码中,使用到了刚才设置的关联,通过统计子节点的个数来判断该节点是否有子节点。

    生成一下解决方案,然后刷新一下页面。喔,根节点没自动打开,而且也没隐藏。先切换到树的Store定义,为根节点添加一个expanded配置项,值为true,让它自动展开。然后切换到视图定义,将rootVisible配置项设置为false。这些事情在复制粘贴过程中经常会发生。

    好了,现在刷新一下页面,就会看到如图48的效果了。

    图48 文章类别树的显示结果

    这样,树的显示就完成了,下文继续。

     源代码下载:http://vdisk.weibo.com/s/hL6up

  • 相关阅读:
    魅族多机房部署方案-tech_meizu-ChinaUnix博客
    环信首席架构师:一个单元化架构的例子-CSDN.NET
    双活数据中心解决方案(最新)_图文_百度文库
    阿里巴巴分布式数据库服务DRDS研发历程
    OpenDigg
    Qcon
    有赞应用层网关剖析
    Enterprise Architect-工具-火龙果软件
    (80 条消息) 哪些管理类的书籍值得推荐?
    【图文】拉姆查兰-领导梯队_百度文库
  • 原文地址:https://www.cnblogs.com/muyuge/p/6333736.html
Copyright © 2020-2023  润新知