android项目案例之超级课程表
Posted 程序员小毛驴
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了android项目案例之超级课程表相关的知识,希望对你有一定的参考价值。
转载请注明出处:http://blog.csdn.net/liulongling/article/details/50127819
demo和超级课程表界面和功能有些不一样 如:
1.效果图左侧时间轴,超级课程表是每节课,我做的是每节课对应的时间
2.每周课程切换,超级课程表是点击顶部的第几周显示每周课程,我做的是监听手指手势切换上下周
实现思路:
1.UI上使用ScrollView来实现一天课程的滚动,因为需要实现通过手势来切换每周的课程,所以这里重写了ScrollViewExtend.否则手势监听事件会与ScrollView发生冲突
2.布局上的划分,左边第一列是时间轴,一共24小时。除第一列,后面几列是显示课程内容.知道了每周是7天,每天24小时,屏幕宽高,求得每小时课程宽高,再深入计算每分钟的高度high。最后通过课程的时间 日期和high计算出课程显示的坐标.知道了坐标 剩下就是堆代码了...
代码运行需要配置:
1.注解配置地址:http://jingyan.baidu.com/article/5552ef47c25fea518ffbc9e9.html
2.注解包下载和使用地址:http://jakewharton.github.io/butterknife/
思路一代码:
1>重写ScrollView
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@drawable/bg_main"
android:orientation="vertical" >
<include
android:id="@+id/weekday"
layout="@layout/course_week_date" />
<com.app.lll.view.ScrollViewExtend
android:id="@+id/scroll_body"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/weekday"
android:scrollbars="none" >
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<LinearLayout
android:id="@+id/ll_weekView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >
<LinearLayout
android:id="@+id/ll_time"
android:layout_width="50dp"
android:layout_height="wrap_content"
android:orientation="vertical" >
</LinearLayout>
<TextView
android:layout_width="1.5dp"
android:layout_height="match_parent"
android:background="#d8d8d8" />
<RelativeLayout
android:id="@+id/rl_courses"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</RelativeLayout>
</LinearLayout>
<RelativeLayout
android:id="@+id/rl_user_courses"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</RelativeLayout>
</RelativeLayout>
</com.app.lll.view.ScrollViewExtend>
</RelativeLayout>
package com.app.lll.view;
import android.content.Context;
import android.util.AttributeSet;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.widget.ScrollView;
/**
* 重写ScrollView 可以与手势事件共同使用
* @author liulongling
*
*/
public class ScrollViewExtend extends ScrollView
GestureDetector gestureDetector;
public ScrollViewExtend(Context context)
super(context);
public ScrollViewExtend(Context context, AttributeSet attrs)
super(context, attrs);
public ScrollViewExtend(Context context, AttributeSet attrs, int defStyle)
super(context, attrs, defStyle);
public void setGestureDetector(GestureDetector gestureDetector)
this.gestureDetector = gestureDetector;
public boolean onTouchEvent(MotionEvent ev)
super.onTouchEvent(ev);
return gestureDetector.onTouchEvent(ev);
public boolean dispatchTouchEvent(MotionEvent ev)
gestureDetector.onTouchEvent(ev);
super.dispatchTouchEvent(ev);
return true;
2>计算课程格子高度宽度
//第一个格子宽度
firstGridWidth =DensityUtils.dp2px(mContext, 50+2);
//格子平均宽度
aveWidth = (ScreenUtils.getScreenWidth(mContext)-firstGridWidth) / 7;
//格子平均高度
gridHeight =ScreenUtils.getScreenHeight(mContext) / 12;
3>左侧时间轴
<pre name="code" class="java">public void initViewParams()
if(mHourParams == null)
mHourParams = new RelativeLayout.LayoutParams(firstGridWidth,gridHeight);
if(mHourTextParams == null)
mHourTextParams = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT,RelativeLayout.LayoutParams.WRAP_CONTENT);
mHourTextParams.addRule(RelativeLayout.CENTER_HORIZONTAL);
mHourTextParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);
if(mHourLineParams == null)
mHourLineParams = new RelativeLayout.LayoutParams(DensityUtils.dp2px(mContext, 10),DensityUtils.dp2px(mContext, (float)1.5));
mHourLineParams.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
mHourLineParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);
/**
* 初始化24小时*8view
*/
public void initTwentyFourHourViews()
initViewParams();
for(int i=1;i<HOURS.length;i++)
for(int j=1;j<=8;j++)
if(j==1)
addTimeView(i-1);//时间轴
else
addDotView(i,j-1);//小黑点
//可以点击的TextView 用来添加课程
TextView tx = new TextView(mContext);
tx.setId((i - 1) * 7 + j);
//相对布局参数
RelativeLayout.LayoutParams rp = new RelativeLayout.LayoutParams(aveWidth,gridHeight);
//设置他们的相对位置
if(j == 2)
if(i > 1)
rp.addRule(RelativeLayout.BELOW, (i - 2) * 7+j);
else
//字体样式
tx.setTextAppearance(mContext, R.style.courseTableText);
rp.addRule(RelativeLayout.RIGHT_OF, (i - 1) * 7 + j - 1);
rp.addRule(RelativeLayout.ALIGN_TOP, (i - 1) * 7 + j - 1);
tx.setText("");
tx.setLayoutParams(rp);
tx.setOnClickListener(new OnClickListener()
@Override
public void onClick(View v)
int hour = (v.getId()-2)/7;
int weekofday=(v.getId() -1)%7;
if(weekofday == 0)
weekofday = 7;
if(hour < 0)
hour = 0;
//莫忘了计算点击的时间时 加上开始时间
hour += HOURS[0];
if(curClickView!=null)
curClickView.setBackground(null);
if(curClickView.getId() == v.getId())
curClickView = null;
//跳转到添加课程界面
return;
curClickView = v;
curClickView.setBackground(getResources().getDrawable(R.drawable.bg_course_add));
curClickView.setAlpha((float)0.5);
);
courseLayout.addView(tx);
4>左侧时间轴格子
<pre name="code" class="java"> /**
* 时间轴
* @param hour 几点
*/
public void addTimeView(int hour)
RelativeLayout layout = new RelativeLayout(mContext);
layout.setLayoutParams(mHourParams);
//第一个格子里显示2个时间 24点 1点
if(hour == 0)
RelativeLayout.LayoutParams layoutParams= new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT,RelativeLayout.LayoutParams.WRAP_CONTENT);
layoutParams.addRule(RelativeLayout.CENTER_HORIZONTAL);
layoutParams.addRule(RelativeLayout.ALIGN_PARENT_TOP);
TextView textView = new TextView(mContext);
textView.setText("0"+HOURS[0]+":00");
textView.setLayoutParams(layoutParams);
textView.setTextAppearance(mContext, R.style.weekViewTimeText);
layout.addView(textView);
//第一个时间显示在格子顶部 其它时间显示在底部
hour = HOURS[hour+1];
TextView textView = new TextView(mContext);
textView.setLayoutParams(mHourTextParams);
textView.setTextAppearance(mContext, R.style.weekViewTimeText);
StringBuilder builder = new StringBuilder();
builder.append(hour < 10?("0"+hour):hour);
builder.append(":00");
//22点不显示
textView.setText(builder.toString());
if(hour == 22)
textView.setVisibility(View.INVISIBLE);
layout.addView(textView);
//22点横线不显示
if(hour != 22)
TextView lineView = new TextView(mContext);
lineView.setLayoutParams(mHourLineParams);
lineView.setBackgroundColor(getResources().getColor(R.color.week_view_black));
layout.addView(lineView);
timeLayout.addView(layout);
思路二代码
自定义view显示课程位置
<pre name="code" class="java">/**
* 根据课程时间绘制课程显示的位置
* @param name 课程名称
* @param sHour 课程开始时间
* @param sHour 课程开始分钟
* @param min 这节课有多少分钟
* @param weekday 周几
*/
public void addCourseView(Lesson bean)
int[] sParams = DateUtil.getTime(bean.getsTime());
int[] eParams = DateUtil.getTime(bean.geteTime());
if(sParams == null || eParams == null)
return;
//开始时间 分钟 总时间
int sHour,sMin,eHour,eMin,min;
sHour = sParams[0];
sMin = sParams[1];
eHour= eParams[0];
eMin = eParams[1];
if(eHour > sHour || eMin > sMin)
min = (eHour - sHour)*60+(eMin - sMin);
if(min < 40)
min = 40;
//课程高度
float minHeight = (float)gridHeight/(float)60;
int cHeight = (int)(((float)gridHeight/(float)60)*min);
int weekday = DateUtil.getWeekOfDate(bean.getLessonDate());
if(weekday == 0)
weekday = 7;
//1.添一个相对布局 来存储图片和文字
RelativeLayout layout = new RelativeLayout(mContext);
layout.setTag(String.valueOf(bean.getId()));
RelativeLayout.LayoutParams rlp = new RelativeLayout.LayoutParams(aveWidth,cHeight);
//Calculate the location of the course Since the beginning of the course is from 7 points
rlp.topMargin = (sHour-7)*gridHeight+(int)(minHeight*sMin);
rlp.leftMargin = firstGridWidth+(weekday-1)*aveWidth;
layout.setLayoutParams(rlp);
//设置背景框
layout.setBackgroundResource(R.drawable.course_bg);
//设置背景颜色
GradientDrawable drawable =(GradientDrawable) layout.getBackground();
drawable.setColor(ColorUtils.getFillColor(1));
//设置描边颜色
drawable.setStroke(DensityUtils.dp2px(mContext, 2),ColorUtils.getStrokeColor(2));
//bean.status == ClientCode.YS?mContext.getResources().getColor(background[0]):mContext.getResources().getColor(background[DateUtil.getWeekDay()])
//设置不透明度
layout.getBackground().setAlpha(222);
//2.添加课程
TextView courseInfo = new TextView(mContext);
StringBuilder builder = new StringBuilder();
builder.append(bean.getsTime());
builder.append("\\n");
builder.append(" ");
builder.append(bean.getName());
courseInfo.setText(builder.toString());
// 偏移由这节课是星期几决定
//rlp.addRule(RelativeLayout.RIGHT_OF, 1);
// 字体居中
//courseInfo.setGravity(Gravity.CENTER);
RelativeLayout.LayoutParams layoutParams= new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT,RelativeLayout.LayoutParams.WRAP_CONTENT);
courseInfo.setTextSize(12);
courseInfo.setLayoutParams(layoutParams);
courseInfo.setTextColor(Color.WHITE);
layout.setOnClickListener(new OnClickListener()
@Override
public void onClick(View v)
//课程信息界面
);
layout.addView(courseInfo);
//课程以上显示已经图标
if(bean.getStatus() == 1)
layout.addView(addClassOkIcon());
mUserCourseLayout.addView(layout);
源码下载地址(需CSDN积分):http://download.csdn.net/detail/liulongling/9422256
源码github地址:https://github.com/liulongling/CourseTable.git
以上是关于android项目案例之超级课程表的主要内容,如果未能解决你的问题,请参考以下文章
Linux课程笔记 Linux系统集权分治管理sudoer配置案例