Okhttp封装 , 运用单利
public class OkhttpsUtil {
private OkHttpClient client;
private static OkhttpsUtil okhttpsUtil;
private Handler handler;
private OkhttpsUtil(){
handler = new Handler(Looper.getMainLooper());
//拦截类
Okhttplan okhttplan = new Okhttplan();
client = new OkHttpClient.Builder()
//添加拦截类
.addInterceptor(okhttplan)
.writeTimeout(5,TimeUnit.SECONDS)
.readTimeout(5,TimeUnit.SECONDS)
.connectTimeout(5,TimeUnit.SECONDS)
.build();
}
public static OkhttpsUtil getIntense(){
if (okhttpsUtil==null){
synchronized (OkhttpsUtil.class){
if (okhttpsUtil==null){
return okhttpsUtil = new OkhttpsUtil();
}
}
}
return okhttpsUtil;
}
public interface OkCallBack{
void cheng(String json);
void bai(Exception e);
}
public void doPost(String path, Map<String,String> map, final OkCallBack lkOkCallBak){
FormBody.Builder builder = new FormBody.Builder();
if(map!=null){
for(String key: map.keySet()){
builder.add(key,map.get(key));
}
}
FormBody formBody = builder.build();
Request request = new Request.Builder()
.post(formBody)
.url(path)
.build();
Call call = client.newCall(request);
call.enqueue(new Callback() {
@Override
public void onFailure(Call call, final IOException e) {
if (lkOkCallBak!=null){
handler.post(new Runnable() {
@Override
public void run() {
lkOkCallBak.bai(e);
}
});
}
}
@Override
public void onResponse(Call call, final Response response) throws IOException {
try{
if (lkOkCallBak!=null&&response.isSuccessful()){
final String json = response.body().string();
handler.post(new Runnable() {
@Override
public void run() {
lkOkCallBak.cheng(json);
}
});
}
}catch (Exception e){
e.printStackTrace();
}
if (lkOkCallBak != null) {
lkOkCallBak.bai(new Exception("网络异常"));
}
}
});
}
}
OkHtpp拦截器
//继承Interceptor
public class Okhttplan implements Interceptor {
@Override
public Response intercept(Interceptor.Chain chain) throws IOException {
//拿到Request对象
Request request = chain.request();
long t1 = System.nanoTime();
System.out.println(" request = " + String.format("Sending request %s on %s%n%s",
request.url(), chain.connection(), request.headers()));
//拿到Response对象
Response response = chain.proceed(request);
long t2 = System.nanoTime();
//得出请求网络,到得到结果,中间消耗了多长时间
System.out.println("response " + String.format("Received response for %s in %.1fms%n%s",
response.request().url(), (t2 - t1) / 1e6d, response.headers()));
return response;
}
}
主页面布局
<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:orientation="vertical"
android:layout_height="match_parent"
tools:context=".MainActivity">
<ExpandableListView
android:id="@+id/ex1"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
></ExpandableListView>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="60dp"
android:layout_alignParentBottom="true"
android:background="#eeeeee"
android:gravity="center_vertical">
<CheckBox
android:id="@+id/cb_cart_all_select"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="全选" />
<TextView
android:id="@+id/tv_cart_total_price"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:paddingLeft="20dp"
android:text="合计:¥0.00" />
<Button
android:id="@+id/btn_cart_pay"
android:layout_width="100dp"
android:layout_height="match_parent"
android:text="去结算(0)" />
</LinearLayout>
</LinearLayout>
商家布局
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="60dp"
android:gravity="center_vertical"
>
<CheckBox
android:id="@+id/seller_cb"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/seller_name_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="20dp" />
</LinearLayout>
商品布局
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="120dp"
android:gravity="center_vertical">
<CheckBox
android:id="@+id/child_cb"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<ImageView
android:id="@+id/product_icon_iv"
android:layout_width="80dp"
android:layout_height="80dp"
android:layout_marginLeft="20dp"
android:scaleType="centerCrop"
android:src="@color/colorPrimary" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical">
<TextView
android:id="@+id/product_title_name_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="2"
android:text="商品标题" />
<TextView
android:id="@+id/product_price_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:text="¥0.0" />
</LinearLayout>
//自定义组件
<bwei.com.fengxiangbin.day18.MyAddSubView
android:id="@+id/add_remove_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginRight="10dp" />
</LinearLayout>
自定义View组件布局
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:padding="2dp"
android:layout_marginLeft="10dp"
android:layout_width="60dp"
android:layout_height="30dp"
android:layout_gravity="center_vertical"
android:background="#99000000"
android:gravity="center_vertical">
<TextView
android:background="#ffffff"
android:layout_weight="1"
android:id="@+id/sub_tv"
android:layout_width="0dp"
android:layout_height="match_parent"
android:gravity="center"
android:text="-"
android:textSize="16sp" />
<TextView
android:text="1"
android:layout_marginLeft="2dp"
android:background="#ffffff"
android:layout_weight="1"
android:id="@+id/product_number_tv"
android:layout_width="0dp"
android:layout_height="match_parent"
android:gravity="center"
/>
<TextView
android:layout_marginLeft="2dp"
android:background="#ffffff"
android:layout_weight="1"
android:id="@+id/add_tv"
android:layout_width="0dp"
android:layout_height="match_parent"
android:gravity="center"
android:text="+"
android:textSize="16sp" />
</LinearLayout>
自定义组件代码实现
public class MyAddSubView extends LinearLayout implements View.OnClickListener {
private int number = 1;
private TextView sub_tv;
private TextView product_number_tv;
private TextView add_tv;
public MyAddSubView(Context context) {
this(context,null);
}
public MyAddSubView(Context context, @Nullable AttributeSet attrs) {
this(context, attrs,0);
}
public MyAddSubView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
View view = inflate(context, R.layout.add_remove_view_layout, this);
sub_tv=view.findViewById(R.id.sub_tv);
product_number_tv=view.findViewById(R.id.product_number_tv);
add_tv=view.findViewById(R.id.add_tv);
sub_tv.setOnClickListener(this);
add_tv.setOnClickListener(this);
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.sub_tv:
if (number > 1) {
--number;
product_number_tv.setText(number + "");
if (onNumberChangeListener != null) {
onNumberChangeListener.onNumberChange(number);
}
} else {
Toast.makeText(getContext(), "不能再少了", Toast.LENGTH_SHORT).show();
}
break;
case R.id.add_tv:
++number;
product_number_tv.setText(number + "");
if (onNumberChangeListener != null) {
onNumberChangeListener.onNumberChange(number);
}
break;
}
}
public int getNumber() {
return number;
}
public void setNumber(int number) {
this.number = number;
product_number_tv.setText(number + "");
}
OnNumberChangeListener onNumberChangeListener;
public void setOnNumberChangeListener(OnNumberChangeListener onNumberChangeListener) {
this.onNumberChangeListener = onNumberChangeListener;
}
interface OnNumberChangeListener {
void onNumberChange(int num);
}
}
自定义主件效果如下
MainCtivity
public class MainActivity extends AppCompatActivity implements View.OnClickListener {
ExpandableListView ex1;
Button bt1;
TextView tx1;
CheckBox cb;
NewsAdaptre adapter;
String url = "http://www.zhaoapi.cn/product/getCarts";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
initData();
}
private void initData() {
HashMap<String,String> map = new HashMap<>();
map.put("uid","71");
OkhttpsUtil.getIntense().doPost(url, map, new OkhttpsUtil.OkCallBack() {
@Override
public void cheng(String json) {
NewsBean newsBean= new Gson().fromJson(json,NewsBean.class);
if ("0".equals(newsBean.getCode())){
List<NewsBean.DataBean> li = newsBean.getData();
adapter = new NewsAdaptre((ArrayList<NewsBean.DataBean>) li);
// //可以先不写,先写出主要效果,这是加减号点击,多选框点击效果
**adapter.setOnCartListChangeListener(new NewsAdaptre.onCartListChangeListener() {
@Override
public void onSellerCheckedChange(int groupPosition) {
boolean cur = adapter.isCurrentSellerAllProductSelected(groupPosition);
adapter.changeCurrentSellerAllProductsStatus(groupPosition,!cur);
adapter.notifyDataSetChanged();
refreshSelectedAndTotalPriceAndTotalNumber();
}
@Override
public void onProductCheckedChange(int groupPosition, int childPosition) {
adapter.changeCurrentProductStatus(groupPosition,childPosition);
adapter.notifyDataSetChanged();
refreshSelectedAndTotalPriceAndTotalNumber();
}
@Override
public void onProducNumberChange(int groupPosition, int childPosition, int number) {
adapter.changeCurrentProductNumber(groupPosition,childPosition,number);
adapter.notifyDataSetChanged();
refreshSelectedAndTotalPriceAndTotalNumber();
}
});**
ex1.setAdapter(adapter);
for(int i=0;i<li.size();i++){
ex1.expandGroup(i);
}
}
}
@Override
public void bai(Exception e) {
}
});
}
private void initView() {
ex1 = findViewById(R.id.ex1);
bt1 = findViewById(R.id.btn_cart_pay);
tx1 = findViewById(R.id.tv_cart_total_price);
cb = findViewById(R.id.cb_cart_all_select);
bt1.setOnClickListener(this);
cb.setOnClickListener(this);
}
@Override
public void onClick(View v) {
switch (v.getId()){
case R.id.btn_cart_pay:
break;
//可以先不写,先写出主要效果,这是全选按钮
case R.id.cb_cart_all_select:
boolean all = adapter.isAllProductsSelected();
adapter.changeAllProductStatus(!all);
adapter.notifyDataSetChanged();
refreshSelectedAndTotalPriceAndTotalNumber();
break;
}
}
//可以先不写,先写出主要效果
private void refreshSelectedAndTotalPriceAndTotalNumber(){
//去判断是否所有的商品都被选中
boolean allProductsSelected = adapter.isAllProductsSelected();
//把这个值设置给checkBox
cb.setChecked(allProductsSelected);
//计算总计
float totalPrice = adapter.calculateTotalPrice();
tx1.setText("总计"+totalPrice);
//计算总数量
int totalNumber = adapter.calculateTotalNumber();
bt1.setText("去结算("+totalNumber+")");
}
}
Adapter类
public class NewsAdaptre extends BaseExpandableListAdapter {
private ArrayList<NewsBean.DataBean> list ;
public NewsAdaptre(ArrayList<NewsBean.DataBean> li) {
list = li;
}
@Override//决定了有多少个组
public int getGroupCount() {
//三元运算符,提供程序运行效率
return list == null ? 0 : list.size();
}
@Override//一个组里面有多少个子条目
public int getChildrenCount(int groupPosition) {
return list.get(groupPosition).getList() == null ? 0 : list.get(groupPosition).getList().size();
}
@Override
public View getGroupView(final int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) {
NewsBean.DataBean dataBean = list.get(groupPosition);
ParentViewHolder parentViewHolder;
if (convertView == null) {
convertView = View.inflate(parent.getContext(), R.layout.item_cart_parent, null);
parentViewHolder = new ParentViewHolder(convertView);
convertView.setTag(parentViewHolder);
} else {
parentViewHolder = (ParentViewHolder) convertView.getTag();
}
parentViewHolder.seller_name_tv.setText(dataBean.getSellerName());
//可以先不写,先写出主要效果
*Boolean currentSellerAllProductSelected = isCurrentSellerAllProductSelected(groupPosition);
parentViewHolder.seller_cb.setChecked(currentSellerAllProductSelected);
parentViewHolder.seller_cb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(mOnCartListChangeListener!=null){
mOnCartListChangeListener.onSellerCheckedChange(groupPosition);
}
}
});*
return convertView;
}
@Override
public View getChildView(final int groupPosition, final int childPosition, boolean isLastChild, View convertView, ViewGroup parent) {
NewsBean.DataBean dataBean = list.get(groupPosition);
ArrayList<NewsBean.DataBean.ListBean> lis = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
NewsBean.DataBean.ListBean listBean = lis.get(childPosition);
ChildViewHolder childViewHolder;
if (convertView!=null){
childViewHolder = (ChildViewHolder) convertView.getTag();
}else{
convertView = View.inflate(parent.getContext(), R.layout.item_cart_child, null);
childViewHolder = new ChildViewHolder(convertView);
convertView.setTag(childViewHolder);
}
//设置商品名字
childViewHolder.product_title_name_tv.setText(listBean.getTitle());
//设置商品单价
childViewHolder.product_price_tv.setText(listBean.getPrice()+"");
//设置复选框是否选中
childViewHolder.child_cb.setChecked(listBean.getSelected() == 1);
//设置组合式自定义控件内部的数量
childViewHolder.add_remove_view.setNumber(listBean.getNum());
ImageLoader.getInstance().displayImage(listBean.getImages(),childViewHolder.product_icon_iv);
//设置自条目多选框点击事件
//可以先不写,先写出主要效果
*childViewHolder.child_cb.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(mOnCartListChangeListener!=null){
mOnCartListChangeListener.onProductCheckedChange(groupPosition,childPosition);
}
}
});
childViewHolder.add_remove_view.setOnNumberChangeListener(new MyAddSubView.OnNumberChangeListener() {
@Override
public void onNumberChange(int num) {
if (mOnCartListChangeListener!=null){
mOnCartListChangeListener.onProducNumberChange(groupPosition,childPosition,num);
}
}
});*
returnconvertView;
}
//判断商家的商品是否被选中(两种情况,一全选,有没选中的)
//可以先不写,先写出主要效果
*public boolean isCurrentSellerAllProductSelected(int groupPosition){
NewsBean.DataBean dataBean = list.get(groupPosition);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for(NewsBean.DataBean.ListBean listBean :li){
if (listBean.getSelected()==0){
return false;
}
}
return true;
}
//全选按钮
public boolean isAllProductsSelected(){
for(int i=0;i<list.size();i++){
NewsBean.DataBean dataBean = list.get(i);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for (int j=0;j<li.size();j++){
if(li.get(j).getSelected()==0){
return false;
}
}
}
return true;
}
//计算商品的总量
public int calculateTotalNumber(){
int totalNumber = 0;
for(int x=0;x<list.size();x++){
NewsBean.DataBean dataBean = list.get(x);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for(int j=0;j<li.size();j++){
if(li.get(j).getSelected()==1){
int num=li.get(j).getNum();
totalNumber+=num;
}
}
}
return totalNumber;
}
//计算商品的价格
public float calculateTotalPrice(){
float totalPrice=0;
for(int x = 0;x<list.size();x++){
NewsBean.DataBean dataBean = list.get(x);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for(int j=0;j<li.size();j++){
if(li.get(j).getSelected()==1){
float price = li.get(j).getPrice();
int num = li.get(j).getNum();
totalPrice+=price*num;
}
}
}
return totalPrice;
}
public void changeCurrentProductNumber(int groupPosition,int childPositon,int number){
NewsBean.DataBean dataBean = list.get(groupPosition);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
NewsBean.DataBean.ListBean listBean = li.get(childPositon);
listBean.setNum(number);
}
//当商品组全选点击时,更新状态
public void changeCurrentSellerAllProductsStatus(int groupPosition , boolean isSelected){
NewsBean.DataBean dataBean = list.get(groupPosition);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for(int x=0;x<li.size();x++){
NewsBean.DataBean.ListBean listBean1 = li.get(x);
listBean1.setSelected(isSelected ? 1:0);
}
}
//当子条目全选点击时
public void changeCurrentProductStatus(int groupPosition , int childPositon){
NewsBean.DataBean dataBean = list.get(groupPosition);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
NewsBean.DataBean.ListBean listBean = li.get(childPositon);
listBean.setSelected(listBean.getSelected()==0?1:0);
}
//设置所有商品的状态
public void changeAllProductStatus(Boolean selected){
for(int i=0;i<list.size();i++){
NewsBean.DataBean dataBean = list.get(i);
ArrayList<NewsBean.DataBean.ListBean> li = (ArrayList<NewsBean.DataBean.ListBean>) dataBean.getList();
for(int j=0;j<li.size();j++){
li.get(j).setSelected(selected?1:0);
}
}
}*
public static class ParentViewHolder {
public CheckBox seller_cb;
public TextView seller_name_tv;
public ParentViewHolder(View rootView) {
this.seller_cb = (CheckBox) rootView.findViewById(R.id.seller_cb);
this.seller_name_tv = (TextView) rootView.findViewById(R.id.seller_name_tv);
}
}
public static class ChildViewHolder {
public CheckBox child_cb;
public ImageView product_icon_iv;
public TextView product_title_name_tv;
public TextView product_price_tv;
public MyAddSubView add_remove_view;
public ChildViewHolder(View rootView) {
this.child_cb = (CheckBox) rootView.findViewById(R.id.child_cb);
this.product_icon_iv = (ImageView) rootView.findViewById(R.id.product_icon_iv);
this.product_title_name_tv = (TextView) rootView.findViewById(R.id.product_title_name_tv);
this.product_price_tv = (TextView) rootView.findViewById(R.id.product_price_tv);
this.add_remove_view = (MyAddSubView) rootView.findViewById(R.id.add_remove_view);
}
}
public interface onCartListChangeListener{
void onSellerCheckedChange(int groupPosition);
void onProductCheckedChange(int groupPosition ,int childPosition);
void onProducNumberChange(int groupPosition , int childPosition , int number);
}
//接口回调
onCartListChangeListener mOnCartListChangeListener;
//暴露方法
public void setOnCartListChangeListener(onCartListChangeListener onCartListChangeListener){
mOnCartListChangeListener = onCartListChangeListener ;
}
@Override//不管
public boolean hasStableIds() {
return false;
}
@Override//不管
public boolean isChildSelectable(int groupPosition, int childPosition) {
return false;
}
@Override//不管
public Object getGroup(int groupPosition) {
return null;
}
@Override//不管
public Object getChild(int groupPosition, int childPosition) {
return null;
}
@Override//不管
public long getGroupId(int groupPosition) {
return 0;
}
@Override//不管
public long getChildId(int groupPosition, int childPosition) {
return 0;
}
}
效果如下