1.LayUI页面效果展示
本猿只是简单地使用LayUi做了这么一个页面效果,想深入了解LayUi,请访问官网[link]https://www.layui.com/
方便大家看懂源码,本猿会在源码中予以注释,如有错误,请在评论中指出!
1.1 配件管理
相较于EasyUI,很漂亮有木有?!?
1.2 弹出层form表单
1.2.1 添加
1.2.2 修改
数据回显
1.3 其他功能展示
1.3.1 删除与批量删除
1.3.2 筛选列,导出,打印
这三项功能LayUI已经为我们写好了,不需要我们在后台实现功能;暖暖的,很贴心!
2.前端源码
2.1 parts.jsp
<!DOCTYPE html>
<%--
Created by IntelliJ IDEA.
User: DieuKing
Date: 2019/4/11
Time: 16:38
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>配件</title>
<link rel="stylesheet" href="/static/js/layui/css/layui.css" media="all">
<script type="text/javascript" src="/static/js/layui/layui.js"></script>
<%--导入jQuery的支持包--%>
<script type="text/javascript" src="/static/js/jquery.min.js"></script>
<script type="text/javascript" src="/static/js/jquery.form.min.js"></script>
<%--自定义js--%>
<script type="text/javascript" src="/static/js/model/parts/parts.js"></script>
</head>
<body>
<fieldset class="layui-elem-field site-demo-button">
<legend>查询模块</legend>
<div class="layui-form">
<div class="layui-form-item">
<label class="layui-form-label">配件名称</label>
<div class="layui-input-block">
<input type="text" name="name" id="name" lay-verify="" placeholder="请输入配件名称"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">起始时间</label>
<div class="layui-input-block">
<input type="text" name="startTime" id="startTime" lay-verify="" placeholder="请选择起始时间"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">截至时间</label>
<div class="layui-input-block">
<input type="text" name="endTime" id="endTime" lay-verify="" placeholder="请选择截至时间"
autocomplete="off" class="layui-input">
</div>
</div>
<button class="layui-btn" lay-submit lay-filter="search"><i class="layui-icon"></i>高级查询</button>
</div>
</fieldset>
<fieldset class="layui-elem-field site-demo-button">
<legend>配件基本信息</legend>
<div>
<table id="parts_table" lay-filter="parts_table"></table>
</div>
</fieldset>
<%--弹出表单--%>
<div class="layui-row" id="parts_formpopbox" style="display:none;position: absolute;
top: 0; left: 0; bottom: 0; right: 0;">
<div class="layui-col-md11">
<form id="parts_form" class="layui-form" action="" style="margin-top: 20px;align:center;">
<%--隐藏字段id,区分添加和修改--%>
<input type="hidden" name="id"/>
<div class="layui-form-item">
<label class="layui-form-label">配件名称</label>
<div class="layui-input-block">
<input type="text" name="partsname" id="partsname" lay-verify="required" placeholder="请输入配件名称"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">配件价格</label>
<div class="layui-input-block">
<input type="text" name="price" id="price" lay-verify="required" placeholder="请输入价格"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">配件数量</label>
<div class="layui-input-block">
<input type="text" name="num" id="num" lay-verify="required" placeholder="请输入数量"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">预警数量</label>
<div class="layui-input-block">
<input type="text" name="warnnum" id="warnnum" lay-verify="required" placeholder="请输入预警数量"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<div class="layui-inline">
<label class="layui-form-label">入库时间</label>
<div class="layui-input-inline">
<input type="text" class="layui-input" id="createtime" name="createtime" placeholder="请输入入库时间">
</div>
</div>
</div>
<div class="layui-form-item">
<label class="layui-form-label">配件描述</label>
<div class="layui-input-block">
<input type="text" name="context" id="context" lay-verify="required" placeholder="请输入配件描述"
autocomplete="off" class="layui-input">
</div>
</div>
<div class="layui-form-item">
<div class="layui-input-block">
<button class="layui-btn layui-btn-radius layui-btn-normal" lay-submit=""
lay-filter="parts_submit" <%--onclick="parts_submit()"--%>>确认
</button>
<%--<input type="button" class="layui-btn layui-btn-radius layui-btn-normal" value="确认" onclick="parts_submit()" />--%>
<button type="reset" class="layui-btn layui-btn-radius layui-btn-primary">重置</button>
</div>
</div>
</form>
</div>
</div>
<%-- 这里放头工具栏按钮 id和table头的toolbar属性绑定--%>
<script type="text/html" id="parts_toolbar">
<div class="layui-btn-container">
<button class="layui-btn layui-btn-danger layui-btn-sm" lay-event="delAll"><i class="layui-icon"></i>批量删除
</button>
<button class="layui-btn layui-btn-sm layui-btn-warm" lay-event="add" <%--onclick=""--%>><i class="layui-icon"></i>添加
</button>
</div>
</script>
<%-- 这里放CRUD行工具栏按钮 id和table行的toolbar属性绑定--%>
<script type="text/html" id="form_bar">
<a <%--class="layui-btn layui-btn-primary layui-btn-xs"--%> lay-event="detail" title="查看"><i class="layui-icon"></i></a>
<a <%--class="layui-btn layui-btn-xs"--%> lay-event="edit" title="编辑"><i class="layui-icon"></i></a>
<a <%--class="layui-btn layui-btn-danger layui-btn-xs"--%> lay-event="del" title="删除"><i
class="layui-icon"></i></a>
</script>
</body>
</html>
2.2 parts.js
//序列化form表单字段为json对象格式
$.fn.serializeFormToJson = function () {
var arr = $(this).serializeArray();//form表单数据 name:value
var param = {};
$.each(arr, function (i, obj) { //将form表单数据封装成json对象
param[obj.name] = obj.value;
})
return param;
}
/**
* 注意:这里使用了上面的方式,没有使用这种-------------------------------------------
* 将form里面的内容序列化成json
* 相同的checkbox用分号拼接起来
* @param {dom} 指定的选择器
* @param {obj} 需要拼接在后面的json对象
* @method serializeJson
* */
$.fn.serializeJson = function (otherString) {
var serializeObj = {},
array = this.serializeArray();
$(array).each(function () {
if (serializeObj[this.name]) {
serializeObj[this.name] += ';' + this.value;
} else {
serializeObj[this.name] = this.value;
}
});
if (otherString != undefined) {
var otherArray = otherString.split(';');
$(otherArray).each(function () {
var otherSplitArray = this.split(':');
serializeObj[otherSplitArray[0]] = otherSplitArray[1];
});
}
return serializeObj;
};
/**
* 将josn对象赋值给form
* @param {dom} 指定的选择器
* @param {obj} 需要给form赋值的json对象
* @method serializeJson
* */
$.fn.setForm = function (jsonValue) {
var obj = this;
$.each(jsonValue, function (name, ival) {
var $oinput = obj.find("input[name=" + name + "]");
if ($oinput.attr("type") == "checkbox") {
if (ival !== null) {
var checkboxObj = $("[name=" + name + "]");
var checkArray = ival.split(";");
for (var i = 0; i < checkboxObj.length; i++) {
for (var j = 0; j < checkArray.length; j++) {
if (checkboxObj[i].value == checkArray[j]) {
checkboxObj[i].click();
}
}
}
}
}
else if ($oinput.attr("type") == "radio") {
$oinput.each(function () {
var radioObj = $("[name=" + name + "]");
for (var i = 0; i < radioObj.length; i++) {
if (radioObj[i].value == ival) {
radioObj[i].click();
}
}
});
}
else if ($oinput.attr("type") == "textarea") {
obj.find("[name=" + name + "]").html(ival);
}
else {
obj.find("[name=" + name + "]").val(ival);
}
})
}
//注册组件
layui.use(['table', 'layer', 'form', 'laypage', 'laydate', 'upload'], function () {
var laydate = layui.laydate
, table = layui.table
, form = layui.form
, upload = layui.upload;
/**
* 高级查询时间范围
* 其中:开始时间不能大于截至时间
*/
var startDate = laydate.render({
elem: '#startTime'
// ,theme: 'grid' //自定义时间版主题
, type: 'datetime'
, max: "2099-12-31" //设置一个默认最大值
, done: function (value, date) {
endDate.config.min = {
year: date.year,
month: date.month - 1, //关键
date: date.date,
hours: 0,
minutes: 0,
seconds: 0
};
}
});
var endDate = laydate.render({
elem: '#endTime'
// ,theme: 'grid' //自定义时间版主题
, type: 'datetime'
, min: "1970-1-1",//设置min默认最小值
done: function (value, date) {
startDate.config.max = {
year: date.year,
month: date.month - 1,//关键
date: date.date,
hours: 0,
minutes: 0,
seconds: 0
}
}
});
/**
* 添加或修改时间框
*/
laydate.render({
elem: '#createtime'
, type: 'datetime'
});
/**
* 配件表
*/
table.render({
elem: '#parts_table'
, fit: true
, url: '/parts/page' //数据接口
, toolbar: '#parts_toolbar' //自定义工具栏
// , toolbar: true // true为layui的默认工具栏,默认工具栏中只包含筛选列,导出和打印功能
, page: true //开启分页
// , height: $(document).height() - $('#parts_form').offset().top - 15 //固定分页栏
/**
* layui返回table表数据是有相应格式的
* @param res
* @returns {{code: number, msg: string, count: number, data: *}}
*/
/*
,parseData:function (res) {
console.log(res);
return{
"code":0,
"msg":"",
"count":1000,
data:res
}
}*/
, cols: [[ //表头
{type: 'checkbox', fixed: 'left'}
/*,{field: 'id', title: 'ID', sort: true, fixed: 'left'}*/
, {field: 'partsname', title: '配件名称'}
, {field: 'price', title: '价格', sort: true}
, {field: 'num', title: '数量',templet:function (data) {
if(data.num>data.warnnum){
return "<span class='btnNot' style='color:green;'>"+data.num+"</span>";
}else if(data.num<data.warnnum){
return "<span class='btnNot' style='color: red;'>"+data.num+"</span>";
}else {
return "<span class='btnNot' style='color:yellow'>"+data.num+"</span>";
}
}}
, {field: 'warnnum', title: '预警数量'}
, {field: 'context', title: '配件描述', sort: true}
, {field: 'createtime', title: '入库时间', sort: true}
, {fixed: 'right', width: 165, align: 'center', toolbar: '#form_bar'}
]],
id: "partslist" //重载表的时候被引用, table.reload('partslist');
});
//监听头工具栏事件
table.on('toolbar(parts_table)', function (obj) {
var checkStatus = table.checkStatus(obj.config.id)
, data = checkStatus.data; //获取选中的数据
//json字符串转换成Json数据 eval("("+jsonStr+")") /JSON.parse(jsonStr)
data = eval("(" + JSON.stringify(data) + ")");
switch (obj.event) {
case 'delAll':
if (data.length === 0) {
layer.msg('请至少选择1行', {icon: 2, time: 1500});
} else {
layer.alert('您确认要删除' + data.length + '条数据吗?', {
skin: 'layui-layer-molv' //样式类名layui-layer-lan或layui-layer-molv 自定义样式
, closeBtn: 1 // 是否显示关闭按钮
, anim: 1 //动画类型
, btn: ['确定', '取消'] //按钮
, icon: 2 // icon
, yes: function () {
// layer.msg('确定', { icon: 1, time: 1500 });
for (var i = 0; i < data.length; i++) {
console.debug("id:======" + data[i].id)
//发送请求到后台
$.post("parts/delete", {id: data[i].id}, function (result) {
if (result.success == true) {//删除成功,刷新当前页表格
// obj.del(); //删除对应行(tr)的DOM结构,并更新缓存
layer.msg(result.msg, {icon: 1, time: 1500});
// layer.close(index);
$(".layui-laypage-btn").click();//点击分页刷新当前页
} else if (result.success == false) { //删除失败
layer.alert(result.msg, {icon: 2}, function () {
$(".layui-laypage-btn").click();
window.location.reload();
});
}
});
}
/* //捉到所有被选中的,发异步进行删除
layer.msg('删除成功', {icon: 1});
$(".layui-form-checked").not('.header').parents('tr').remove();*/
}
, btn2: function () {
layer.msg('好的,暂时不给您删除。', {icon: 1, time: 1500});
}
});
}
break;
/**
* 弹出添加表格
*/
case 'add':
parts_form('添加菜单', 'url这个值不管', '', '');
$("#parts_form").setForm({id: data.id, partsname: data.partsname, price: data.price, num: data.num});
break;
}
});
//监听行工具事件
table.on('tool(parts_table)', function (obj) { //注:tool 是工具条事件名,parts_table 是 table 原始容器的属性 lay-filter="对应的值"
var data = obj.data //获得当前行数据
, layEvent = obj.event; //获得 lay-event 对应的值(也可以是表头的 event 参数对应的值)
var tr = obj.tr; //获得当前行 tr 的DOM对象
switch (layEvent) {
case 'detail':
//json字符串转换成Json数据 eval("("+jsonStr+")") /JSON.parse(jsonStr)
var jsonstr = JSON.stringify(data);//json数据转字符串 JSON.stringify(obj)
layer.alert(jsonstr);
break;
case 'del':
layer.confirm('您确定删除id:' + data.id + '的数据吗?', function (index) {
//向服务端发送删除指令,在这里可以使用Ajax异步
$.post("parts/delete", {id: data.id}, function (ret) {
if (ret.success == true) {//删除成功,刷新当前页表格
layer.msg(ret.msg, {icon: 1, time: 1500}, function () {
obj.del(); //删除对应行(tr)的DOM结构,并更新缓存
layer.close(index);
// $(".layui-laypage-btn").click();//点击分页刷新当前页
});
} else if (ret.success == false) { //删除失败
layer.alert(ret.msg, {icon: 2}, function () {
layer.close(index);
// $(".layui-laypage-btn").click();
window.location.reload();
});
}
});
});
break;
/**
* 弹出编辑表格
*/
case 'edit':
console.debug(data);
parts_form('编辑菜单', 'url这个值不管', 500, 400);
//回显数据
$("#parts_form").setForm({
id: data.id,
partsname: data.partsname,
price: data.price,
num: data.num,
warnnum: data.warnnum,
createtime: data.createtime,
context: data.context
});
break;
}
});
//监听单元格编辑 parts_table 对应 <table> 中的 lay-filter="parts_table" 做可编辑表格使用
table.on('edit(parts_table)', function (obj) {
var value = obj.value //得到修改后的值
, data = obj.data //得到所在行所有键值
, field = obj.field; //得到字段
layer.msg('[ID: ' + data.id + '] ' + field + ' 字段更改为:' + value);
});
//监听提交 lay-filter="parts_submit"
form.on('submit(parts_submit)', function (data) {
console.log(data.field) //当前from表单所提交的所有字段, 名值对形式:{name: value}
// layer.msg(JSON.stringify(data.field));//表格数据序列化
var formData = data.field;
var id = formData.id,
partsname = formData.partsname,
price = formData.price,
num = formData.num,
warnnum = formData.warnnum,
createtime = formData.createtime,
context = formData.context;
$.ajax({
type: "post", //数据提交方式(post/get)
url: "/parts/save", //提交到的url
data: {
"id": id,
"partsname": partsname,
"price": price,
"num": num,
"warnnum": warnnum,
"createtime": createtime,
"context": context
},//提交的数据
dataType: "json",//返回的数据类型格式
success: function (msg) {
if (msg.success) { //成功
//关闭编辑窗口
layer.closeAll();
//弹出提示窗口
layer.alert(msg.msg, {icon: 1, time: 2500, title: '操作成功'});
//刷新parts_table
table.reload('partslist');
} else { //失败
layer.open({
icon: 2,
// time:1500,
type: 0,
title: '操作失败',
content: msg.msg,
area: ['500px', '300px']
});
}
}
});
/*
$.post('/parts/save', data.field, function (r) {
console.log(data.field);
if (r.success) {
layer.msg(r.msg, {icon: 1, time: 1500, title: '操作成功'});
//关闭窗口
layer.closeAll();
//刷新parts_table
table.reload('partslist');
} else {
layer.open({
icon: 2,
// time:1500,
type: 0,
title: '操作失败',
content: r.msg,
area: ['500px', '300px']
});
}
});*/
return false;//false:阻止表单跳转 true:表单跳转
});
//高级查询--监听提交 lay-filter="search"
form.on('submit(search)', function (data) {
// layer.msg(JSON.stringify(data.field));//表格数据序列化
var formData = data.field;
console.debug(formData);
var name = formData.name,
startTime = formData.startTime,
endTime = formData.endTime;
if (name == "" && startTime == "" && endTime == "") {
layer.alert('请输入筛选条件!', {icon: 2, time: 1500});
return false;
}
//数据表格重载
table.reload('partslist', {
page: {
curr: 1 //重新从第 1 页开始
}
, where: {//这里传参 向后台
name: name,
startTime: startTime,
endTime: endTime
}
, url: '/parts/advancedQuery'//后台做模糊搜索接口路径
, method: 'post'
});
/**
* 发送Ajax请求
*/
/*$.ajax({
type: "post", //数据提交方式(post/get)
url: "/parts/advancedQuery", //提交到的url
data: {
"name": name,
"startTime": startTime,
"endTime": endTime,
},//提交的数据
dataType: "json",//返回的数据类型格式
});*/
return false;//false:阻止表单跳转 true:表单跳转
});
});
var index;//layer.open 打开窗口后的索引,通过layer.close(index)的方法可关闭
//表单弹出层
function parts_form(title, url, w, h) {
if (title == null || title == '') {
title = false;
}
;
if (url == null || url == '') {
}
;// url="404.html";
if (w == null || w == '') {
w = ($(window).width() * 0.9);
}
;
if (h == null || h == '') {
h = ($(window).height() - 50);
}
;
index = layer.open({ //layer提供了5种层类型。可传入的值有:0(信息框,默认)1(页面层)2(iframe层)3(加载层)4(tips层)
type: 1,
title: title,
area: ['25%', '55%'],//类型:String/Array,默认:'auto' 只有在宽高都定义的时候才不会自适应
// area: [w+'px', h +'px'],
fix: false, //不固定
maxmin: true,//开启最大化最小化按钮
shadeClose: true,//点击阴影处可关闭
shade: 0.4,//背景灰度
skin: 'layui-layer-rim', //加上边框
content: $("#parts_formpopbox")
});
}
3.后端源码
后端部分,我采用的是SSM框架,至于SSM框架的搭建,我在之前的博客中已经详细介绍了,在这儿,我就不再赘述了。
3.1 domain
注意:字段需与数据库中表的字段相同!
Parts.java
public class Parts {
//配件id
private Long id;
//配件名称
private String partsname;
//配件价格
private BigDecimal price;
//配件实时数量
private int num;
//配件预警数量
private Integer warnnum;
//配件描述
private String context;
//配件入库时间
private Date createtime;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getPartsname() {
return partsname;
}
public void setPartsname(String partsname) {
this.partsname = partsname;
}
public BigDecimal getPrice() {
return price;
}
public void setPrice(BigDecimal price) {
this.price = price;
}
public int getNum() {
return num;
}
public void setNum(int num) {
this.num = num;
}
public Integer getWarnnum() {
return warnnum;
}
public void setWarnnum(Integer warnnum) {
this.warnnum = warnnum;
}
public String getContext() {
return context;
}
public void setContext(String context) {
this.context = context;
}
//hh为12小时制,HH为24小时制;GMT+8 东八区
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
public Date getCreatetime() {
return createtime;
}
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
public void setCreatetime(Date createtime) {
this.createtime = createtime;
}
@Override
public String toString() {
return "Parts{" +
"id=" + id +
", partsname='" + partsname + '\'' +
", price=" + price +
", num=" + num +
", warnnum=" + warnnum +
", context='" + context + '\'' +
", createtime=" + createtime +
'}';
}
}
3.2 mapper
也就是dao层
我这儿抽取了一个父类写公共的方法,当有很多子类时,就不需要重复写相同代码了,子类可以在自己的类中写其独有的方法。
BaseMapper.java
public interface BaseMapper<T> {
int deleteByPrimaryKey(Long id);
int insert(T t);
T selectByPrimaryKey(Long id);
List<T> selectAll();
int updateByPrimaryKey(T t);
List<T> findByPage(BaseQuery query);
}
PartsMapper.java
public interface PartsMapper extends BaseMapper<Parts>{
/**
* 高级查询
* @param partsQuery
* @return advancedQuery
*/
List<Parts> advancedQuery(PartsQuery partsQuery);
}
3.3 resources
xml文件为MyBatis代码生成器生成的(除高级查询外),想要了解,可以查看我之前写的博客;当然自己写也并不麻烦!
PartsMapper.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="cn.dieu.rpms.mapper.PartsMapper">
<resultMap id="BaseResultMap" type="cn.dieu.common.domain.Parts">
<id column="id" property="id" jdbcType="BIGINT"/>
<result column="partsname" property="partsname" jdbcType="VARCHAR"/>
<result column="price" property="price" jdbcType="DECIMAL"/>
<result column="num" property="num" jdbcType="BIGINT"/>
<result column="warnnum" property="warnnum" jdbcType="BIGINT"/>
<result column="context" property="context" jdbcType="VARCHAR"/>
<result column="createtime" property="createtime" jdbcType="TIMESTAMP"/>
</resultMap>
<delete id="deleteByPrimaryKey" parameterType="java.lang.Long">
delete from t_parts
where id = #{id,jdbcType=BIGINT}
</delete>
<insert id="insert" parameterType="cn.dieu.common.domain.Parts">
insert into t_parts (partsname, price,
num, warnnum, createtime, context)
values (#{partsname,jdbcType=VARCHAR}, #{price,jdbcType=DECIMAL},
#{num,jdbcType=BIGINT}, #{warnnum,jdbcType=BIGINT}, #{createtime,jdbcType=TIMESTAMP},
#{context,jdbcType=VARCHAR})
</insert>
<update id="updateByPrimaryKey" parameterType="cn.dieu.common.domain.Parts">
update t_parts
set partsname = #{partsname,jdbcType=VARCHAR},
price = #{price,jdbcType=DECIMAL},
num = #{num,jdbcType=BIGINT},
warnnum = #{warnnum,jdbcType=BIGINT},
context = #{context,jdbcType=VARCHAR},
createtime = #{createtime,jdbcType=TIMESTAMP}
where id = #{id,jdbcType=BIGINT}
</update>
<select id="selectByPrimaryKey" resultMap="BaseResultMap" parameterType="java.lang.Long">
select id, partsname, price, num, warnnum, context, createtime
from t_parts
where id = #{id,jdbcType=BIGINT}
</select>
<!--查询所有数据-->
<select id="selectAll" resultMap="BaseResultMap">
select id, partsname, price, num, warnnum, context, createtime
from t_parts
</select>
<!--分页查询-->
<select id="findByPage" resultMap="BaseResultMap">
select id, partsname, price, num, warnnum, context, createtime
from t_parts
</select>
<!--高级查询-->
<select id="advancedQuery" parameterType="cn.dieu.common.query.PartsQuery" resultMap="BaseResultMap">
SELECT *
FROM t_parts
<include refid="whereSql"></include>
</select>
<!-- sql:放的一些代码片断 -->
<sql id="whereSql">
<where>
<if test="name!=null and name!=''">
AND partsname LIKE CONCAT("%",#{name},"%")
</if>
<if test="startTime !=null and startTime !='' ">
<![CDATA[ and createtime >= #{startTime} ]]>
</if>
<if test="endTime !=null and endTime!='' ">
<![CDATA[ and createtime <= #{endTime} ]]>
</if>
</where>
</sql>
</mapper>
3.4 service
3.4.1 IXxxService
IBaseService.java
public interface IBaseService<T> {
void save(T t);
void update(T t);
void delete(Long id);
T findOne(Long id);
List<T> findAll();
PageUi<T> findByQuery(BaseQuery query);
}
IPartsService.java
public interface IPartsService extends IBaseService<Parts> {
/**
* 高级查询
*/
PageUi<Parts> advancedQuery(PartsQuery partsQuery);
}
3.4.2 XxxServiceImpl
BaseServiceImpl.java
@Transactional(readOnly = true,propagation = Propagation.SUPPORTS)
public
abstract class BaseServiceImpl<T> implements IBaseService<T> {
//Basic没有引入spring相关包,不能使用注解注入,在具体service上实现本方法
protected abstract BaseMapper<T> getMapper();
@Override
@Transactional
public void save(T t) {
getMapper().insert(t);
}
@Override
@Transactional
public void update(T t) {
getMapper().updateByPrimaryKey(t);
}
@Override
@Transactional
public void delete(Long id) {
getMapper().deleteByPrimaryKey(id);
}
@Override
public T findOne(Long id) {
return getMapper().selectByPrimaryKey(id);
}
@Override
public List<T> findAll() {
return getMapper().selectAll();
}
@Override
public PageUi<T> findByQuery(BaseQuery query) {
PageUi<T> pageUi = new PageUi<>();
Page page = PageHelper.startPage(query.getPage(), query.getLimit());
//查询当前页的数据
Page<T> data = (Page<T>) getMapper().findByPage(query);
//获取总条数
long count = page.getTotal();
pageUi.setCount(count);
pageUi.setData(data);
return pageUi;
}
}
PartsServiceImpl.java
@Service
public class PartsServiceImpl extends BaseServiceImpl<Parts> implements IPartsService {
@Autowired
private PartsMapper partsMapper;
@Override
protected BaseMapper<Parts> getMapper() {
return partsMapper;
}
@Override
public PageUi<Parts> advancedQuery(PartsQuery partsQuery) {
PageUi<Parts> pageUi = new PageUi<>();
Page<Parts> page = PageHelper.startPage(partsQuery.getPage(), partsQuery.getLimit());
//查询当前页数据
Page<Parts> parts = (Page<Parts>)partsMapper.advancedQuery(partsQuery);
//获取总条数
long total = page.getTotal ();
//
pageUi.setCount(total);
pageUi.setData(parts);
return pageUi;
}
}
3.5 web.controller
与前台实现数据交互
PartsController.java
@Controller
@RequestMapping("/parts")
public class PartsController {
@Autowired
private IPartsService partsService;
@RequestMapping("/parts")
public String index(){
return "parts/parts";
}
//查询所有配件信息
@RequestMapping("/list")
@ResponseBody
public List<Parts> findAll() {
return partsService.findAll();
}
//分页查询
@RequestMapping("/page")
@ResponseBody
public PageUi<Parts> findByPage(PartsQuery partsQuery) {
return partsService.findByQuery(partsQuery);
}
//返回的结果:{success:true,msg:xxxx}
@RequestMapping("/save")
@ResponseBody
public JsonResult save(Parts parts){
System.out.println(parts);
try {
if(parts.getId()!=null){
//有id就是修改
partsService.update(parts);
return new JsonResult(true,"修改成功!");
}else {
partsService.save(parts);
return new JsonResult(true,"添加成功!");
}
} catch (Exception e) {
e.printStackTrace();
return new JsonResult(false,e.getMessage());
}
}
@RequestMapping("/delete")
@ResponseBody
public JsonResult delete(Long id){
try {
partsService.delete(id);
return new JsonResult(true,"删除成功!");
} catch (Exception e) {
e.printStackTrace();
return new JsonResult(false,e.getMessage());
}
}
/*@RequestMapping("/delAll")
@ResponseBody
public JsonResult delAll(Long [] ids){
JsonResult jsonResult = new JsonResult();
try {
for(Long id:ids){
partsService.delete(id);
}
} catch (Exception e) {
e.printStackTrace();
jsonResult = new JsonResult(false, e.getMessage());
}
return jsonResult;*//*
}*/
/**
* 高级查询
* @param partsQuery
* @return
*/
@RequestMapping("/advancedQuery")
@ResponseBody
public PageUi<Parts> advancedQuery(PartsQuery partsQuery){
return partsService.advancedQuery(partsQuery);
}
@RequestMapping("/findOne")
@ResponseBody
public Parts findOne(Long id){
return partsService.findOne(id);
}
}
3.6 query
用于封装前台页面传来的分页查询参数
BaseQuery.java
public class BaseQuery {
private Integer page = 1;
private Integer limit = 10;
private String q;
public Integer getPage() {
return page;
}
public void setPage(Integer page) {
this.page = page;
}
public Integer getLimit() {
return limit;
}
public void setLimit(Integer limit) {
this.limit = limit;
}
public String getQ() {
return q;
}
public void setQ(String q) {
this.q = q;
}
}
PartsQuery.java
用于封装前台传来的高级查询参数
继承BaseQuery.java,新添高级查询功能。
public class PartsQuery extends BaseQuery {
private Date startTime;
private Date endTime;
private String name;
public Date getStartTime() {
return startTime;
}
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
public void setStartTime(Date startTime) {
this.startTime = startTime;
}
public Date getEndTime() {
return endTime;
}
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
public void setEndTime(Date endTime) {
this.endTime = endTime;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
3.7 util
封装由后台传向前台的json状态以及信息数据
JsonResult.java
public class JsonResult {
private Boolean success =true;
private String msg;
public JsonResult() {
}
public JsonResult(Boolean success, String msg) {
this.success = success;
this.msg = msg;
}
public Boolean getSuccess() {
return success;
}
public void setSuccess(Boolean success) {
this.success = success;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
}
PageUi.java
封装后台传往前台的表格中的数据,LayUi的table表格需要以一种特殊的格式接收数据,否则会报错:数据接口异常!
public class PageUi<T> {
private Integer code = 0;
private String msg;
private Long count;
private List<T> data = new ArrayList<>();
public Integer getCode() {
return code;
}
public void setCode(Integer code) {
this.code = code;
}
public String getMsg() {
return msg;
}
public void setMsg(String msg) {
this.msg = msg;
}
public Long getCount() {
return count;
}
public void setCount(Long count) {
this.count = count;
}
public List<T> getData() {
return data;
}
public void setData(List<T> data) {
this.data = data;
}
}
4.心得
本猿之前偶尔写写前端,所使用的是EasyUi框架,只要眼不瞎都能看出来,相较于EasyUi,LayUi做出来的页面挺好看的!而且易于上手,js语法虽有不同,但也大同小异!参照着官方文档,基本上都能理解,实在弄不明白的,可以多多参考一些大佬的博客;总之,LayUi,你值得拥有!