• MVC基本开发介绍 (1)列表展示


    前言:

    现在如果用.net 的解决方案来做网站或者是网站的后台管理系统,MVC 应该是比较流行的。

    自从进了新公司后,也一直在用mvc + webapi 来做项目,这里做个分享性的总结,有更好的方法欢迎分享,希望对初学者有帮助。

    正文:

      这里先说个工具,Web Essential ,具体使用参考这里,真的是个神器一般的存在,一定会对你的开发提供极大的便利。推荐大家使用最新版本,新功能,新特性值得一试。顺道提一下,如果你发现这个这个东西无法调用了,看看页面是不是少了body元素。

      项目是基本的mvc asp.net 4.5模板,不进行身份验证(这东西写起来感觉就多了。。)

    QQ20160309205711_thumb6_thumb

    确定之后项目应该是如下:

    QQ20160309210221_thumb1_thumb

    一个HomeController,有jquery, bootstrap(js+css)。

    这里顺便提一下Scripts 里面的_references.js 文件,他是给vs的智能提示用的,项目中引用的js文件默认都会被自动添加到该文件中,如果你发现vs的js提示不管用了,看看1:是不是引用的js不存在于这个文件中,2:是不是按顺序添加,比如bootstrap要引用jquery,所以jquery就应该在bootstrap前面,像下面这样。

    QQ20160309211418_thumb1_thumb

    一个一个来介绍,首先是最常见的列表页面。一般来说有两种做法

    1. 页面提交ajax请求,向服务端获取json格式的数据,然后用js来给面的元素赋值,可以参考这里.

    2. 用mvc的视图模板引擎直接生成视图页面。下面来简单说明一下:

    现在公司项目中ORM没有用微软推荐的EF,外加介绍起来东西也比较多,这里就直接模拟一下数据库了。

    新建一个静态DB类,给添加一个模拟数据,然后CRUD都对这些数据进行操作。代码如下:

        public static class DB
        {
            public static List<Person> Persons = new List<Person>()
            {
                new Person() { ID = 1,Name = "aaa",Birth = new DateTime(1991,1,1),IsAdmin  = true ,Gender = 1 },
                new Person() { ID = 1,Name = "bbb",Birth = new DateTime(1992,1,1),IsAdmin  = false  ,Gender = 2 },
                new Person() { ID = 1,Name = "ccc",Birth = new DateTime(1993,1,1),IsAdmin  = false ,Gender = 0 },
                new Person() { ID = 1,Name = "ddd",Birth = new DateTime(1994,1,1),IsAdmin  = false ,Gender = 2 },
    
            };
        }
        public class Person
        {
            public int ID { get; set; }
            public bool IsAdmin { get; set; }
            public String Name { get; set; }
            public short Gender { get; set; }
            public DateTime Birth { get; set; }
            public int Age
            {
                get
                {
                    return DateTime.Now.Year - Birth.Year;
                }
            }
    
        }

    我们把Index页面作为列表页,用Strong Type的model. Controller 里面就应该是这样:

            public ActionResult Index(string name = "")
            {
                var ps = DB.Persons.Where(w => w.Name.IndexOf(name) != -1);
                return View(ps);
            }

    name是我们的查询参数。

    View这样:

    @using BasicMVCCRUDExample.Models
    @model IEnumerable<Person>
    <div style="margin-top:30px;">
        <table class="table table-bordered text-center">
            <thead>
                <tr>
                    <th>ID</th>
                    <th>姓名</th>
                    <th>年龄</th>
                    <th>出生日期</th>
                    <th>性别</th>
                    <th>是管理员</th>
                    <th>操作</th>
                </tr>
            </thead>
            <tbody>
                @foreach (var p in Model) {
                    <tr>
                        <td>@p.ID</td>
                        <td>@p.Name</td>
                        <td>@p.Age</td>
                        <td>@p.Birth.ToShortDateString()</td>
                        <td>
                            @(p.Gender == 1 ? "男" : p.Gender == 2 ? "女" : "未知")
                        </td>
                        <td>
                            @Html.CheckBox("IsAdmin", p.IsAdmin)
                        </td>
                        <td>
                            <a>编辑</a>
                            <a>删除</a>
                        </td>
                    </tr>
                }
            </tbody>
        </table>
    </div>

    除了基本的数据展示,通常还会增加一列操作列,用于编辑和修改。

    第一行我们using了BasicMVCCRUDExample.Models这个命名空间,如果说这个namespace在这个controller对应的view里面用到的频率比较高,我们可以把他放到web.config里面,然后重开一下vs,就不需要在每个view里面引用一遍了。如下:

    QQ20160309215745_thumb1_thumb

    运行访问页面,效果如下。

    QQ20160309220319_thumb1_thumb

    然后我们给他加上搜索查询过滤的功能:

    controller里面已经加好了参数,下面是页面中。一般来说,我们把查询条件放到form表单里面提交,当然也可以自己用jquery ajax来模拟提交(有些情况下需要用到),这里先介绍一下form表单的。

    把原先的页面改成如下:

    @using BasicMVCCRUDExample.Models
    @model IEnumerable<Person>
    <div style="margin-top:30px;">
        @using (Html.BeginForm("Index", "Home", FormMethod.Get)) {
            <div class="row">
                <div class="col-md-3">
                    <input type="text" name="name" class="form-control" />
                </div>
                <div class="col-md-1">
                    <button class="btn btn-primary" type="submit">搜索</button>
                </div>
            </div>
        }
     <table>.....</table>
    </div>

    我们在table上面加了一个using块,用来渲染一个form标签。这里有两点要注意,

    1:搜索框的name属性一定要和查询参数名一样,controller里面Index ActionResult接收一个name参数,input的name属性值就必须是name,否则controller无法接收到。

    2. button标签,如果不给type属性,默认是submit,点一下按钮就会提交form,造成页面的刷新。所以这里标识一下。

    完成之后效果如下:

    QQ20160309222613_thumb1_thumb

    可以看一下地址栏,点搜索之后会给地址加上name参数。如果在搜索框里面写了条件,能实现对应的过滤。

    输入aaa,点搜索:

    QQ20160309222843_thumb1_thumb

    看地址栏变化,调试也可发现name 为aaa

    QQ20160309223000_thumb1_thumb

    一般来说,我们会希望这个搜索框的内容在搜索完之后还在里面,这样我们就需要aaa传给后台之后再传回来,最简单的做法就是放到ViewBag里面,然后回传到页面,再给页面的input value属性赋值。但这样做有个缺点,如果查询的条件比较多,Index方法参数就会比较多,ViewBag的就会多次赋值。所以,介绍另一个方法,用SearchModel的方式来实现。

    首先定义一个查询类:

    public class PersonSearchModel
        {
            //只有一个查询条件,所以只要一个属性
            public String Name { get; set; }
        }

    然后修改一下Index方法:

    public ActionResult Index(PersonSearchModel m)
            {
                m.Name += "";
                IEnumerable<Person> ps = DB.Persons.Where(p => p.Name.IndexOf(m.Name) != -1);
                ViewBag.PersonSearchModel = m;
                return View(ps);
            }

    Index 接收一个m,m不会为null,即使页面没有传参数。因为这里我们把name作为IndexOf方法的参数,所以name不能为null,所以我们给他加上一个空字符串.

    然后把这个m赋值给ViewBag。

    页面如下:

    @using BasicMVCCRUDExample.Models
    @model IEnumerable<Person>
    @{
        var searchM = (PersonSearchModel)ViewBag.PersonSearchModel;
    }
    <div style="margin-top:30px;">
        @using (Html.BeginForm("Index", "Home", FormMethod.Get)) {
            <div class="row">
                <div class="col-md-3">
                    <input type="text" name="name" class="form-control" value="@searchM.Name" />
                </div>
                <div class="col-md-1">
                    <button class="btn btn-primary" type="submit">搜索</button>
                </div>
            </div>
        }
        <table class="table table-bordered text-center">
            <thead>
                <tr>
                    <th>ID</th>
                    <th>姓名</th>
                    <th>年龄</th>
                    <th>出生日期</th>
                    <th>性别</th>
                    <th>是管理员</th>
                    <th>操作</th>
                </tr>
            </thead>
            <tbody>
                @foreach (var p in Model) {
                    <tr>
                        <td>@p.ID</td>
                        <td>@p.Name</td>
                        <td>@p.Age</td>
                        <td>@p.Birth.ToShortDateString()</td>
                        <td>
                            @(p.Gender == 1 ? "男" : p.Gender == 2 ? "女" : "未知")
                        </td>
                        <td>
                            @Html.CheckBox("IsAdmin", p.IsAdmin)
                        </td>
                        <td>
                            <a>编辑</a>
                            <a>删除</a>
                        </td>
                    </tr>
                }
            </tbody>
        </table>
    </div>

    先获取到这个searchM,由于ViewBag 的属性是dynamic类型,所以强制转换成我们的PersonSearchModel类型。然后用这个searchM给input的value属性赋值。再搜索,输入查询条件之后内容就能保存下来了。

    如果以后新加了查询条件,只要给searchModel加参数,然后页面赋值就可以了。

    QQ20160309224734_thumb1_thumb

    关于这个列表页面,暂时也就想到这么些东西,想到再加把。

    明天再写修改的。

  • 相关阅读:
    Unity下Reflection相关测试记录
    【疯狂造轮子-iOS】JSON转Model系列之一
    【原】FMDB源码阅读(三)
    【原】FMDB源码阅读(二)
    【原】FMDB源码阅读(一)
    (没时间维护,已下架)博客园第三方客户端-i博客园正式发布App Store
    【原】AFNetworking源码阅读(六)
    【原】AFNetworking源码阅读(五)
    【原】AFNetworking源码阅读(四)
    【原】AFNetworking源码阅读(三)
  • 原文地址:https://www.cnblogs.com/sheldon-lou/p/5260276.html
Copyright © 2020-2023  润新知