如何快速开发一个课程表App?

如题所述

课程表是如今学生群体最常用的功能之一,那么如何快速实现课程表功能呢?

首先展示项目效果:

接下来详细讲解课程表功能的实现。

功能实现的思路:本项目基于AVM多端框架编写,因此需要想办法去构造特定数据、然后再改变数据,本项目核心业务就是课程数据的处理,难点在于课表的添加。

项目主要针对大学课表进行设计,课程很多地方存在不确定性,如课程周次数可能连续也可能不连续、上课时间可能1-2节也可能一整天、上课教室也可能不一样,因此课程的数据结构如下图。

后端需要提供当前周、当前周课程数据、添加课程等接口,当然课程数据查询是比较复杂的,这里不展开讨论。前端主要是将课表信息显示在指定位置,数据比较简单。

1、课程列表页面

(1)当前周课程原始数据结构

这个数据需要再重组,因为需要将课程摆放到指定位置,必须知道与顶部距离以及自身高度。可以通过上课时间jie这个参数获取height,top。

letdata=[{'name':'大数据可视化技术','room':'机房C414','weekday':'3','bg':'2','jie':'3-4','top':'140px','height':'140px'}]横向分为8份,每份宽度12.5%,高度70px,默认可以显示13节课。课程背景默认有7种样式,星期对应的是left参数也有7种样式,上课节次对应top参数有12种样式。具体css样式如下:

.bg-1{background:linear-gradient(#facea8,#fe8979)}.bg-2{background:linear-gradient(#dfc3fe,#90c5fb)}.bg-3{background:linear-gradient(#9deef5,#68e1b5)}.bg-4{background:linear-gradient(#eeba93,#dd65c7)}.bg-5{background:linear-gradient(#e6f6c9,#68e1b5)}.bg-6{background:linear-gradient(#dfc3fe,#dd65c7)}.bg-7{background:linear-gradient(#c8e65f,#7abafb)}.week-1{left:12.5%;}.week-2{left:25%;}.week-3{left:37.5%;}.week-4{left:50%;}.week-5{left:62.5%;}.week-6{left:75%;}.week-0{left:87.5%;}每一门课程都是用绝对定位,宽度相同,根据上课时间决定高度、位置,代码表示如下:

<viewclass="course_list"><viewv-for="(rs,key)incourse_data":key="key":class="'courseweek-'+rs.weekday+'bg-'+rs.bg":style="'height:'+rs.height+';top:'+rs.top"><textclass="course-name">{{rs.name}}</text><textclass="course-room">{{rs.room}}</text></view></view>(2)当前周星期数据结构

获取当前周的时间代码如下:

this.setDate(newDate());setDate(date){letarr=[];letweek=date.getDay()-1;date=this.addDate(date,week*-1);this.currentFirstDate=newDate(date);for(vari=0;i<7;i++){arr[i]=this.formatDate(i==0?date:this.addDate(date,1))}this.week_data=arrthis.currentWeek()},addDate(date,n){date.setDate(date.getDate()+n);returndate;},formatDate(date){letyear=date.getFullYear();letmonth=(date.getMonth()+1);letday=date.getDate();letweek=['周日','周一','周二','周三','周四','周五','周六'][date.getDay()];this.currentMonth=month;if(month<10){month='0'+month;}if(day<10){day='0'+day;}return{"week":week,"date":month+'/'+day,"active":false};},//当前星期currentWeek(){letdate=newDate();letweekday=date.getDay();if(weekday==1){this.week_data[0].active=true}elseif(weekday==2){this.week_data[1].active=true}elseif(weekday==3){this.week_data[2].active=true}elseif(weekday==4){this.week_data[3].active=true}elseif(weekday==5){this.week_data[4].active=true}elseif(weekday==6){this.week_data[5].active=true}elseif(weekday==0){this.week_data[6].active=true}}上一周以及下一周相应代码:

last(){if(this.week>1){this.week=this.week-1this.setDate(this.addDate(this.currentFirstDate,-7));}},next(){if(this.week<20){this.week=this.week+1this.setDate(this.addDate(this.currentFirstDate,7));}},2、课程添加页面

本项目主要针对大学课程进行设计,由于上课时间地点可能不规律,因此需要考虑周次、节次、星期、上课地点几个因素。为了方便用户快速添加课程,同一门课程可支持添加多个上课时间。页面业务逻辑只有周次选择、时间选择两个地方有点复杂因此将其拆分为两个组件<class-week></class-week><class-time></class-time>。

课程的主要字段如下:

name:'大学计算机',//课程名称room:'机房C411',//上课教室teacher:'李国海',//任课教师weekday:'0',//星期weeks:'1-9,11-20',//上课周数jie:'5-9',//上课节次bg:'1',//课程颜色,系统提供7种颜色大学的课程上课时间可能不规律,上课周数也不一定是20周,周数大致分为单双周以及其他,周数的格式如下:

不规律的周次格式:1-9,11,13,15-201-20周单周的格式:1,3,5,7,9,11,13,15,17,191-20周双周的格式:2,4,6,8,10,12,14,16,18,201-20周的格式:1-20但是这种数据格式对后端数据查询很不友好。

页面初始数据,默认1-24周全部选中。

(1)单周choose(1),双周choose(2),全选choose(0),具体业务处理源代码如下:

choose(n){for(letiinthis.weeks){this.weeks[i].on=false}if(n==1){if(this.choose==1){this.choose=3}else{this.choose=1for(leti=0;i<this.weeks.length;i++){if(this.weeks[i].week%2!=0){this.weeks[i].on=true}}}}elseif(n==2){if(this.choose==2){this.choose=3}else{this.choose=2for(leti=0;i<this.weeks.length;i++){if(this.weeks[i].week%2==0){this.weeks[i].on=true}}}}elseif(n==0){if(this.choose==0){this.choose=3}else{this.choose=0for(letiinthis.weeks){this.weeks[i].on=true}}}}(2)选择某一周的函数set_week(i)源代码如下:

set_week(i){if(this.weeks[i].on==true){this.weeks[i].on=false}else{this.weeks[i].on=true}}(3)确定按钮get_weeks()源代码如下:

get_weeks(){this.mask=false//影藏组件letarr=[];for(leti=0;i<this.weeks.length;i++){leton=this.weeks[i].on;if(on==true){arr.push(this.weeks[i].week);}}letresult=[];lettmp;while(tmp=arr.shift()){if(result.length==0){result.push([tmp]);continue;}lete=result[result.length-1];if(tmp==e[e.length-1]+1){e.push(tmp);}else{result.push([tmp]);}}for(leti=0;i<result.length;i++){letres=result[i];if(res.length>1){result[i]=res[0]+'-'+res[res.length-1];}else{result[i]=res[0]+''}}for(leti=0;i<result.length;i++){if(result[i].indexOf("-")!=-1){result[i]=result[i]}}this.fire('GetWeek',{weeks:result.join(',')});//格式为1-9,11,13,15-20}上课时间组件<class-time></class-time>里面包含星期、上课节次数(注意上课节次数必须是连续的,否则需要单独添加另一个上课时间),主要难点在于判断上课节次数是否连续。

页面初始数据,默认最大上课节次13节。

weekdays:[{name:'星期一',on:false},{name:'星期二',on:false},{name:'星期三',on:false},{name:'星期四',on:false},{name:'星期五',on:false},{name:'星期六',on:false},{name:'星期日',on:false}],times:base.class_time(),num_arr:[],mask:false,jie:'',weekday:0class_time(){letdata=[{'jie':'1节','time':'08:30-09:15'},{'jie':'2节','time':'09:25-10:10'},{'jie':'3节','time':'10:25-11:10'},{'jie':'4节','time':'11:20-12:05'},{'jie':'5节','time':'14:00-14:45'},{'jie':'6节','time':'14:55-15:40'},{'jie':'7节','time':'15:55-16:40'},{'jie':'8节','time':'16:50-17:35'},{'jie':'9节','time':'17:45-18:30'},{'jie':'10节','time':'18:30-19:00'},{'jie':'11节','time':'19:00-19:45'},{'jie':'12节','time':'19:50-20:35'},{'jie':'13节','time':'20:45-21:30'}]returndata;}选择上课节次数(如5-9需要判断单击后选中的数据是否为连续的数字)函数set_time(index)源代码如下:

set_time(index){letjie=(index+1);//判断是否已添加if(this.isInArray(this.num_arr,jie)){this.delArrItem(this.num_arr,jie);this.num_arr.sort(function(x,y){returnx-y;});//console.log('删除'+jie)if(this.isContinuityNum(this.num_arr)){this.times[index].td1=false}else{//console.log('删除后不连续')this.times[index].td1=truethis.num_arr.push(jie);this.num_arr.sort(function(x,y){returnx-y;});api.toast({msg:'上课时间必须连续'});}}else{this.num_arr.push(jie);this.num_arr.sort(function(x,y){returnx-y;});if(this.isContinuityNum(this.num_arr)){this.times[index].td1=true}else{//console.log('增加后不连续')this.delArrItem(this.num_arr,jie);this.num_arr.sort(function(x,y){returnx-y;});this.times[index].td1=falseapi.toast({msg:'上课时间必须连续'});}}this.jie=this.num_arr[0]+'-'+this.num_arr[(this.num_arr.length-1)];//格式1-2}//删除数组元素delArrItem(arr,item){for(vari=0;i<arr.length;i++){if(arr[i]===item){if(arr[i+1]===item){arr.splice(i,1);i--;continue;}arr.splice(i,1);}}returnarr;},//判断是否是连续的数字isContinuityNum(array){if(!array){//数组为nullreturnfalse;}if(array.length==0){//数组为[]returntrue;}varlen=array.length;varn0=array[0];varsortDirection=1;//默认升序if(array[0]>array[len-1]){//降序sortDirection=-1;}if((n0*1+(len-1)*sortDirection)!==array[len-1]){//筛除['3',4,5,6,7,8]returnfalse;}varisContinuation=true;for(vari=0;i<len;i++){if(array[i]!==(i+n0*sortDirection)){isContinuation=false;break;}}returnisContinuation;},//判断元素是否在数组里面isInArray(arr,value){for(vari=0;i<arr.length;i++){if(value==arr[i]){returntrue;}}returnfalse;}最终前端需要提交给后端的数据格式如下:

yearId:'200',//学年id,这里是指那一学期的课程name:'大学计算机',//课程名称teacher:'李国海',//任课教师bg:'1',//课程颜色,系统提供7种颜色class_time:[{weeks:'1-20',room:'一教A307',weekday:'1',jie:'1-2'},{weeks:'1-20',room:'机房C405',weekday:'3',jie:'3-4'}]以上便是本次开发学堂全部内容,有用的话,请大家点赞、分享、评论~

温馨提示:答案为网友推荐,仅供参考