diff --git a/app/src/main/java/com/gh/common/constant/Config.java b/app/src/main/java/com/gh/common/constant/Config.java index 05b2e920be..e4543b3575 100644 --- a/app/src/main/java/com/gh/common/constant/Config.java +++ b/app/src/main/java/com/gh/common/constant/Config.java @@ -8,7 +8,7 @@ public class Config { public static final String HOST = "http://api.ghzhushou.com/v2d2/"; public static final String USER_HOST = "http://user.ghzhushou.com/v1d0/"; - public static final String COMMENT_HOST = "http://comment.ghzhushou.com/v1d0/"; + public static final String COMMENT_HOST = "http://comment.ghzhushou.com/v1d1/"; public static final String DATA_HOST = "http://data.ghzhushou.com/"; public static final String PREFERENCE = "ghzhushou"; diff --git a/app/src/main/java/com/gh/gamecenter/StrategyActivity.java b/app/src/main/java/com/gh/gamecenter/StrategyActivity.java new file mode 100644 index 0000000000..50f86e42b3 --- /dev/null +++ b/app/src/main/java/com/gh/gamecenter/StrategyActivity.java @@ -0,0 +1,174 @@ +package com.gh.gamecenter; + +import android.animation.Animator; +import android.graphics.drawable.ColorDrawable; +import android.os.Bundle; +import android.support.v7.widget.LinearLayoutManager; +import android.support.v7.widget.RecyclerView; +import android.view.KeyEvent; +import android.view.View; +import android.widget.ImageView; +import android.widget.LinearLayout; +import android.widget.PopupWindow; +import android.widget.RelativeLayout; +import android.widget.TextView; + +import com.gh.base.BaseActivity; +import com.gh.common.util.MeasureHeightLayoutManager; +import com.gh.gamecenter.adapter.StrategyAdapter; +import com.gh.gamecenter.adapter.StrategyDialogAdapter; +import com.gh.gamecenter.db.info.ConcernInfo; + +import butterknife.BindView; +import butterknife.ButterKnife; +import butterknife.OnClick; + +/** + * Created by khy on 2016/12/5. + * + */ +public class StrategyActivity extends BaseActivity implements StrategyDialogAdapter.OnStrategyDialogCallBackListener{ + + @BindView(R.id.strategy_game_name) TextView mGameName; + @BindView(R.id.strategy_select_game_rl) RelativeLayout mSelectGameRl; + @BindView(R.id.strategy_rv) RecyclerView mStrategyRv; + @BindView(R.id.popup_bg) View popupBg; + @BindView(R.id.reuse_none_data) LinearLayout mNoData; + + private StrategyAdapter mStrategyAdapter; + + private PopupWindow mPopupWindow; + + private int mDialogGamePosition; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + View contentView = View.inflate(this, R.layout.activity_strategy, null); + init(contentView, "攻略"); + + ButterKnife.bind(this); + + mDialogGamePosition = -1; + + mStrategyAdapter = new StrategyAdapter(this, null, mNoData); + final LinearLayoutManager layoutManager = new LinearLayoutManager(this); + mStrategyRv.setLayoutManager(layoutManager); + mStrategyRv.setAdapter(mStrategyAdapter); + + mStrategyRv.setOnScrollListener(new RecyclerView.OnScrollListener() { + @Override + public void onScrollStateChanged(RecyclerView recyclerView, int newState) { + super.onScrollStateChanged(recyclerView, newState); + if(layoutManager.findLastVisibleItemPosition() + 1 == mStrategyAdapter.getItemCount() + && newState == RecyclerView.SCROLL_STATE_IDLE && mStrategyAdapter.isCanLoading()) { + mStrategyAdapter.addList(mStrategyAdapter.getItemCount()-1); + } + } + }); + } + + @OnClick(R.id.strategy_select_game_rl) + public void OnSelectGameClickListener() { + isShowPopupBg(true); + + View contentView = View.inflate(this, R.layout.dialog_strategy_select_game, null); + RecyclerView selectGameRv = (RecyclerView) contentView.findViewById(R.id.dialog_strategy_select_game_rv); + ImageView selectIcon = (ImageView) contentView.findViewById(R.id.dialog_strategy_select_game_icon); + RelativeLayout allGameRl = (RelativeLayout) contentView.findViewById(R.id.dialog_strategy_select_game_rl); + + allGameRl.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + mGameName.setText("全部游戏"); + mDialogGamePosition = -1; + isShowPopupBg(false); + mStrategyAdapter = new StrategyAdapter(StrategyActivity.this, null, mNoData); + mStrategyRv.setAdapter(mStrategyAdapter); + } + }); + + if (mDialogGamePosition == -1) { + selectIcon.setImageResource(R.drawable.strategy_game_select); + } else { + selectIcon.setImageDrawable(new ColorDrawable(0)); + } + + selectGameRv.setLayoutManager(new MeasureHeightLayoutManager(this)); + selectGameRv.setAdapter(new StrategyDialogAdapter(this, mDialogGamePosition)); + + mPopupWindow = new PopupWindow(contentView, LinearLayout.LayoutParams.MATCH_PARENT + , LinearLayout.LayoutParams.MATCH_PARENT, true); + mPopupWindow.setAnimationStyle(R.style.scale_popwindow_anim_style); + mPopupWindow.showAtLocation(mSelectGameRl, 0, 0, 0); + + selectGameRv.setOnKeyListener(new View.OnKeyListener() { + @Override + public boolean onKey(View v, int keyCode, KeyEvent event) { + if (keyCode == KeyEvent.KEYCODE_BACK + && event.getRepeatCount() == 0 + && mPopupWindow != null + && mPopupWindow.isShowing()) { + isShowPopupBg(false); + } + return false; + } + }); + + contentView.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + isShowPopupBg(false); + } + }); + } + + public void isShowPopupBg(boolean isShow) { + if(isShow) { + popupBg.setVisibility(View.VISIBLE); + popupBg.animate() + .alpha(1f) + .setDuration(300) + .setListener(null); + } else { + mPopupWindow.dismiss(); + popupBg.animate() + .alpha(0f) + .setDuration(300) + .setListener(new Animator.AnimatorListener() { + @Override + public void onAnimationStart(Animator animation) { + + } + + @Override + public void onAnimationEnd(Animator animation) { + popupBg.setVisibility(View.GONE); + } + + @Override + public void onAnimationCancel(Animator animation) { + + } + + @Override + public void onAnimationRepeat(Animator animation) { + + } + + }); + } + + } + + @Override + public void selectPosition(int position, ConcernInfo concernInfo) { + mNoData.setVisibility(View.GONE); + mDialogGamePosition = position; + mGameName.setText(concernInfo.getGameName()); + isShowPopupBg(false); + + mStrategyAdapter = new StrategyAdapter(this, concernInfo.getId(), mNoData); + mStrategyRv.setAdapter(mStrategyAdapter); + } +} diff --git a/app/src/main/java/com/gh/gamecenter/adapter/StrategyAdapter.java b/app/src/main/java/com/gh/gamecenter/adapter/StrategyAdapter.java new file mode 100644 index 0000000000..0f2afd6b55 --- /dev/null +++ b/app/src/main/java/com/gh/gamecenter/adapter/StrategyAdapter.java @@ -0,0 +1,233 @@ +package com.gh.gamecenter.adapter; + +import android.content.Context; +import android.support.v7.widget.RecyclerView; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.LinearLayout; + +import com.gh.common.util.DataUtils; +import com.gh.common.util.DisplayUtils; +import com.gh.common.util.NewsUtils; +import com.gh.common.view.CardLinearLayout; +import com.gh.gamecenter.R; +import com.gh.gamecenter.StrategyActivity; +import com.gh.gamecenter.adapter.viewholder.NewsFooterViewHolder; +import com.gh.gamecenter.adapter.viewholder.NewsTextViewHolder; +import com.gh.gamecenter.entity.NewsEntity; +import com.gh.gamecenter.manager.DataCollectionManager; +import com.gh.gamecenter.retrofit.Response; +import com.gh.gamecenter.retrofit.RetrofitManager; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import rx.Observable; +import rx.android.schedulers.AndroidSchedulers; +import rx.functions.Func1; +import rx.schedulers.Schedulers; + +/** + * Created by khy on 2016/12/5. + */ +public class StrategyAdapter extends RecyclerView.Adapter { + + private Context mContext; + + private LinearLayout mNoData; + + private List mNewsList; + + private String mGameId; + + private boolean isRemove; + private boolean isLoading; + private boolean isNetworkError; + + public StrategyAdapter(StrategyActivity strategyActivity, String gameId, LinearLayout noData) { + this.mContext = strategyActivity; + this.mGameId = gameId; + this.mNoData = noData; + + mNewsList = new ArrayList<>(); + + isLoading = false; + isRemove = false; + isNetworkError = false; + + addList(0); + } + + public void addList(final int offset) { + isLoading = true; + if (offset == 0) { + mNewsList.clear(); + notifyDataSetChanged(); + } + + Observable> gameNews; + if (mGameId == null) { + gameNews = RetrofitManager.getApi().getNews("攻略", 20, offset); + } else { + gameNews = RetrofitManager.getApi().getGameNews(mGameId, 20, offset); + } + gameNews.map(new Func1, List>() { + @Override + public List call(List newsEntities) { + return NewsUtils.removeDuplicateData(mNewsList, newsEntities); + } + }) + .subscribeOn(Schedulers.io()) + .observeOn(AndroidSchedulers.mainThread()) + .subscribe(new Response>(){ + @Override + public void onResponse(List response) { + super.onResponse(response); + if (response.size() != 0) { + mNewsList.addAll(response); + if (mNewsList.size() <= 20) { + notifyDataSetChanged(); + } else { + notifyItemRangeInserted(mNewsList.size() - response.size(), response.size()); + } + notifyItemChanged(getItemCount() - response.size() - 2); + } + + if (response.size() < 20) { + isRemove = true; + notifyItemChanged(getItemCount() - 1); + } + + if (mNewsList.size() == 0) { + mNoData.setVisibility(View.VISIBLE); + notifyItemChanged(0); + } else { + mNoData.setVisibility(View.GONE); + } + isLoading = false; + } + + @Override + public void onFailure(Throwable e) { + super.onFailure(e); + isNetworkError = true; + isLoading = false; + notifyItemChanged(getItemCount() - 1); + } + }); + } + + @Override + public int getItemViewType(int position) { + if (position == getItemCount() - 1) { + return 0; + } else { + return 1; + } + } + + @Override + public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { + if (viewType == 1) { + View view = LayoutInflater.from(mContext).inflate(R.layout.news_text_item, parent, false); + return new NewsTextViewHolder(view); + } else { + View view = LayoutInflater.from(mContext).inflate(R.layout.news_footer_item, parent, false); + return new NewsFooterViewHolder(view); + } + } + + @Override + public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { + if (holder instanceof NewsTextViewHolder) { + final NewsTextViewHolder viewHolder = (NewsTextViewHolder) holder; + + viewHolder.type.setVisibility(View.GONE); + + // 第一个 + if (position == 0) { + viewHolder.line.setVisibility(View.GONE); + } else { + viewHolder.line.setVisibility(View.VISIBLE); + ((CardLinearLayout) holder.itemView).setmTop(0); + } + + // 最后一个 + if (position +1 == mNewsList.size()) { + ((CardLinearLayout) viewHolder.itemView).setBottom(true); + ((CardLinearLayout) viewHolder.itemView).setmBottom(DisplayUtils.dip2px(mContext, 8)); + } else { + ((CardLinearLayout) viewHolder.itemView).setBottom(false); + ((CardLinearLayout) viewHolder.itemView).setmBottom(0); + } + + final NewsEntity newsEntity = mNewsList.get(position); + viewHolder.type.setBackgroundResource(NewsUtils.getDrawableIdByType(newsEntity.getType())); + viewHolder.type.setText(newsEntity.getType()); + viewHolder.title.setText(newsEntity.getTitle()); + viewHolder.itemView.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + Map kv = new HashMap<>(); + kv.put("名字", newsEntity.getTitle()); + kv.put("位置", String.valueOf(viewHolder.getPosition() + 1)); + DataUtils.onEvent(mContext, "点击", "游戏新闻详情", kv); + + Map map = new HashMap<>(); + map.put("page", "游戏新闻详情"); + map.put("news", newsEntity.getTitle()); + map.put("news_id", newsEntity.getId()); + DataCollectionManager.onEvent(mContext, "click-item", map); + + // 统计阅读量 + NewsUtils.statNewsViews(newsEntity.getId()); + NewsUtils.startNewsActivity(mContext, newsEntity, "主页-游戏-攻略"); + } + }); + } else { + final NewsFooterViewHolder footerViewHolder = ((NewsFooterViewHolder) holder); + if (mNoData.getVisibility() == View.VISIBLE) { + footerViewHolder.itemView.setVisibility(View.GONE); + }else{ + footerViewHolder.itemView.setVisibility(View.VISIBLE); + } + if (isRemove){ + footerViewHolder.hint.setText("加载完毕"); + footerViewHolder.loading.setVisibility(View.GONE); + }else if (isNetworkError){ + footerViewHolder.hint.setText("网络错误,点击重试!"); + footerViewHolder.loading.setVisibility(View.GONE); + } else { + footerViewHolder.hint.setText("加载中..."); + footerViewHolder.loading.setVisibility(View.VISIBLE); + } + footerViewHolder.itemView.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + if (isNetworkError) { + isNetworkError = false; + footerViewHolder.hint.setText("加载中..."); + footerViewHolder.loading.setVisibility(View.VISIBLE); + addList(mNewsList.size()); + } + } + }); + } + } + + @Override + public int getItemCount() { + return mNewsList.size() + 1; + } + + public boolean isCanLoading() { + if (isNetworkError != true && isLoading != true && isRemove != true) { + return true; + } else { + return false; + } + } +} diff --git a/app/src/main/java/com/gh/gamecenter/adapter/StrategyDialogAdapter.java b/app/src/main/java/com/gh/gamecenter/adapter/StrategyDialogAdapter.java new file mode 100644 index 0000000000..227b79df83 --- /dev/null +++ b/app/src/main/java/com/gh/gamecenter/adapter/StrategyDialogAdapter.java @@ -0,0 +1,74 @@ +package com.gh.gamecenter.adapter; + +import android.content.Context; +import android.graphics.drawable.ColorDrawable; +import android.support.v7.widget.RecyclerView; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; + +import com.gh.gamecenter.R; +import com.gh.gamecenter.StrategyActivity; +import com.gh.gamecenter.adapter.viewholder.StrategyDialogViewHolder; +import com.gh.gamecenter.db.info.ConcernInfo; +import com.gh.gamecenter.manager.ConcernManager; + +import java.util.List; + +/** + * Created by khy on 2016/12/5. + */ +public class StrategyDialogAdapter extends RecyclerView.Adapter { + + private Context mContext; + + private OnStrategyDialogCallBackListener callBackListener; + + private List mConcernGame; + + private int mSelectPosition; + + public StrategyDialogAdapter(StrategyActivity strategyActivity, int selectPosition) { + this.mContext = strategyActivity; + this.mSelectPosition = selectPosition; + this.callBackListener = strategyActivity; + + ConcernManager concernManager = new ConcernManager(strategyActivity); + mConcernGame = concernManager.getConcernGame(); + } + + @Override + public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { + View view = LayoutInflater.from(mContext).inflate(R.layout.dialog_strategy_item, parent, false); + return new StrategyDialogViewHolder(view); + } + + @Override + public void onBindViewHolder(RecyclerView.ViewHolder holder, final int position) { + if (holder instanceof StrategyDialogViewHolder) { + StrategyDialogViewHolder viewHolder = ((StrategyDialogViewHolder) holder); + viewHolder.gameName.setText(mConcernGame.get(position).getGameName()); + if (position == mSelectPosition) { + viewHolder.selectIcon.setImageResource(R.drawable.strategy_game_select); + } else { + viewHolder.selectIcon.setImageDrawable(new ColorDrawable(0)); + } + + viewHolder.itemView.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + callBackListener.selectPosition(position, mConcernGame.get(position)); + } + }); + } + } + + @Override + public int getItemCount() { + return mConcernGame.size(); + } + + public interface OnStrategyDialogCallBackListener{ + void selectPosition(int position, ConcernInfo concernInfo); + } +} diff --git a/app/src/main/java/com/gh/gamecenter/adapter/viewholder/StrategyDialogViewHolder.java b/app/src/main/java/com/gh/gamecenter/adapter/viewholder/StrategyDialogViewHolder.java new file mode 100644 index 0000000000..7cedb2d3f5 --- /dev/null +++ b/app/src/main/java/com/gh/gamecenter/adapter/viewholder/StrategyDialogViewHolder.java @@ -0,0 +1,24 @@ +package com.gh.gamecenter.adapter.viewholder; + +import android.support.v7.widget.RecyclerView; +import android.view.View; +import android.widget.ImageView; +import android.widget.TextView; + +import com.gh.gamecenter.R; + +import butterknife.BindView; +import butterknife.ButterKnife; + +/** + * Created by khy on 2016/12/5. + */ +public class StrategyDialogViewHolder extends RecyclerView.ViewHolder{ + @BindView(R.id.dialog_strategy_item_icon) public ImageView selectIcon; + @BindView(R.id.dialog_strategy_item_name) public TextView gameName; + + public StrategyDialogViewHolder(View itemView) { + super(itemView); + ButterKnife.bind(this, itemView); + } +} diff --git a/app/src/main/java/com/gh/gamecenter/retrofit/ApiService.java b/app/src/main/java/com/gh/gamecenter/retrofit/ApiService.java index 7345c821e3..3f8f334487 100644 --- a/app/src/main/java/com/gh/gamecenter/retrofit/ApiService.java +++ b/app/src/main/java/com/gh/gamecenter/retrofit/ApiService.java @@ -47,6 +47,10 @@ public interface ApiService { @GET("support/time/current") Observable getTime(); + @GET("game/{game_id}/news") + Observable> getGameNews(@Path("game_id") String game_id, + @Query("limit") int limit, @Query("offset") int offset); + @Headers({"Content-Type: application/json", "Accept: application/json"}) @PUT("device/{device_id}/concern") // 更新设备关注 Observable putConcern(@Path("device_id") String device_id, @Body RequestBody body); diff --git a/app/src/main/java/com/gh/gamecenter/retrofit/ApiServiceImpl.java b/app/src/main/java/com/gh/gamecenter/retrofit/ApiServiceImpl.java index 09c04111d9..80ca4cd1b4 100644 --- a/app/src/main/java/com/gh/gamecenter/retrofit/ApiServiceImpl.java +++ b/app/src/main/java/com/gh/gamecenter/retrofit/ApiServiceImpl.java @@ -63,6 +63,10 @@ public class ApiServiceImpl { return apiService.getRemenkapai(); } + public Observable> getGameNews(String gameId, int limit, int offset) { + return apiService.getGameNews(gameId, limit, offset); + } + public void putConcern(String device_id, RequestBody body) { subscribe(apiService.putConcern(device_id, body), new Response()); } diff --git a/app/src/main/res/anim/pophidden_anim_scale.xml b/app/src/main/res/anim/pophidden_anim_scale.xml new file mode 100644 index 0000000000..6c985cf448 --- /dev/null +++ b/app/src/main/res/anim/pophidden_anim_scale.xml @@ -0,0 +1,16 @@ + + + \ No newline at end of file diff --git a/app/src/main/res/anim/popshow_anim_scale.xml b/app/src/main/res/anim/popshow_anim_scale.xml new file mode 100644 index 0000000000..43a823b29b --- /dev/null +++ b/app/src/main/res/anim/popshow_anim_scale.xml @@ -0,0 +1,16 @@ + + + \ No newline at end of file diff --git a/app/src/main/res/drawable-hdpi/strategy_game_select.png b/app/src/main/res/drawable-hdpi/strategy_game_select.png new file mode 100644 index 0000000000..e1e0427deb Binary files /dev/null and b/app/src/main/res/drawable-hdpi/strategy_game_select.png differ diff --git a/app/src/main/res/drawable-hdpi/strategy_open.png b/app/src/main/res/drawable-hdpi/strategy_open.png new file mode 100644 index 0000000000..e66e0e5d3a Binary files /dev/null and b/app/src/main/res/drawable-hdpi/strategy_open.png differ diff --git a/app/src/main/res/layout/activity_strategy.xml b/app/src/main/res/layout/activity_strategy.xml new file mode 100644 index 0000000000..7088473145 --- /dev/null +++ b/app/src/main/res/layout/activity_strategy.xml @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_strategy_item.xml b/app/src/main/res/layout/dialog_strategy_item.xml new file mode 100644 index 0000000000..f5355e93d8 --- /dev/null +++ b/app/src/main/res/layout/dialog_strategy_item.xml @@ -0,0 +1,25 @@ + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_strategy_select_game.xml b/app/src/main/res/layout/dialog_strategy_select_game.xml new file mode 100644 index 0000000000..e05ba37f1a --- /dev/null +++ b/app/src/main/res/layout/dialog_strategy_select_game.xml @@ -0,0 +1,50 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/gamedetail_item_intro.xml b/app/src/main/res/layout/gamedetail_item_intro.xml index d2684654cb..efc9c95252 100644 --- a/app/src/main/res/layout/gamedetail_item_intro.xml +++ b/app/src/main/res/layout/gamedetail_item_intro.xml @@ -31,7 +31,7 @@ android:layout_width="match_parent" android:layout_height="1dp" android:layout_marginBottom="15dp" - android:background="#ededed"/> + android:background="@color/cutting_line"/> + //攻略页面 游戏选择动画 + +