NewsApp01
2018-10-03 本文已影响0人
GeekGray
1. 项目包含技术点
1.项目框架搭建
2.SlidingMenu侧滑菜单的使用
3.Fragment的使用
4.ViewPagerIndicator的使用
TabLayout
5.xUtils3的使用->okhttp3
6.Volley的使用
7.消息推送-极光推送
8.图片三级缓存
9.Gson数据解析
10.手动解析数据
11.解决控件中事件冲突
12.自定义下拉刷新
第三方下拉刷新
13.使用SharedSDK分享数据
14.第三方支付-支付宝
15.屏幕适配
16.WebView的使用
17.Java 和Js调用-支持HTML5开发(重点)
18.RecyclerView的使用
19.SwipeRefreshLayout
20.MaterialRefreshLayout实现下拉和上拉刷新
21.photoView的使用
22.购物车
2. 欢迎界面SplashActivity
布局文件activity_splash
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:id="@+id/rl_splahs_root"
android:layout_height="match_parent"
android:background="@drawable/splash_bg_newyear">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerInParent="true"
android:src="@drawable/splash_sheep_newyear" />
</RelativeLayout>
欢迎界面具体代码
/**
* @author: Hashub
* @WeChat: NGSHMVP
* @Date: 2018/9/2 19:46
* @function:欢迎界面
*/
public class SplashActivity extends Activity
{
/**
* 静态常量
*/
public static final String START_MAIN = "start_main";
private RelativeLayout rl_splahs_root;
@Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_splash);
initView();//初始化视图
initAnimation();//动画
}
/**
* //渐变动画,缩放动画,旋转动画
*/
private void initAnimation()
{
//渐变动画
AlphaAnimation alphaAnimation = new AlphaAnimation(0, 1);
//alphaAnimation.setDuration(500);//持续播放时间 //被动画集中的setDuration()屏蔽,无效
alphaAnimation.setFillAfter(true);
//缩放动画,旋转动画
ScaleAnimation scaleAnimation = new ScaleAnimation(0, 1, 0, 1, ScaleAnimation.RELATIVE_TO_SELF, 0.5f, ScaleAnimation.RELATIVE_TO_SELF, 0.5f);
scaleAnimation.setFillAfter(true);
//旋转动画
RotateAnimation rotateAnimation = new RotateAnimation(0, 360, RotateAnimation.RELATIVE_TO_SELF, 0.5f, RotateAnimation.RELATIVE_TO_SELF, 0.5f);
rotateAnimation.setFillAfter(true);
//动画集
AnimationSet animationSet = new AnimationSet(false);
//添加三个动画没有先后顺序,便于同时播放动画
animationSet.addAnimation(rotateAnimation);
animationSet.addAnimation(scaleAnimation);
animationSet.addAnimation(alphaAnimation);
animationSet.setDuration(2000);
//整个布局进行动画播放
rl_splahs_root.startAnimation(animationSet);
animationSet.setAnimationListener(new MyAnimationListener());
}
class MyAnimationListener implements Animation.AnimationListener
{
@Override
public void onAnimationStart(Animation animation)
{
}
/**
* 当动画播放结束的时候回调这个方法
*
* @param animation
*/
@Override
public void onAnimationEnd(Animation animation)
{
toMainOrGuide();
}
/**
* 当动画重复播放的时候回调这个方法
*
* @param animation
*/
@Override
public void onAnimationRepeat(Animation animation)
{
}
}
/**
* 判断是进入主界面还是引导页面
*/
private void toMainOrGuide()
{
//判断是否进入过主页面
boolean isStartMain = CacheUtils.getBoolean(SplashActivity.this, START_MAIN);
Intent intent;
if (isStartMain)
{
//如果进入过主页面,直接进入主页面
//2.跳转到主页面
intent = new Intent(SplashActivity.this, MainActivity.class);
}
else
{
//如果没有进入过主页面,进入引导页面
intent = new Intent(SplashActivity.this,GuideActivity.class);
}
startActivity(intent);
//关闭Splash页面
finish();
}
private void initView()
{
rl_splahs_root = (RelativeLayout) findViewById(R.id.rl_splahs_root);
}
@Override
public boolean onTouchEvent(MotionEvent event)
{
toMainOrGuide();
return super.onTouchEvent(event);
}
}
3. 引导页面GuideActivity
布局文件activity_guide.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.newsapp.activity.GuideActivity">
<android.support.v4.view.ViewPager
android:id="@+id/viewpager"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<Button
android:id="@+id/btn_start_main"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="80dp"
android:background="@drawable/btn_start_main_selector"
android:paddingLeft="20dp"
android:paddingRight="20dp"
android:text="开始体验"
android:visibility="gone"
android:textColor="@drawable/btn_start_main_textcolor_selector"
android:textSize="20sp" />
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="40dp">
<LinearLayout
android:id="@+id/ll_point_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal" />
<ImageView
android:id="@+id/iv_red_point"
android:background="@drawable/point_red"
android:layout_width="10dp"
android:layout_height="10dp" />
</RelativeLayout>
</RelativeLayout>
CacheUtils缓存工具类
/**
* @author: Hashub
* @WeChat: NGSHMVP
* @Date: 2018/9/2 19:46
* @function:缓存软件的一些参数和数据
*/
public class CacheUtils
{
/**
* 得到缓存值
*
* @param context 上下文
* @param key
* @return
*/
public static boolean getBoolean(Context context, String key)
{
SharedPreferences sp = context.getSharedPreferences("newsapp", Context.MODE_PRIVATE);
return sp.getBoolean(key, false);
}
/**
* 保存软件参数
*
* @param context
* @param key
* @param value
*/
public static void putBoolean(Context context, String key, boolean value)
{
SharedPreferences sp = context.getSharedPreferences("newsapp", Context.MODE_PRIVATE);
sp.edit().putBoolean(key, value).commit();
}
}
红点移动的原理
利用距离左边的距离实现红点的移动
params.leftMargin = 动态值
屏幕滑动的距离: 屏幕宽 = 屏幕滑动的百分比
两点间移动的距离:间距 = 屏幕滑动的距离: 屏幕宽 = 屏幕滑动百分比(已知)
两点间移动的距离 = 屏幕滑动百分比 * 间距
两点间滑动距离对应的坐标 = 原来的起始位置 + 两点间移动的距离
params.leftMargin = 两点间滑动距离对应的坐标
间距 = 第1个点距离左边的距离 - 第0个点距离左边的距离
px和dp互相转换工具DensityUtil
/**
* @author: Hashub
* @WeChat: NGSHMVP
* @Date: 2018/9/3 20:00
* @function:单位转换工具 px和dp互相转换工具
*/
public class DensityUtil
{
/**
* 根据手机的分辨率从 dip 的单位 转成为 px(像素)
*/
public static int dip2px(Context context, float dpValue)
{
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (dpValue * scale + 0.5f);
}
/**
* 根据手机的分辨率从 px(像素) 的单位 转成为 dp
*/
public static int px2dip(Context context, float pxValue)
{
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (pxValue / scale + 0.5f);
}
}
GuideActivity
public class GuideActivity extends Activity
{
private static final String TAG = GuideActivity.class.getSimpleName();
private ViewPager viewpager;
private Button btn_start_main;
private LinearLayout ll_point_group;
private ImageView iv_red_point;
private ArrayList<ImageView> imageViews;
/**
* 两点的间距
*/
private int leftmax;
private int widthdpi;
@Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_guide);
initView();
initData();
initListener();
}
/**
* 监听
*/
private void initListener()
{
//根据View的生命周期,当视图执行到onLayout或者onDraw的时候,视图的高和宽,边距都有了
iv_red_point.getViewTreeObserver().addOnGlobalLayoutListener(new MyOnGlobalLayoutListener());
//得到屏幕滑动的百分比
viewpager.addOnPageChangeListener(new MyOnPageChangeListener());
//设置按钮的点击事件
btn_start_main.setOnClickListener(new View.OnClickListener()
{
@Override
public void onClick(View v)
{
//1.保存曾经进入过主页面
CacheUtils.putBoolean(GuideActivity.this, SplashActivity.START_MAIN, true);
//2.跳转到主页面
Intent intent = new Intent(GuideActivity.this, MainActivity.class);
startActivity(intent);
//3.关闭引导页面
finish();
}
});
}
/**
* 准备数据
*/
private void initData()
{
int[] ids = new int[]
{
R.drawable.guide_1,
R.drawable.guide_2,
R.drawable.guide_3
};
widthdpi = DensityUtil.dip2px(this, 10);
Log.e(TAG, widthdpi + "--------------");
imageViews = new ArrayList<>();
for (int i = 0; i < ids.length; i++)
{
ImageView imageView = new ImageView(this);
//设置背景
imageView.setBackgroundResource(ids[i]);
//添加到集合中
imageViews.add(imageView);
//创建点
ImageView point = new ImageView(this);
point.setBackgroundResource(R.drawable.point_normal);
/**
* 单位是像数
* 把单位当成dp转成对应的像数
*/
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(widthdpi, widthdpi);
if (i != 0)
{
//不包括第0个,所有的点距离左边有10个像数
params.leftMargin = widthdpi;
}
point.setLayoutParams(params);
//添加到线性布局里面
ll_point_group.addView(point);
}
//设置ViewPager的适配器
viewpager.setAdapter(new MyPagerAdapter());
}
/**
*
*/
class MyOnPageChangeListener implements ViewPager.OnPageChangeListener
{
/**
* 当页面滑动了了会回调这个方法
*
* @param position 当前滑动页面的位置
* @param positionOffset 页面滑动的百分比
* @param positionOffsetPixels 滑动的像数
*/
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels)
{
//两点间移动的距离 = 屏幕滑动百分比 * 间距
// int leftmargin = (int) (positionOffset * leftmax);
// Log.e(TAG,"position=="+position+",positionOffset=="+positionOffset+",positionOffsetPixels=="+positionOffsetPixels);
//两点间滑动距离对应的坐标 = 原来的起始位置 + 两点间移动的距离
int leftmargin = (int) (position * leftmax + (positionOffset * leftmax));
//params.leftMargin = 两点间滑动距离对应的坐标
RelativeLayout.LayoutParams params = (RelativeLayout.LayoutParams) iv_red_point.getLayoutParams();
params.leftMargin = leftmargin;
iv_red_point.setLayoutParams(params);
}
/**
* 当页面被选中的时候,回调这个方法
*
* @param position 被选中页面的对应的位置
*/
@Override
public void onPageSelected(int position)
{
if (position == imageViews.size() - 1)
{
//最后一个页面
btn_start_main.setVisibility(View.VISIBLE);
}
else
{
//其他页面
btn_start_main.setVisibility(View.GONE);
}
}
/**
* 当ViewPager页面滑动状态发生变化的时候
*
* @param state
*/
@Override
public void onPageScrollStateChanged(int state)
{
}
}
class MyOnGlobalLayoutListener implements ViewTreeObserver.OnGlobalLayoutListener
{
@Override
public void onGlobalLayout()
{
//执行不只一次
iv_red_point.getViewTreeObserver().removeGlobalOnLayoutListener(MyOnGlobalLayoutListener.this);
// 间距 = 第1个点距离左边的距离 - 第0个点距离左边的距离
leftmax = ll_point_group.getChildAt(1).getLeft() - ll_point_group.getChildAt(0).getLeft();
Log.e(TAG, "leftmax==" + leftmax);
}
}
/**
* ViewPager的适配器
*/
class MyPagerAdapter extends PagerAdapter
{
/**
* 返回数据的总个数
*
* @return
*/
@Override
public int getCount()
{
return imageViews.size();
}
/**
* 作用,getView
*
* @param container ViewPager
* @param position 要创业页面的位置
* @return 返回和创建当前页面右关系的值
*/
@Override
public Object instantiateItem(ViewGroup container, int position)
{
ImageView imageView = imageViews.get(position);
//添加到容器中
container.addView(imageView);
// return position;//对应isViewFromObject()方法中的首行注释写法
return imageView;
}
/**
* 判断
*
* @param view 当前创建的视图
* @param object 上面instantiateItem返回的结果值
* @return
*/
@Override
public boolean isViewFromObject(View view, Object object)
{
// return view ==imageViews.get(Integer.parseInt((String) object));
return view == object;
}
/**
* 销毁页面
*
* @param container ViewPager
* @param position 要销毁页面的位置
* @param object 要销毁的页面
*/
@Override
public void destroyItem(ViewGroup container, int position, Object object)
{
container.removeView((View) object);
}
}
/**
* 初始化视图
*/
private void initView()
{
viewpager = (ViewPager) findViewById(R.id.viewpager);
btn_start_main = (Button) findViewById(R.id.btn_start_main);
ll_point_group = (LinearLayout) findViewById(R.id.ll_point_group);
iv_red_point = (ImageView) findViewById(R.id.iv_red_point);
}
}