1.依赖
/《Banner依赖》 compile 'com.youth.banner:banner:1.4.9' //《Fresco图片框架依赖》 compile 'com.facebook.fresco:fresco:0.14.1' //《Retrofit网络请求依赖》 implementation 'com.squareup.retrofit2:retrofit:2.4.0' compile 'com.squareup.retrofit2:converter-gson:2.4.0' //《Recyclerview的依赖》 compile 'com.android.support:recyclerview-v7:26.1.0' //《Butterknife依赖(黄油刀)》 compile 'com.jakewharton:butterknife:8.8.1' annotationProcessor 'com.jakewharton:butterknife-compiler:8.8.1' //《RXjava2的适配器》 compile 'com.squareup.retrofit2:adapter-rxjava2:2.4.0' //《Rxjava2》 compile 'io.reactivex.rxjava2:rxjava:2.1.7' compile 'io.reactivex.rxjava2:rxandroid:2.0.1' //《EventBus的依赖》 compile 'org.greenrobot:eventbus:3.1.1' //SmartRefreshLayout的依赖 compile 'com.scwang.smartrefresh:SmartRefreshLayout:1.0.4' compile 'com.scwang.smartrefresh:SmartRefreshHeader:1.0.4'//没有使用特殊Header,可以不加这行
2.权限
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.dell.jingdong201804"> <!-- 必须的权限 --> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /> <uses-permission android:name="android.permission.READ_PHONE_STATE" /> <uses-permission android:name="android.permission.INTERNET" /> <!-- 推荐的权限 --> <!-- 添加如下权限,以便使用更多的第三方SDK和更精准的统计数据 --> <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <!-- AndroidManifest清单配置文件方式初始化appkey和channel --> <meta-data android:name="UMENG_APPKEY" android:value="5ac599ccf43e4822c00003ba" /> <meta-data android:name="UMENG_CHANNEL" android:value="Channel ID" /> <application android:name=".app.App" android:allowBackup="true" android:icon="@drawable/jd_buy_icon" android:label="京东" android:roundIcon="@drawable/jd_buy_icon" android:supportsRtl="true" android:theme="@style/AppTheme"> <activity android:name=".MainActivity"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <activity android:name=".Main2Activity" /> <activity android:name=".Main3Activity" /> <activity android:name=".view.WoDe.WoDe_LoginActivity" /> <!-- QQ --> <activity android:name="com.tencent.tauth.AuthActivity" android:launchMode="singleTask" android:noHistory="true"> <intent-filter> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="tencent100424468" /> </intent-filter> </activity> <activity android:name="com.tencent.connect.common.AssistActivity" android:configChanges="orientation|keyboardHidden|screenSize" android:theme="@android:style/Theme.Translucent.NoTitleBar" /> <activity android:name=".view.WoDe.WoDe_ZhuCeActivity" /> <activity android:name=".view.ShouYe.ShouYeXQActivity" /> <activity android:name=".view.FenLei.FenLeiLBActivity"></activity> </application> </manifest>
3.切换Fragment的布局
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context="com.example.dell.jingdong201804.Main3Activity"> <RelativeLayout android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="9.3" android:id="@+id/relative"> </RelativeLayout> <RadioGroup android:id="@+id/radio" android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="0.7" android:orientation="horizontal"> <RadioButton android:id="@+id/btn_01" android:layout_width="0dp" android:layout_weight="1" android:checked="true" android:button="@null" android:background="@drawable/select_btn_01" android:layout_height="wrap_content" /> <RadioButton android:id="@+id/btn_02" android:layout_width="0dp" android:layout_weight="1" android:button="@null" android:background="@drawable/select_btn_02" android:layout_height="wrap_content" /> <RadioButton android:id="@+id/btn_03" android:layout_width="0dp" android:layout_weight="1" android:button="@null" android:background="@drawable/select_btn_03" android:layout_height="wrap_content" /> <RadioButton android:id="@+id/btn_04" android:layout_width="0dp" android:layout_weight="1" android:button="@null" android:background="@drawable/select_btn_04" android:layout_height="wrap_content" /> <RadioButton android:id="@+id/btn_05" android:layout_width="0dp" android:layout_weight="1" android:button="@null" android:background="@drawable/select_btn_05" android:layout_height="wrap_content" /> </RadioGroup> </LinearLayout>
4.实现切换的主页
package com.example.dell.jingdong201804; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.widget.RadioButton; import android.widget.RadioGroup; import android.widget.RelativeLayout; import android.widget.Toast; import com.example.dell.jingdong201804.view.ShouYe.Fragment01; import com.example.dell.jingdong201804.view.FenLei.Fragment02; import com.example.dell.jingdong201804.fragment.Fragment03; import com.example.dell.jingdong201804.view.Shopping.Fragment04; import com.example.dell.jingdong201804.fragment.Fragment05; import butterknife.BindView; import butterknife.ButterKnife; public class Main3Activity extends AppCompatActivity { @BindView(R.id.relative) RelativeLayout my_relative; @BindView(R.id.radio) RadioGroup my_radio; @BindView(R.id.btn_01) RadioButton btn_01; //初始化碎片类 final Fragment01 fragment01 = new Fragment01(); final Fragment02 fragment02 = new Fragment02(); final Fragment03 fragment03 = new Fragment03(); final Fragment04 fragment04 = new Fragment04(); final Fragment05 fragment05 = new Fragment05(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main3); ButterKnife.bind(this); Toast.makeText(this, "欢迎进入京东App", Toast.LENGTH_SHORT).show(); //将占位布局换成碎片 getSupportFragmentManager().beginTransaction() .add(R.id.relative,fragment01) .add(R.id.relative,fragment02) .add(R.id.relative,fragment03) .add(R.id.relative,fragment04) .add(R.id.relative,fragment05) .commit(); //设置进入页面就显示首页 if (btn_01.isChecked()){ getSupportFragmentManager().beginTransaction() .show(fragment01) .hide(fragment02) .hide(fragment03) .hide(fragment04) .hide(fragment05) .commit(); } //给RadioGroup设置改变的监听事件 (先加载所有碎片,使用显示与隐藏的方法交替显示) my_radio.setOnCheckedChangeListener(new RadioGroup.OnCheckedChangeListener() { @Override public void onCheckedChanged(RadioGroup radioGroup, int i) { switch (i) { case R.id.btn_01: getSupportFragmentManager().beginTransaction() .show(fragment01) .hide(fragment02) .hide(fragment03) .hide(fragment04) .hide(fragment05) .commit(); break; case R.id.btn_02: getSupportFragmentManager().beginTransaction() .show(fragment02) .hide(fragment01) .hide(fragment03) .hide(fragment04) .hide(fragment05) .commit(); break; case R.id.btn_03: getSupportFragmentManager().beginTransaction() .show(fragment03) .hide(fragment01) .hide(fragment02) .hide(fragment04) .hide(fragment05) .commit(); break; case R.id.btn_04: getSupportFragmentManager().beginTransaction() .show(fragment04) .hide(fragment01) .hide(fragment02) .hide(fragment03) .hide(fragment05) .commit(); break; case R.id.btn_05: getSupportFragmentManager().beginTransaction() .show(fragment05) .hide(fragment01) .hide(fragment02) .hide(fragment03) .hide(fragment04) .commit(); break; default: break; } } }); } }
5.Api
package com.example.dell.jingdong201804.api; import com.example.dell.jingdong201804.model.FenLei.FenLeiDataBean.FenLeiDataBean_left; import com.example.dell.jingdong201804.model.FenLei.FenLeiDataBean.FenLeiDataBean_ringht; import com.example.dell.jingdong201804.model.FenLei.FenLeiDataBean.FenLeiLBDataBean; import com.example.dell.jingdong201804.model.Shopping.bean.ShoppingDataBean; import com.example.dell.jingdong201804.model.Shopping.bean.ShoppingDataBean2; import com.example.dell.jingdong201804.model.Shopping.bean.ShoppingDataBean3; import com.example.dell.jingdong201804.model.ShouYe.ShouYeDataBean.ShouYeDataBean; import com.example.dell.jingdong201804.model.ShouYe.ShouYeDataBean.ShouYeXQDataBean; import com.example.dell.jingdong201804.model.WoDe.UserBean; import java.util.List; import io.reactivex.Flowable; import io.reactivex.Observable; import retrofit2.http.GET; import retrofit2.http.Query; /** * Created by dell on 2018/4/23. */ public interface ApiService { //公共参数source=android //注册 @GET("user/reg") Observable<UserBean> getzc(@Query("mobile")String mobile, @Query("password")String password); //登录 @GET("user/login") Observable<UserBean> getlogin(@Query("mobile")String mobile, @Query("password")String password); //首页轮播图 秒杀 为你推荐;我的页面为你推荐数据 @GET("ad/getAd") Flowable<ShouYeDataBean> getShouYe(); //首页为你推荐的商品详情 @GET("product/getProductDetail?source=android") Flowable<ShouYeXQDataBean> getShouYeXQDataBean(@Query("pid")String pid); //分类 @GET("product/getCatagory") Flowable<FenLeiDataBean_left> getLeft(); @GET("product/getProductCatagory") Flowable<FenLeiDataBean_ringht> getRight(@Query("cid")String cid); //分类右侧列表 @GET("product/getProducts") Flowable<FenLeiLBDataBean> getFenLeiLB(@Query("pscid") String pscid); //添加购物车 @GET("product/addCart?source=android") Flowable<ShoppingDataBean<List<ShoppingDataBean2<List<ShoppingDataBean3>>>>> getShoppingAdd(@Query("uid")String uid,@Query("pid")String pid); //查询购物车数据 @GET("product/getCarts?source=android") Flowable<ShoppingDataBean<List<ShoppingDataBean2<List<ShoppingDataBean3>>>>> getShopping(@Query("uid") String uid); }
6.App
package com.example.dell.jingdong201804.app; import android.app.Application; import com.facebook.drawee.backends.pipeline.Fresco; import com.umeng.commonsdk.UMConfigure; import com.umeng.socialize.PlatformConfig; /** * Created by dell on 2018/4/21. */ public class App extends Application{ //三方的key 友盟 { PlatformConfig.setWeixin("wx967daebe835fbeac", "5bb696d9ccd75a38c8a0bfe0675559b3"); PlatformConfig.setQQZone("100424468", "c7394704798a158208a74ab60104f0ba"); PlatformConfig.setSinaWeibo("3921700954", "04b48b094faeb16683c32669824ebdad", "http://sns.whalecloud.com"); } @Override public void onCreate() { super.onCreate(); //初始化Fresco Fresco.initialize(this); //初始化友盟 UMConfigure.init(this, "5a12384aa40fa3551f0001d1", "umeng", UMConfigure.DEVICE_TYPE_PHONE, "");//58edcfeb310c93091c000be2 5965ee00734be40b580001a0 } }
7.首页跑马灯
package com.example.dell.jingdong201804.app; import android.content.Context; import android.widget.ImageView; import com.bumptech.glide.Glide; import com.youth.banner.loader.ImageLoader; /** * Created by dell on 2018/4/21. */ public class SyImgApp extends ImageLoader { //用于首页的跑马灯广告栏 @Override public void displayImage(Context context, Object url, ImageView imageView) { Glide.with(context).load(url).into(imageView); } }
8.跑马灯自定义控件
package com.example.dell.jingdong201804.customView; import android.content.Context; import android.content.res.TypedArray; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Rect; import android.util.AttributeSet; import android.util.Log; import android.view.MotionEvent; import android.view.View; import com.example.dell.jingdong201804.R; import com.example.dell.jingdong201804.model.ShouYe.ShouYeDataBean.ADEnity; import com.example.dell.jingdong201804.utils.ShouYe.DensityUtil; import com.example.dell.jingdong201804.utils.ShouYe.SizeUtil; import java.util.List; import java.util.Timer; import java.util.TimerTask; /** * Created by dell on 2018/4/24. */ //首页跑马灯 public class ADTextView extends View{ private int mSpeed; //文字出现或消失的速度 建议1~5 private int mInterval; //文字停留在中间的时长 private int mFrontColor; //前缀颜色 private int mContentColor; //内容的颜色 private int mFrontTextSize; //前缀文字大小 private int mContentTextSize; //内容文字大小 private List<ADEnity> mTexts; //显示文字的数据源 private int mY = 0; //文字的Y坐标 private int mIndex = 0; //当前的数据下标 private Paint mPaintContent; //绘制内容的画笔 private Paint mPaintFront; //绘制前缀的画笔 private boolean isMove = true; //文字是否移动 private String TAG = "ADTextView"; private boolean hasInit = false; private boolean isPaused = false; public interface onClickListener { public void onClick(String mUrl); } private onClickListener onClickListener; public void setOnClickListener(onClickListener onClickListener) { this.onClickListener = onClickListener; } public ADTextView(Context context) { this(context, null); } public ADTextView(Context context, AttributeSet attrs) { super(context, attrs); obtainStyledAttrs(attrs); init(); } //获取资源文件 private void obtainStyledAttrs(AttributeSet attrs) { TypedArray array = getContext().obtainStyledAttributes(attrs, R.styleable.ADTextView); mSpeed = array.getInt(R.styleable.ADTextView_ad_text_view_speed, 1); mInterval = array.getInt(R.styleable.ADTextView_ad_text_view_interval, 2000); mFrontColor = array.getColor(R.styleable.ADTextView_ad_text_front_color, Color.RED); mContentColor = array.getColor(R.styleable.ADTextView_ad_text_content_color, Color.BLACK); mFrontTextSize = (int) array.getDimension(R.styleable.ADTextView_ad_text_front_size, SizeUtil.Sp2Px(getContext(), 15)); mContentTextSize = (int) array.getDimension(R.styleable.ADTextView_ad_text_content_size, SizeUtil.Sp2Px(getContext(), 15)); array.recycle(); } @Override public boolean onTouchEvent(MotionEvent event) { int action = event.getAction(); switch (action) { case MotionEvent.ACTION_DOWN: if (onClickListener != null) { onClickListener.onClick(mTexts.get(mIndex).getmUrl()); } break; } return true; } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); int widthMode = MeasureSpec.getMode(widthMeasureSpec); int widthSize = MeasureSpec.getSize(widthMeasureSpec); int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); setMeasuredDimension(DensityUtil.dip2px(getContext(), 500), DensityUtil.dip2px(getContext(), 40)); } //测量宽度 private int measureHeight(int heightMeasureSpec) { int result = 0; int mode = MeasureSpec.getMode(heightMeasureSpec); int size = MeasureSpec.getSize(heightMeasureSpec); if (mode == MeasureSpec.EXACTLY) { result = size; } else { //高度至少为两倍字高 int mfronTextHeight = (int) (mPaintFront.descent() - mPaintFront.ascent()); //前缀文字字高 int mContentTextHeight = (int) (mPaintContent.descent() - mPaintContent.ascent()); //内容文字字高 result = Math.max(mfronTextHeight, mContentTextHeight) * 2; if (mode == MeasureSpec.AT_MOST) { result = Math.min(result, size); } } return result; } //测量高度 private int measureWidth(int widthMeasureSpec) { int result = 0; int mode = MeasureSpec.getMode(widthMeasureSpec); int size = MeasureSpec.getSize(widthMeasureSpec); if (mode == MeasureSpec.EXACTLY) { result = size; } else { //宽度最小十个字的宽度 String text = "十个字十个字十个字字"; Rect rect = new Rect(); mPaintContent.getTextBounds(text, 0, text.length(), rect); result = rect.right - rect.left; if (mode == MeasureSpec.AT_MOST) { result = Math.min(result, size); } } return result; } //设置数据源 public void setmTexts(List<ADEnity> mTexts) { this.mTexts = mTexts; } //设置广告文字的停顿时间 public void setInterval(int mInterval) { this.mInterval = mInterval; } //设置速度 public void setSpeed(int spedd) { this.mSpeed = spedd; } //设置前缀的文字颜色 public void setFrontColor(int mFrontColor) { mPaintFront.setColor(mFrontColor); } //设置正文内容的颜色 public void setBackColor(int mBackColor) { mPaintContent.setColor(mBackColor); } //初始化默认值 private void init() { mIndex = 0; mPaintFront = new Paint(); mPaintFront.setAntiAlias(true); mPaintFront.setDither(true); mPaintFront.setTextSize(mFrontTextSize); mPaintFront.setColor(mFrontColor); mPaintContent = new Paint(); mPaintContent.setAntiAlias(true); mPaintContent.setDither(true); mPaintContent.setTextSize(mContentTextSize); mPaintContent.setColor(mContentColor); } @Override protected void onDraw(Canvas canvas) { if (mTexts != null) { ADEnity model = mTexts.get(mIndex); String font = model.getmFront(); String back = model.getmBack(); //绘制前缀 Rect indexBound = new Rect(); mPaintFront.getTextBounds(font, 0, font.length(), indexBound); //绘制内容文字 Rect contentBound = new Rect(); mPaintContent.getTextBounds(back, 0, back.length(), contentBound); if (mY == 0 && hasInit == false) { mY = getMeasuredHeight() - indexBound.top; hasInit = true; } //移动到最上面 if (mY <= 0 - indexBound.bottom) { Log.i(TAG, "onDraw: " + getMeasuredHeight()); mY = getMeasuredHeight() - indexBound.top; mIndex++; isPaused = false; } canvas.drawText(back, 0, back.length(), (indexBound.right - indexBound.left) + 20, mY, mPaintContent); canvas.drawText(font, 0, font.length(), 10, mY, mPaintFront); //移动到中间 if (!isPaused && mY <= getMeasuredHeight() / 2 - (indexBound.top + indexBound.bottom) / 2) { isMove = false; isPaused = true; Timer timer = new Timer(); timer.schedule(new TimerTask() { @Override public void run() { postInvalidate(); isMove = true; } }, mInterval); } mY -= mSpeed; //循环使用数据 if (mIndex == mTexts.size()) { mIndex = 0; } //如果是处于移动状态时的,则延迟绘制 //计算公式为一个比例,一个时间间隔移动组件高度,则多少毫秒来移动1像素 if (isMove) { postInvalidateDelayed(2); } } } }
9.DensityUtil
package com.example.dell.jingdong201804.utils.ShouYe; import android.content.Context; /** * Created by dell on 2018/4/24. */ public class DensityUtil { /** * 根据手机的分辨率从 dp 的单位 转成为 px(像素) */ public static int dip2px(Context context, float dpValue) { final float scale = context.getResources().getDisplayMetrics().density; return (int) (dpValue * scale + 0.5f); } /** * 根据手机的分辨率从 px(