Compare commits

..

6 Commits

Author SHA1 Message Date
fengjignqi
50912b10c9 首页设备列表,上拉加载,下拉刷新 2026-05-19 18:03:35 +08:00
fengjignqi
99e0ee56a5 首页设备列表,添加设备 2026-05-19 16:40:34 +08:00
fengjignqi
182289f82d 首页设备列表 2026-05-19 15:02:09 +08:00
fengjignqi
4ef664125e 注册/登录接口联调
个人信息接口联调
2026-05-19 14:05:22 +08:00
fengjignqi
695ace9209 注册/登录接口联调
个人信息接口联调
2026-05-19 11:43:49 +08:00
fengjignqi
c485b1e059 注册/登录接口联调 2026-05-19 08:15:24 +08:00
91 changed files with 1772 additions and 6451 deletions

View File

@@ -4,10 +4,10 @@
<selectionStates>
<SelectionState runConfigName="app">
<option name="selectionMode" value="DROPDOWN" />
<DropdownSelection timestamp="2026-05-15T02:49:19.581976200Z">
<DropdownSelection timestamp="2026-05-19T02:00:28.842946500Z">
<Target type="DEFAULT_BOOT">
<handle>
<DeviceId pluginId="LocalEmulator" identifier="path=C:\Users\Admin\.android\avd\Pixel_7a_2.avd" />
<DeviceId pluginId="PhysicalDevice" identifier="serial=D122222104A9" />
</handle>
</Target>
</DropdownSelection>

View File

@@ -34,6 +34,7 @@
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.BLUETOOTH_SCAN" />
<!--后台获取位置信息,若需后台定位则必选-->
<uses-permission android:name="android.permission.ACCESS_BACKGROUND_LOCATION" />
<!--用于申请调用A-GPS模块,卫星定位加速-->

View File

@@ -18,7 +18,7 @@ public class AppConfig {
// public static boolean IS_TEST_REQUEST = true;
/**************************本地*******************************/
public static String BASE_URL = "http://192.168.1.67:8081/";//测试
public static String BASE_URL = "http://192.168.1.217:8081/";//测试
public static String BASE_URL_TWO = BASE_URL;//测试
public static String BASE_URL_THREE = BASE_URL;//测试
public static boolean IS_TEST_REQUEST = true;
@@ -116,4 +116,8 @@ public class AppConfig {
//用户分享链接
public static String USER_SHARE_URL = "https://sta.mingdengbazi.site/on/index.html?code=";
//clientID 固定 token
public static String APP_CLIENT_ID = "428a8310cd442757ae699df5d894f051";
public static String APP_USER_TYPE = "app_user";
}

View File

@@ -7,9 +7,9 @@ package com.ckkj.water;
*/
public class ConstantUtil {
public static final String ADD_DEVICE_FLAG = "add_device_flag";
//页面跳转来源
public static final String ACTIVITY_NAVIGATE_FLAG = "activity_navigate_flag";
public static final String SHARE_PRE_NAME = "mingdengbazi_pre";
public static final String FIRST_ENTER_APP_AGREEMENT_TIPS = "first_enter_app_agreement_tips";
public static final String FIRST_ENTER_APP_FLAG = "first_enter_app_flag";
@@ -20,47 +20,12 @@ public class ConstantUtil {
public static final String USER_ID = "user_id";
public static final String USER_RONGCLOUD_ID = "user_rongcloud_id";
public static final String USER_INFO_JSON_CONTENT = "user_info_json_content";
public static final String SEARCH_HISTORY = "search_history";
public static final String USER_CONFIRM_UPLOAD_INFO = "user_confirm_upload_info";
public static final String GROUP_LAST_TIME = "group_last_time";
//用户是否同意隐私政策
public static final String PRIVACY_POLICY_AGREED = "privacy_policy_agreed";
//App访问验证code
public static final String APP_ENTER_CODE_VALUE = "app_enter_code_value";
//用户是否允许定位授权
public static final String USER_AUTH_LOCATION = "user_auth_location";
//用户是否请求过定位权限
public static final String USER_REQUEST_LOCATION_PERMISSION = "user_request_location_permission";
//用户是否请求过文件访问权限
public static final String USER_REQUEST_READ_WRITE_PERMISSION = "user_request_read_write_permission";
//用户是否请求过麦克风权限
public static final String USER_REQUEST_RECORD_AUDIO_PERMISSION = "user_request_record_audio_permission";
//用户是否请求过相机权限
public static final String USER_REQUEST_CAMERA_PERMISSION = "user_request_camera_permission";
//用户当前定位省份
public static final String USER_LOCATION_PROVICE_NAME = "user_location_provice_name";
//用户当前定位城市
public static final String USER_LOCATION_CITY_NAME = "user_location_city_name";
//用户当前定位县区
public static final String USER_LOCATION_COUNTY_NAME = "user_location_county_name";
public static final String USER_SELECT_PROVICE_NAME = "user_select_provice_name";
//用户当前定位城市
public static final String USER_SELECT_CITY_NAME = "user_select_city_name";
//用户当前定位县区
public static final String USER_SELECT_COUNTY_NAME = "user_select_county_name";
//首页用户定位code
public static final String INDEX_LOCATION_PROVINCE_CODE = "index_location_province_code";
//用户当前定位县区
public static final String INDEX_LOCATION_CITY_CODE = "index_location_city_code";
//首页用户定位code
public static final String INDEX_SELECT_PROVINCE_CODE = "index_select_province_code";
//用户当前定位县区
public static final String INDEX_SELECT_CITY_CODE = "index_select_city_code";
//用户提交的企业会员认证结果
public static final String USER_REVIEW_STATUS_CODE = "user_review_status_code";
//用户是否为企业会员
public static final String USER_IS_VIP_FLAG = "user_is_vip_flag";
//用户资料中的个人手机号码
public static final String USER_INFO_PHONE_NUMBER = "user_info_phone_number";
//用户资料中头像
@@ -69,36 +34,6 @@ public class ConstantUtil {
public static final String USER_NICKNAME = "user_nickname";
//企业名称
public static final String USER_UPLOAD_COMPANY_NAME = "user_upload_company_name";
//单位名称
public static final String GOODS_UNIT_JSON = "goods_unit_json";
//运费json
public static final String TRANS_COST_JSON = "trans_cost_json";
//品牌名称json
public static final String GOODS_BRAND_JSON = "goods_brand_json";
//所有字典
public static final String MRO_BRAND_DICT_JSON = "mro_dict_json";
/********************大宗相关*********************/
public static final String DICT_DATAS_JSON = "dict_datas_json";
//生成订单来自何处 100商品详情 200购物车
public static final int CREAT_ORDER_FROM_PRODUCT_CODE = 100;
public static final int CREAT_ORDER_FROM_SHOPCAR_CODE = 200;
/********************订单相关*********************/
public static final int ORDER_ALLCODE = -1;//全部
public static final int ORDER_DAIZHIFU = 0;//待支付
public static final int ORDER_WEIFAHUO = 1;//未发货
public static final int ORDER_DAISHOUHUO = 2;//待收货
public static final int ORDER_YIWANCHENG = 3;//已完成
public static final int ORDER_CANCELED = 4;
public static final int ORDER_SHOUHOU = 5;//待收货
public static final int ORDER_BUFENFAHUO = 7;//待收货
public static final int ORDER_DAIQUEREN = 8;//待确认
public static final int ORDER_JIESUANZHONG = 9;//结算中
public static final int ORDER_CHULIZHONG = 0;//处理中
/*******询价单********/
public static final int XJ_BAOJIAZHONG_CODE = 0;//报价中
public static final int XJ_YIBAOJIA_CODE = 1;//已报价
public static final int XJ_YICHEXIAO_CODE = 2;//已撤销
//权限申请请求
public static final int PERMISSION_QUEST = 500;
/***************权限相关*******************/

View File

@@ -11,12 +11,12 @@ import android.util.Log;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.google.gson.Gson;
import com.ckkj.water.fate.util.LunarDateLoader;
import com.ckkj.water.login.entity.LoginEntity;
import com.ckkj.water.network.NetWorkManager;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import java.util.List;
@@ -66,8 +66,6 @@ public class MyApplication extends Application {
super.onCreate();
instance = this;
context = getApplicationContext();
// 异步预加载农历数据缓存
LunarDateLoader.preloadLunarJson(this);
boolean isUserAgreed = SharePreUtil.getBoolean(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.PRIVACY_POLICY_AGREED);
if(isUserAgreed){
@@ -76,16 +74,11 @@ public class MyApplication extends Application {
NetWorkManager.getInstance().init(this);
AppConfig.USER_LOGIN = SharePreUtil.getBoolean(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.USER_LOGIN);
AppConfig.USER_TOKEN = SharePreUtil.getString(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.USER_TOKEN);
AppConfig.USER_SET_BIRTH_INFO = SharePreUtil.getBoolean(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.USER_HAS_SET_BIRTH);
//单位JSON
AppConfig.PRODUCT_UNIT_JSON = SharePreUtil.getString(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.GOODS_UNIT_JSON);
AppConfig.PRODUCT_BRAND_JSON = SharePreUtil.getString(ConstantUtil.SHARE_PRE_NAME,context,ConstantUtil.GOODS_BRAND_JSON);
AppConfig.USER_ID = SharePreUtil.getString(ConstantUtil.SHARE_PRE_NAME,context, ConstantUtil.USER_ID);
String userInfoJson = SharePreUtil.getString(ConstantUtil.SHARE_PRE_NAME,context, ConstantUtil.USER_INFO_JSON_CONTENT);
if(!TextUtils.isEmpty(userInfoJson)){
LoginEntity entity = new Gson().fromJson(userInfoJson, LoginEntity.class);
MingDengUserInfoManager.getInstance().setEntity(entity);
MingDengUserInfoManager.getInstance().setUserInfo(entity.getUser_info());
MineUserInfoBean entity = new Gson().fromJson(userInfoJson, MineUserInfoBean.class);
WaterUserInfoManager.getInstance().setUserInfo(entity);
}
registerActivityLifecycleCallbacks(new ActivityLifecycleCallbacks() {
@Override

View File

@@ -1,6 +1,10 @@
package com.ckkj.water.base.entity;
import java.io.Serializable;
import java.util.List;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author fengxiaoyang
@@ -8,44 +12,55 @@ import java.io.Serializable;
* @description TODO: 描述该类的作用
*/
@NoArgsConstructor
@Data
public class MineUserInfoBean implements Serializable {
private UserInfoEntity userInfo;
private boolean hasEightCharacters;
private String constellation;
private String birthTime;
/**
* userId : 2056543507514097665
* tenantId : 000000
* deptId : null
* userName : null
* nickName : 用户1779153155517
* userType : app_user
* email :
* phonenumber : 133****6054
* sex : 0
* avatar : null
* password : $2a$10$KsCb1Z1znyQgL7W.GoljuuVPctzZ7tS7obu8W2WkK5ydsejQOjRi2
* status : 0
* loginIp : 192.168.1.7
* loginDate : 2026-05-19 11:06:22
* remark : null
* createTime : 2026-05-19 09:12:36
* deptName : null
* roles : []
* roleIds : null
* postIds : null
* roleId : null
* oldPassword : null
*/
public String getConstellation() {
return constellation;
}
public void setConstellation(String constellation) {
this.constellation = constellation;
}
public String getBirthTime() {
return birthTime;
}
public void setBirthTime(String birthTime) {
this.birthTime = birthTime;
}
public UserInfoEntity getUserInfo() {
return userInfo;
}
public void setUserInfo(UserInfoEntity userInfo) {
this.userInfo = userInfo;
}
public boolean isHasEightCharacters() {
return hasEightCharacters;
}
public void setHasEightCharacters(boolean hasEightCharacters) {
this.hasEightCharacters = hasEightCharacters;
}
private String userId;
private String tenantId;
private Object deptId;
private Object userName;
private String nickName;
private String userType;
private String email;
private String phonenumber;
private String sex;
private Object avatar;
private String password;
private String status;
private String loginIp;
private String loginDate;
private Object remark;
private String createTime;
private Object deptName;
private Object roleIds;
private Object postIds;
private Object roleId;
private Object oldPassword;
private List<?> roles;
}

View File

@@ -1,900 +0,0 @@
package com.ckkj.water.chat;
import static android.app.Activity.RESULT_OK;
import android.content.Context;
import android.content.Intent;
import android.graphics.Color;
import android.os.Bundle;
import android.os.Handler;
import android.text.Editable;
import android.text.TextUtils;
import android.text.TextWatcher;
import android.view.MotionEvent;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.core.content.ContextCompat;
import androidx.core.widget.NestedScrollView;
import androidx.recyclerview.widget.GridLayoutManager;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.ckkj.water.AppConfig;
import com.ckkj.water.EventMessage;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.chat.adapter.ChatQuestionDetailAdapter;
import com.ckkj.water.chat.adapter.ChatZixunAdapter;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.ckkj.water.custom.GridSpacingItemDecoration;
import com.ckkj.water.databinding.IndexLayoutBinding;
import com.ckkj.water.chat.adapter.IndexChatAdapter;
import com.ckkj.water.chat.adapter.IndexOptionAdapter;
import com.ckkj.water.chat.adapter.IndexEnterHintAdapter;
import com.ckkj.water.chat.adapter.IndexQuickAskAdapter;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.ChatMultiItem;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.chat.mvp.IndexContract;
import com.ckkj.water.chat.mvp.IndexImpl;
import com.ckkj.water.chat.mvp.IndexPresenter;
import com.ckkj.water.dialog.ContentReportDialog;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.plate.entity.BaziResultBean;
import com.ckkj.water.plate.entity.PaipanCache;
import com.ckkj.water.utils.click.ClickUtil;
import com.ckkj.water.utils.manager.ColorManage;
import com.ckkj.water.utils.show.ToastUtil;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import de.greenrobot.event.Subscribe;
import de.greenrobot.event.ThreadMode;
import android.content.ClipData;
import android.content.ClipboardManager;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class ChatFragment extends BaseFragment<IndexLayoutBinding, IndexPresenter> implements IndexContract.IndexView {
//顶部 adapter
private IndexOptionAdapter mOptionAdapter;
private ChatZixunAdapter mZixunQuestAdapter;
private ChatQuestionDetailAdapter mQuesDetailAdapter;
//快速提问 adapter
private IndexQuickAskAdapter mQuickAskAdapter;
private List<IndexTemplateEntity> mQuickAskList = new ArrayList<>();
private List<ChatMultiItem> mChatMsgList = new ArrayList<>();
//聊天 adapter
private IndexChatAdapter mChatAdapter;
//欢迎语 adapter
private IndexEnterHintAdapter mHintAdapter;
//输入的内容
private String mCurrentInputContent = "";
//当前options 的 pos
private int mCurrentStreamPos = 0;
//模板数据 list
private List<IndexTemplateEntity> mIndexTemList = new ArrayList<>();
//输出是否完成
private boolean mIsStreamStop = true;
//当前选中 option 的 typeID
private String mSelectTypeID = "1";
//会话 ID
private String mSessionId = "";
// 添加流式数据累积变量
private StringBuilder mStreamContentBuilder = new StringBuilder();
private ChatAiMsgEntity mCurrentStreamEntity = null;
// 智能滚动管理
private boolean mIsUserScrolling = false;
// 优化防抖机制
private Handler mUpdateHandler = new Handler();
private Runnable mUpdateRunnable;
private List<ChatQuestionEntity> mQuesTypeList = new ArrayList<>();
private boolean mIsShowQuestions = true;
@Override
public void initData(Bundle state) {
mOptionAdapter = new IndexOptionAdapter(mContext, R.layout.index_device_list_item, mIndexTemList);
viewBinding.rvOptions.setAdapter(mOptionAdapter);
mQuickAskAdapter = new IndexQuickAskAdapter(mContext, R.layout.index_home_quick_ask_item, mQuickAskList);
viewBinding.rvQuickAsk.setAdapter(mQuickAskAdapter);
mChatAdapter = new IndexChatAdapter(mContext, mChatMsgList, viewBinding.rvChat);
viewBinding.rvChat.setAdapter(mChatAdapter);
//提问类型
GridLayoutManager manager = new GridLayoutManager(mContext, 2);
viewBinding.rvChatQuick.setLayoutManager(manager);
List<ChatQuestionEntity.SubheadingsDTO> subList = new ArrayList<>();
mQuesDetailAdapter = new ChatQuestionDetailAdapter(R.layout.chat_quest_detail_item, subList);
viewBinding.rvChatQuick.setAdapter(mQuesDetailAdapter);
viewBinding.rvChatQuick.addItemDecoration(new GridSpacingItemDecoration(2, 10, true));
mZixunQuestAdapter = new ChatZixunAdapter(mContext, R.layout.chat_zixun_type_item, mQuesTypeList);
viewBinding.rvChatType.setAdapter(mZixunQuestAdapter);
// 设置聊天RecyclerView的LayoutManager禁用滚动
androidx.recyclerview.widget.LinearLayoutManager chatLayoutManager =
new androidx.recyclerview.widget.LinearLayoutManager(mContext);
chatLayoutManager.setStackFromEnd(false);
viewBinding.rvChat.setLayoutManager(chatLayoutManager);
// 禁用RecyclerView的滚动让NestedScrollView处理滚动
viewBinding.rvChat.setNestedScrollingEnabled(false);
mHintAdapter = new IndexEnterHintAdapter(mContext, R.layout.index_enter_hint_item, new ArrayList<>());
viewBinding.rvEnterHint.setAdapter(mHintAdapter);
setAdapterClick();
// 添加EditText的焦点监听器
viewBinding.editInput.setOnFocusChangeListener(new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (hasFocus) {
// EditText获取焦点时延迟滚动到底部确保键盘弹出后再滚动
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
scrollNestedScrollViewToBottom();
}
}, 300); // 延迟300ms等待键盘弹出
}
}
});
viewBinding.editInput.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
@Override
public void afterTextChanged(Editable s) {
if (s != null) {
mCurrentInputContent = s.toString().trim();
if (TextUtils.isEmpty(s.toString().trim())) {
viewBinding.imgSend.setImageDrawable(ContextCompat.getDrawable(mContext, R.mipmap.icon_index_send));
viewBinding.editInput.setHint("请输入您的问题");
} else {
viewBinding.imgSend.setImageDrawable(ContextCompat.getDrawable(mContext, R.mipmap.icon_index_send_b));
}
}
}
});
//请求页面模板数据
mPresenter.getIndexTemplateDatas();
mPresenter.getChatTemplateDatas();
//组件增加点击区域
ClickUtil.addClickPart(viewBinding.imgCloseQuick, 30);
ClickUtil.addClickPart(viewBinding.imgRefresh, 30);
ClickUtil.addClickPart(viewBinding.imgHistory, 30);
// 设置智能滚动监听
setupSmartScrollListener();
// 设置页面点击监听,用于隐藏键盘
setupPageClickListener();
// 检查是否有传递过来的参数
checkAndHandleBundle();
}
/**
* 检查并处理传递过来的Bundle参数
*/
private void checkAndHandleBundle() {
Bundle args = getArguments();
if (args != null) {
handleBirthInfoBundle(args);
}
}
/**
* 处理出生信息Bundle参数
*
* @param bundle 包含出生信息的Bundle
*/
public void handleBirthInfoBundle(Bundle bundle) {
if (bundle != null) {
BaziResultBean baseEntity = PaipanCache.get();
// 获取出生信息
BaziResultBean.BaseInfoDTO birthInfo = baseEntity.getBaseInfo();
BaziResultBean.DetailInfoDTO.SizhuInfoDTO sizhuInfoDTO = baseEntity.getDetailInfo().getSizhuInfo();
BaziResultBean.DetailInfoDTO.DayunInfoDTO defaulLiunian = (BaziResultBean.DetailInfoDTO.DayunInfoDTO) bundle.getSerializable("defaul_liunian");
if (birthInfo != null) {
viewBinding.editInput.setText("我叫" + birthInfo.getName() + "," +
((birthInfo.getSex().equals("乾造") ? "" : "") + "," +
"生于公历" + birthInfo.getGongli() + "," + "当前大运为" + defaulLiunian.getDayunStartYear() + "--" +
defaulLiunian.getDayunEndYear() + "" + defaulLiunian.getDayunStartGanzhi() + "大运,四柱为"
+ sizhuInfoDTO.getYear().getTg() + sizhuInfoDTO.getYear().getDz() + "" +
sizhuInfoDTO.getMonth().getTg() + sizhuInfoDTO.getMonth().getDz() + "" +
sizhuInfoDTO.getDay().getTg() + sizhuInfoDTO.getDay().getDz() + "" +
sizhuInfoDTO.getHour().getTg() + sizhuInfoDTO.getHour().getDz() + "," +
"现在需要你根据我的八字,给我具体分析一下我的事业、感情、健康、财富、格局、喜用神"));
}
}
}
/**
* 当Fragment参数更新时调用用于处理onNewIntent的情况
*/
@Override
public void onResume() {
super.onResume();
// 检查是否有新的参数需要处理
Bundle args = getArguments();
if (args != null && args.getBoolean("goto_index_fragment", false)) {
// 处理参数
handleBirthInfoBundle(args);
// 清除标记,避免重复处理
args.remove("goto_index_fragment");
}
}
@Subscribe(threadMode = ThreadMode.MainThread)
public void onGetMessage(EventMessage message) {
//用户添加地址成功
if (message.getEventStrKey().equals(EventMessage.HISTORY_SESSIONID_DELETE_SUCCESS)) {
if (message.getMsg().equals(mSessionId)) {
// viewBinding.linearOptionHint.setVisibility(View.VISIBLE);
mChatMsgList.clear();
mChatAdapter.setNewData(mChatMsgList);
mSessionId = "";
}
}
}
/**
* 设置页面点击监听器
*/
private void setupPageClickListener() {
viewBinding.rvChat.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
// 当用户触摸NestedScrollView时隐藏键盘并清除焦点
if (event.getAction() == MotionEvent.ACTION_DOWN) {
hideKeyboardAndClearFocus();
}
return false;
}
});
}
/**
* 隐藏键盘并清除EditText焦点
*/
private void hideKeyboardAndClearFocus() {
// 清除EditText焦点
viewBinding.editInput.clearFocus();
// 隐藏键盘
InputMethodManager imm = (InputMethodManager) mContext.getSystemService(Context.INPUT_METHOD_SERVICE);
if (imm != null) {
imm.hideSoftInputFromWindow(viewBinding.editInput.getWindowToken(), 0);
}
}
/**
* 滚动NestedScrollView到底部
*/
private void scrollNestedScrollViewToBottom() {
if (viewBinding.nestedScrollChat != null) {
// 获取NestedScrollView的子视图RecyclerView
View childView = viewBinding.nestedScrollChat.getChildAt(0);
if (childView != null) {
// 滚动到底部
viewBinding.nestedScrollChat.smoothScrollTo(0, childView.getHeight());
}
}
}
/**
* 设置智能滚动监听器修改为监听NestedScrollView
*/
private void setupSmartScrollListener() {
// 监听NestedScrollView的滚动
viewBinding.nestedScrollChat.setOnScrollChangeListener(new NestedScrollView.OnScrollChangeListener() {
@Override
public void onScrollChange(NestedScrollView v, int scrollX, int scrollY, int oldScrollX, int oldScrollY) {
// 检测用户是否向上滑动
if (scrollY < oldScrollY) {
// 用户向上滑动
mIsUserScrolling = true;
} else if (scrollY > oldScrollY) {
// 用户向下滑动
mIsUserScrolling = true;
}
// 检查是否滚动到底部
if (scrollY >= (v.getChildAt(0).getHeight() - v.getHeight())) {
// 滚动到底部,恢复自动滚动
mIsUserScrolling = false;
}
}
});
}
private void setAdapterClick() {
//顶部的选项 adapter 点击事件
mOptionAdapter.setOnItemClickListener(new BaseQuickAdapter.OnItemClickListener() {
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
if (mCurrentStreamPos != position) {
if (mIsStreamStop) {
viewBinding.rlQuickAsk.setVisibility(View.GONE);
mOptionAdapter.setSelectPos(position);
setOptionSelStyle(position);
mCurrentStreamPos = position;
mSessionId = "";
mSelectTypeID = mIndexTemList.get(position).getId();
} else {
ToastUtil.showShort(mContext, "Ai解答中请稍后操作");
}
}
}
});
//咨询类型 adapter
mZixunQuestAdapter.setOnItemClickListener(new BaseQuickAdapter.OnItemClickListener() {
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
if (mIsStreamStop) {
mZixunQuestAdapter.setSelectPos(position);
mQuesDetailAdapter.setNewData(mQuesTypeList.get(position).getSubheadings());
} else {
ToastUtil.showShort(mContext, "Ai解答中请稍后操作");
}
}
});
//快速提问
mQuesDetailAdapter.setOnItemClickListener(new BaseQuickAdapter.OnItemClickListener() {
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
if (!AppConfig.USER_LOGIN) {
goTo(mContext, LoginActivity.class, null);
return;
}
if (!mIsStreamStop) {
ToastUtil.showShort(mContext, "Ai解答中请稍后操作");
return;
}
String quickAskContent = mQuesTypeList.get(mZixunQuestAdapter.getmSelPos()).
getSubheadings().get(position).getContent();
sendMsgToAi(quickAskContent);
}
});
//流式输出,是否完成
mChatAdapter.setOnStreamCompleteListener(new IndexChatAdapter.OnStreamCompleteListener() {
@Override
//此时已经流式输出完成
public void onStreamComplete(int position) {
mCurrentStreamPos = position;
viewBinding.imgSend.setVisibility(View.VISIBLE);
viewBinding.imgStop.setVisibility(View.GONE);
mIsStreamStop = true;
}
@Override
public void onStreamStop() {
viewBinding.imgSend.setVisibility(View.VISIBLE);
viewBinding.imgStop.setVisibility(View.GONE);
mIsStreamStop = true;
}
});
mChatAdapter.setOnItemChildClickListener(new BaseQuickAdapter.OnItemChildClickListener() {
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
switch (view.getId()) {
case R.id.img_jb:
ContentReportDialog cancelDialog = new ContentReportDialog(mContext, R.layout.dialog_report_reason, "");
cancelDialog.show();
cancelDialog.setOnDialogListener(new ContentReportDialog.DialogListener() {
@Override
public void callBackDatas(String reason) {
showLoadingDialog();
//举报
mPresenter.commitReport(reason);
}
});
break;
}
}
});
// 设置长按菜单监听器
mChatAdapter.setOnItemLongClickMenuListener(new IndexChatAdapter.OnItemLongClickMenuListener() {
@Override
public void onCopyClick(ChatMultiItem item, int position) {
// 处理复制操作
String content = item.getMessage().getContent();
if (!TextUtils.isEmpty(content)) {
ClipboardManager clipboard = (ClipboardManager) mContext.getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("chat_content", content);
clipboard.setPrimaryClip(clip);
ToastUtil.showShort(mContext, "内容已复制");
}
}
@Override
public void onReportClick(ChatMultiItem item, int position) {
// 处理举报操作
ContentReportDialog cancelDialog = new ContentReportDialog(mContext, R.layout.dialog_report_reason, "");
cancelDialog.show();
cancelDialog.setOnDialogListener(new ContentReportDialog.DialogListener() {
@Override
public void callBackDatas(String reason) {
showLoadingDialog();
//举报
mPresenter.commitReport(reason);
}
});
}
});
// 添加长按监听器
// mChatAdapter.setOnItemChildLongClickListener(new BaseQuickAdapter.OnItemChildLongClickListener() {
// @Override
// public boolean onItemChildLongClick(BaseQuickAdapter adapter, View view, int position) {
// switch (view.getId()) {
// case R.id.tv_text: // 文本内容的view id
// XPopup.fixLongClick(view); // 能保证弹窗弹出后下层的View无法滑动
//
// // 获取当前消息内容
// ChatMultiItem item = mChatMsgList.get(position);
// String content = item.getMessage().getContent();
//
// // 使用链式调用确保atView在asAttachList之前
// new XPopup.Builder(getContext())
// .hasShadowBg(false)
// .atView(view) // 使用atView而不是watchView
// .asAttachList(new String[]{"复制", "举报"},
// null,
// new OnSelectListener() {
// @Override
// public void onSelect(int selectPosition, String text) {
// switch (selectPosition) {
// case 0: // 复制
// if (!TextUtils.isEmpty(content)) {
// ClipboardManager clipboard = (ClipboardManager) mContext.getSystemService(Context.CLIPBOARD_SERVICE);
// ClipData clip = ClipData.newPlainText("chat_content", content);
// clipboard.setPrimaryClip(clip);
// ToastUtil.showShort(mContext, "内容已复制");
// }
// break;
// case 1: // 举报
// ContentReportDialog cancelDialog = new ContentReportDialog(mContext, R.layout.dialog_report_reason, "");
// cancelDialog.show();
// cancelDialog.setOnDialogListener(new ContentReportDialog.DialogListener() {
// @Override
// public void callBackDatas(String reason) {
// showLoadingDialog();
// //举报
// mPresenter.commitReport(reason);
// }
// });
// break;
// }
// }
// })
// .show();
// return true;
// }
// return false;
// }
// });
}
/**
* 停止输出
*/
private void stopSteamOutput() {
// 停止当前网络请求
mPresenter.stopCurrentRequest();
// 获取当前正在流式输出的位置
int currentPosition = mChatMsgList.size() - 1;
// 标记当前消息为被停止状态
mChatAdapter.markAsStopped(currentPosition);
// 停止适配器中的流式输出
mChatAdapter.setStreamerStop(currentPosition);
// 清除当前流式输出位置
mChatAdapter.setCurrentStreamingPosition(-1);
// 强制更新当前item以显示停止标识
mChatAdapter.notifyItemChanged(currentPosition);
// 恢复UI状态
viewBinding.imgSend.setVisibility(View.VISIBLE);
viewBinding.imgStop.setVisibility(View.GONE);
mIsStreamStop = true;
}
@Override
public void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (data != null) {
if (resultCode == RESULT_OK) {
switch (requestCode) {
case REQUEST_EVENT_CODE_10001:
String sessionId = data.getStringExtra("session_id");
String numerologyType = data.getStringExtra("numerology_type");
int showSelPos = -1;
for (int i = 0; i < mIndexTemList.size(); i++) {
if (numerologyType.equals(mIndexTemList.get(i).getId())) {
showSelPos = i;
}
}
if (mCurrentStreamPos != showSelPos) {
}
if (mIsStreamStop) {
viewBinding.rlQuickAsk.setVisibility(View.GONE);
mOptionAdapter.setSelectPos(showSelPos);
setOptionSelStyle(showSelPos);
mCurrentStreamPos = showSelPos;
mSelectTypeID = mIndexTemList.get(showSelPos).getId();
if (!TextUtils.isEmpty(sessionId)) {
mPresenter.getChatDetailByID(sessionId);
}
} else {
ToastUtil.showShort(mContext, "Ai解答中请稍后操作");
}
break;
}
}
}
}
/**
* 发送消息给 AI
*/
private void sendMsgToAi(String senMsg) {
if (!AppConfig.USER_LOGIN) {
goTo(mContext, LoginActivity.class, null);
return;
}
viewBinding.cardQuestion.setVisibility(View.GONE);
viewBinding.imgClose.setImageDrawable(ContextCompat.getDrawable(mContext, R.mipmap.icon_chat_down));
mIsShowQuestions = false;
viewBinding.linearOptionHint.setVisibility(View.GONE);
// 重置滚动状态
mIsUserScrolling = false;
// 清理适配器缓存
mChatAdapter.clearCache();
// 创建用户消息
ChatAiMsgEntity chatMsgEntity = new ChatAiMsgEntity();
chatMsgEntity.setSessionId(mSessionId);
chatMsgEntity.setType(mSelectTypeID);
chatMsgEntity.setContent(senMsg);
ChatMultiItem userEntity = new ChatMultiItem(ChatMultiItem.TYPE_TEXT_RIGHT, chatMsgEntity);
mChatMsgList.add(userEntity);
mChatAdapter.notifyItemInserted(mChatMsgList.size() - 1);
// 创建AI回复消息初始为空
mCurrentStreamEntity = new ChatAiMsgEntity();
mCurrentStreamEntity.setSessionId(mSessionId);
mCurrentStreamEntity.setType(mSelectTypeID);
mCurrentStreamEntity.setContent(""); // 初始为空
ChatMultiItem aiEntity = new ChatMultiItem(ChatMultiItem.TYPE_TEXT_LEFT, mCurrentStreamEntity);
mChatMsgList.add(aiEntity);
// 设置当前流式输出位置
int aiMessagePosition = mChatMsgList.size() - 1;
mChatAdapter.setCurrentStreamingPosition(aiMessagePosition);
mChatAdapter.notifyItemInserted(aiMessagePosition);
// 重置流式数据累积器
mStreamContentBuilder.setLength(0);
// 清空输入框
viewBinding.editInput.setText("");
// 设置UI状态
viewBinding.imgSend.setVisibility(View.GONE);
viewBinding.imgStop.setVisibility(View.VISIBLE);
// 发送消息后自动滚动到底部
scrollToBottomAfterSend();
// 发起流式请求
mPresenter.talkToAi(senMsg, mSelectTypeID, mSessionId);
}
@Override
public IndexPresenter createPresenter() {
return new IndexPresenter(new IndexImpl());
}
@Override
public void getTalkResultSuccess(ChatAiMsgEntity bean) {
hideDialogLoading();
}
/**
* 首页数据获取成功
*
* @param list
*/
@Override
public void getIndexTemplateSuccess(List<IndexTemplateEntity> list) {
if (list != null && list.size() != 0) {
mIndexTemList = list;
mOptionAdapter.setNewData(mIndexTemList);
setAdapterClick();
setOptionSelStyle(0);
mSelectTypeID = mIndexTemList.get(0).getId();
}
}
/**
* 切换设置显示内容
*
* @param pos
*/
private void setOptionSelStyle(int pos) {
try {
mChatMsgList.clear();
mChatAdapter.setNewData(mChatMsgList);
// 清理缓存
mChatAdapter.clearCache();
// viewBinding.linearOptionHint.setVisibility(View.VISIBLE);
IndexTemplateEntity defaulEntity = mIndexTemList.get(pos);
viewBinding.tvTitleExpert.setText(defaulEntity.getTitle() + "专家");
viewBinding.tvSelectOptionLable.setText(defaulEntity.getTitle() + "专家");
viewBinding.tvSelectOptionSlogan.setText(defaulEntity.getSubheading());
if (ColorManage.getInstance().isParsableColor(defaulEntity.getColor())) {
viewBinding.tvSelectOptionSlogan.setTextColor(Color.parseColor(defaulEntity.getColor()));
} else {
viewBinding.tvSelectOptionSlogan.setTextColor(ContextCompat.getColor(mContext, R.color.color_zhu));
}
//提示语
List<String> hintMsgList = new ArrayList<>();
hintMsgList = Arrays.asList(defaulEntity.getIntermediateContent().split("#"));
mHintAdapter.setNewData(hintMsgList);
//快速提问
mQuickAskList.clear();
List<String> quickAskList = new ArrayList<>();
quickAskList = Arrays.asList(defaulEntity.getQuickQuestions().split("#"));
for (String content : quickAskList) {
IndexTemplateEntity entity = new IndexTemplateEntity();
entity.setColor(defaulEntity.getColor());
entity.setBlackcolor(defaulEntity.getBlackcolor());
entity.setSpliteItemContent(content);
mQuickAskList.add(entity);
}
mQuickAskAdapter.setNewData(mQuickAskList);
} catch (Exception e) {
}
}
@Override
public void onNetChange(int netModel) {
}
@Override
public void showError(String message) {
hideDialogLoading();
ToastUtil.showShort(mContext, message);
// 流式传输完成恢复UI状态
viewBinding.imgSend.setVisibility(View.VISIBLE);
viewBinding.imgStop.setVisibility(View.GONE);
mIsStreamStop = true;
// 可以在这里处理会话ID等
if (mCurrentStreamEntity != null && !TextUtils.isEmpty(mCurrentStreamEntity.getSessionId())) {
mSessionId = mCurrentStreamEntity.getSessionId();
}
// 清理当前流式实体
mCurrentStreamEntity = null;
mStreamContentBuilder.setLength(0);
}
@Override
public void logOut(BaseBean bean) {
}
// 实现流式消息接收回调
@Override
public void onStreamMessageReceived(String messageChunk) {
mIsStreamStop = false;
if (mCurrentStreamEntity != null) {
// 更新当前AI消息的内容
mCurrentStreamEntity.setContent(messageChunk);
// 取消之前的更新任务
if (mUpdateRunnable != null) {
mUpdateHandler.removeCallbacks(mUpdateRunnable);
}
mUpdateRunnable = () -> {
// 只更新最后一个item
int lastPosition = mChatMsgList.size() - 1;
if (lastPosition >= 0) {
// 使用更轻量的更新方式,避免重新布局
mChatAdapter.notifyItemChanged(lastPosition, "content_only");
// 流式输出时如果用户没有手动滑动则自动滚动NestedScrollView
if (!mIsUserScrolling) {
smoothScrollNestedScrollView();
}
}
};
// 增加延迟时间,减少更新频率
mUpdateHandler.postDelayed(mUpdateRunnable, 100);
}
}
// 实现流式完成回调
@Override
public void onStreamComplete(String complateMsg) {
// 流式传输完成恢复UI状态
viewBinding.imgSend.setVisibility(View.VISIBLE);
viewBinding.imgStop.setVisibility(View.GONE);
mIsStreamStop = true;
// 清除当前流式输出位置
mChatAdapter.setCurrentStreamingPosition(-1);
// 注意:这里不标记为停止状态,因为这是正常完成
// 可以在这里处理会话ID等
if (mCurrentStreamEntity != null && !TextUtils.isEmpty(mCurrentStreamEntity.getSessionId())) {
mSessionId = mCurrentStreamEntity.getSessionId();
}
// 清理当前流式实体
mCurrentStreamEntity = null;
mStreamContentBuilder.setLength(0);
// 假设你最后一个消息是流式的 placeholder现在替换它
ChatMultiItem lastMessage = mChatMsgList.get(mChatMsgList.size() - 1);
lastMessage.getMessage().setContent(complateMsg); // 你可以解析 Markdown 变 PlainText或保留 Markdown 渲染
// mChatAdapter.notifyItemChanged(mChatMsgList.size() - 1); // 更新 UI
int lastPos = mChatAdapter.getItemCount() - 1;
mChatAdapter.updateTipsVisibility(lastPos);
}
/**
* 根据会话 id 查询对话详情
*
* @param list
*/
@Override
public void getChatDetailSuccess(List<ChatAiMsgEntity> list) {
mChatMsgList.clear();
if (list != null && list.size() != 0) {
mSessionId = list.get(0).getSessionId();
}
for (ChatAiMsgEntity entity : list) {
ChatMultiItem item;
if (entity.getRole().equals("user")) {
item = new ChatMultiItem(ChatMultiItem.TYPE_TEXT_RIGHT, entity);
} else {
item = new ChatMultiItem(ChatMultiItem.TYPE_TEXT_LEFT, entity);
}
mChatMsgList.add(item);
}
mChatAdapter.setNewData(mChatMsgList);
viewBinding.linearOptionHint.setVisibility(View.GONE);
}
@Override
public void loginLost() {
if (isFragmentVisible()) {
handleLoginLost();
}
stopSteamOutput();
if (mChatAdapter != null) {
mChatAdapter.remove(mChatMsgList.size() - 1);
}
}
/**
* 获取咨询模板成功
*
* @param list
*/
@Override
public void getChatZixunSuccess(List<ChatQuestionEntity> list) {
this.mQuesTypeList = list;
if (list != null) {
mZixunQuestAdapter.setNewData(list);
mQuesDetailAdapter.setNewData(list.get(0).getSubheadings());
setAdapterClick();
}
}
/**
* 举报成功
* @param bean
*/
@Override
public void commitReportSuccess(BaseBean bean) {
ToastUtil.showShort(mContext, "星语明灯感谢您的反馈");
hideDialogLoading();
}
// 实现sessionId接收回调
@Override
public void onSessionReceived(String sessionId) {
// 保存sessionId
mSessionId = sessionId;
}
@Override
public void getHistoryDataSuccess(CharHistoryEntity entity) {
}
@Override
public void deleteHistorySuccess(BaseBean bean, int delPos) {
}
/**
* 平滑滚动NestedScrollView到底部
*/
private void smoothScrollNestedScrollView() {
if (mChatAdapter != null && mChatAdapter.getItemCount() > 0) {
// 直接滚动NestedScrollView到底部
viewBinding.nestedScrollChat.post(() -> {
viewBinding.nestedScrollChat.fullScroll(View.FOCUS_DOWN);
});
}
}
/**
* 发送消息后滚动到底部
*/
private void scrollToBottomAfterSend() {
new Handler().postDelayed(() -> {
if (isFragmentVisible()) {
viewBinding.nestedScrollChat.fullScroll(View.FOCUS_DOWN);
}
}, 100);
}
@Override
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
}
@Override
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
}
}

View File

@@ -1,225 +0,0 @@
package com.ckkj.water.chat;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.scwang.smart.refresh.footer.ClassicsFooter;
import com.scwang.smart.refresh.layout.api.RefreshHeader;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.custom.view.CustomRefreshHeader;
import com.ckkj.water.databinding.IndexHistoryLayoutBinding;
import com.ckkj.water.chat.adapter.ChatHistoryAdapter;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.chat.mvp.IndexContract;
import com.ckkj.water.chat.mvp.IndexImpl;
import com.ckkj.water.chat.mvp.IndexPresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.show.ToastUtil;
import java.util.ArrayList;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/11
* @description 历史记录
*/
public class ChatHistoryActivity extends BaseActivity<IndexHistoryLayoutBinding, IndexPresenter>
implements IndexContract.IndexView {
private int mCurrentPage = 1;
private ChatHistoryAdapter mAdapter;
//历史记录
private List<CharHistoryEntity.Sessions> mChatList = new ArrayList<>();
@Override
public IndexPresenter createPresenter() {
return new IndexPresenter(new IndexImpl());
}
@Override
public int getLayoutResId(Bundle savedInstanceState) {
return 0;
}
@Override
public void initData(Bundle savedInstanceState) {
super.initData(savedInstanceState);
ImmersionBar.with(this)
.statusBarColor(R.color.white)
.statusBarDarkFont(true)
.titleBar(viewBinding.rlTitle) // 替换为你的标题栏View
.keyboardEnable(true)
.navigationBarDarkIcon(true)
.init();
viewBinding.includedTitle.tvTitle.setText("历史记录");
viewBinding.includedTitle.imgBack.setOnClickListener(c ->finish());
mAdapter = new ChatHistoryAdapter(mContext, R.layout.history_item_layout, mChatList);
viewBinding.rvData.setAdapter(mAdapter);
setAdapterClick();
// 设置自定义刷新头
RefreshHeader header = new CustomRefreshHeader(mContext);
viewBinding.refresh.setRefreshHeader(header);
viewBinding.refresh.setRefreshFooter(new ClassicsFooter(mContext));
viewBinding.refresh.setOnRefreshListener(layout -> {
mCurrentPage = 1;
getHistoryDatas();
});
viewBinding.refresh.setOnLoadMoreListener(layout -> {
mCurrentPage++;
getHistoryDatas();
});
showLoadingDialog();
getHistoryDatas();
}
private void setAdapterClick() {
mAdapter.setOnItemChildClickListener(new BaseQuickAdapter.OnItemChildClickListener() {
@Override
public void onItemChildClick(BaseQuickAdapter adapter, View view, int position) {
switch (view.getId()){
case R.id.img_delete:
showLoadingDialog();
mPresenter.deleteHistoryBySessionID(mChatList.get(position).getSessionId(),position);
break;
}
}
});
mAdapter.setOnItemClickListener(new BaseQuickAdapter.OnItemClickListener() {
@Override
public void onItemClick(BaseQuickAdapter adapter, View view, int position) {
Intent intent = new Intent();
intent.putExtra("session_id",mChatList.get(position).getSessionId());
intent.putExtra("numerology_type",mChatList.get(position).getNumerologyType());
setResult(RESULT_OK,intent);
finish();
}
});
}
private void getHistoryDatas() {
mPresenter.getHistoryDatas(mCurrentPage);
}
/**
* 查询历史数据成功 g
*
* @param entity
*/
@Override
public void getHistoryDataSuccess(CharHistoryEntity entity) {
hideDialogLoading();
int totalPage = entity.getPages();
viewBinding.refresh.finishRefresh(300);
viewBinding.refresh.finishLoadMore(300);
List<CharHistoryEntity.Sessions> list = entity.getSessions();
if (mCurrentPage == 1) {
mChatList.clear(); // 只在刷新时清除
mChatList = list;
} else {
mChatList.addAll(list);
}
mAdapter.setNewData(mChatList);
// 4. 判断是否还有更多数据
if (totalPage == mCurrentPage || list == null || list.size() == 0) {
// ✅ 告诉 SmartRefreshLayout 没有更多数据了
viewBinding.refresh.setNoMoreData(true);
viewBinding.relNoMore.setVisibility(View.VISIBLE); // 自定义底部提示“暂无更多数据”
} else {
viewBinding.refresh.setNoMoreData(false); // 重置状态
viewBinding.relNoMore.setVisibility(View.GONE);
}
// 5. 控制空布局和内容显示
if (mAdapter.getItemCount() != 0) {
viewBinding.refresh.setVisibility(View.VISIBLE);
viewBinding.relNoresult.setVisibility(View.GONE);
} else {
viewBinding.refresh.setVisibility(View.GONE);
viewBinding.relNoresult.setVisibility(View.VISIBLE);
}
}
/**
* 删除历史会话记录成功
* @param bean
*/
@Override
public void deleteHistorySuccess(BaseBean bean, int delPos) {
hideDialogLoading();
mAdapter.remove(delPos);
if(mAdapter.getItemCount() == 0){
viewBinding.refresh.setVisibility(View.GONE);
viewBinding.relNoresult.setVisibility(View.VISIBLE);
viewBinding.relNoMore.setVisibility(View.GONE);
}
}
@Override
public void getChatDetailSuccess(List<ChatAiMsgEntity> list) {
}
@Override
public void loginLost() {
}
@Override
public void getChatZixunSuccess(List<ChatQuestionEntity> list) {
}
@Override
public void commitReportSuccess(BaseBean bean) {
}
@Override
public void getTalkResultSuccess(ChatAiMsgEntity bean) {
}
@Override
public void getIndexTemplateSuccess(List<IndexTemplateEntity> list) {
}
@Override
public void onStreamMessageReceived(String messageChunk) {
}
@Override
public void onStreamComplete(String complateMsg) {
}
@Override
public void onSessionReceived(String sessionId) {
}
@Override
public void showError(String message) {
viewBinding.refresh.finishRefresh(500);
viewBinding.refresh.finishLoadMore(200);
ToastUtil.showShort(mContext, message);
hideDialogLoading();
}
@Override
public void logOut(BaseBean bean) {
}
}

View File

@@ -1,75 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import android.widget.ImageView;
import androidx.annotation.Nullable;
import androidx.core.content.ContextCompat;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.utils.time.ZYTimeUtils;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/11
* @description TODO: 描述该类的作用
*/
public class ChatHistoryAdapter extends BaseQuickAdapter<CharHistoryEntity.Sessions, BaseViewHolder> {
private Context mContext;
public ChatHistoryAdapter(Context context,int layoutResId, @Nullable List<CharHistoryEntity.Sessions> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder helper, CharHistoryEntity.Sessions item) {
ImageView imgType = helper.getView(R.id.img_logo);
switch (item.getNumerologyType()){
case "1"://八字命理
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap.icon_index_bzml));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_bzml_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_319EF4));
break;
case "2"://紫微斗数
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap. icon_index_zwds));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_zwds_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_B85CE6));
break;
case "3"://风水堪舆
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap.icon_index_fsky));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_fsky_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_24B326));
break;
case "6"://奇门遁甲
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap.icon_index_qmdj));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_qmdj_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_2A5CAA));
break;
case "10"://五行起名
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap. icon_index_wxqm));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_wxqm_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_E69900));
break;
default:
imgType.setImageDrawable(ContextCompat.getDrawable(mContext,R.mipmap.icon_index_bzml));
helper.setBackgroundRes(R.id.tv_type_name,R.drawable.shape_history_type_bzml_bg);
helper.setTextColor(R.id.tv_type_name,ContextCompat.getColor(mContext,R.color.color_319EF4));
break;
}
helper.setText(R.id.tv_type_content,item.getFirstUserMessage());
helper.setText(R.id.tv_type_name,item.getSessionName());
String chatTime = ZYTimeUtils.formatDateOrOneYearAgo(item.getCreateTime());
helper.setText(R.id.tv_time,chatTime);
helper.addOnClickListener(R.id.img_delete);
// helper.addOnClickListener(R.id.rl_title);
// helper.addOnClickListener(R.id.tv_type_content);
// helper.addOnClickListener(R.id.img_logo);
}
}

View File

@@ -1,29 +0,0 @@
package com.ckkj.water.chat.adapter;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/8/19
* @description TODO: 描述该类的作用
*/
public class ChatQuestionDetailAdapter extends BaseQuickAdapter<ChatQuestionEntity.SubheadingsDTO, BaseViewHolder> {
public ChatQuestionDetailAdapter(int layoutResId, @Nullable List<ChatQuestionEntity.SubheadingsDTO> data) {
super(layoutResId, data);
}
@Override
protected void convert(BaseViewHolder helper, ChatQuestionEntity.SubheadingsDTO item) {
helper.setText(R.id.tv_title,item.getTitle());
helper.setText(R.id.tv_content,item.getContent());
}
}

View File

@@ -1,49 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class ChatZixunAdapter extends BaseQuickAdapter<ChatQuestionEntity, BaseViewHolder> {
private Context mContext;
private int mSelPos = 0;
public ChatZixunAdapter(Context context, int layoutResId, @Nullable List<ChatQuestionEntity> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder helper, ChatQuestionEntity item) {
helper.setText(R.id.tv_content,item.getTeb());
if(helper.getLayoutPosition() == mSelPos){
helper.setTextColor(R.id.tv_content,mContext.getColor(R.color.color_zhu));
helper.setBackgroundRes(R.id.tv_content, R.drawable.shape_chat_zixun_type);
}else{
helper.setTextColor(R.id.tv_content,mContext.getColor(R.color.color_7A8699));
helper.setBackgroundRes(R.id.tv_content, R.drawable.shape_trans_touming);
}
}
public void setSelectPos(int position) {
this.mSelPos = position;
notifyDataSetChanged();
}
public int getmSelPos() {
return mSelPos;
}
}

View File

@@ -1,244 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import android.text.Spanned;
import android.text.TextUtils;
import android.util.Log;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.recyclerview.widget.RecyclerView;
import com.chad.library.adapter.base.BaseMultiItemQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.ChatMultiItem;
import com.ckkj.water.utils.show.ToastUtil;
import com.ckkj.water.utils.stream.MarkdownStreamer;
import com.lxj.xpopup.XPopup;
import com.lxj.xpopup.interfaces.OnSelectListener;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import io.noties.markwon.Markwon;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexChatAdapter extends BaseMultiItemQuickAdapter<ChatMultiItem, BaseViewHolder> {
private Context mContext;
private RecyclerView recyclerView;
private OnStreamCompleteListener streamCompleteListener;
//convert() 中每次绑定 item 时缓存 MarkdownStreamer 实例
private final Map<Integer, MarkdownStreamer> streamerMap = new HashMap<>();
// 新增Markdown 解析器
private Markwon markwon;
// 新增:当前正在流式输出的位置
private int mCurrentStreamingPosition = -1;
// 用于标记哪个 position 需要显示 llTips
// 在 IndexChatAdapter 类中新增字段
private Integer pendingTipsCheckPos = null;
// 新增:记录被停止的位置
private final Map<Integer, Boolean> stoppedPositions = new HashMap<>();
public IndexChatAdapter(Context context, List<ChatMultiItem> data, RecyclerView recyclerView) {
super(data);
this.mContext = context;
this.recyclerView = recyclerView;
this.markwon = Markwon.create(context);
addItemType(ChatMultiItem.TYPE_TEXT_LEFT, R.layout.item_text_left);
addItemType(ChatMultiItem.TYPE_TEXT_RIGHT, R.layout.item_text_right);
}
public void setStreamerStop(int position) {
MarkdownStreamer streamer = streamerMap.get(position);
if (streamer != null) {
streamer.stopStreaming();
streamerMap.remove(position);
}
if (mCurrentStreamingPosition == position) {
mCurrentStreamingPosition = -1;
}
}
/**
* 标记某个位置为被停止的状态
*/
public void markAsStopped(int position) {
stoppedPositions.put(position, true);
// 通知该位置更新显示
notifyItemChanged(position);
}
public interface OnStreamCompleteListener {
void onStreamComplete(int position);
void onStreamStop();
}
public void setOnStreamCompleteListener(OnStreamCompleteListener listener) {
this.streamCompleteListener = listener;
}
// 新增:长按菜单项点击回调接口
public interface OnItemLongClickMenuListener {
void onCopyClick(ChatMultiItem item, int position);
void onReportClick(ChatMultiItem item, int position);
}
private OnItemLongClickMenuListener mLongClickMenuListener;
public void setOnItemLongClickMenuListener(OnItemLongClickMenuListener listener) {
this.mLongClickMenuListener = listener;
}
/**
* 设置当前正在流式输出的位置
*/
public void setCurrentStreamingPosition(int position) {
mCurrentStreamingPosition = position;
}
/**
* 对外暴露的方法:检查某个 position 是否为最后一条,并据此显示/隐藏 llTips。
* 仅记录“待检查的位置”并触发该 position 的刷新;实际显示逻辑在 convert() 末尾统一处理。
*/
public void updateTipsVisibility(int position) {
if (position < 0 || position >= getItemCount()) return;
pendingTipsCheckPos = position;
// notifyItemChanged(position);
notifyDataSetChanged();
}
public void setPendingTipsCheckPos(Integer pendingTipsCheckPos) {
this.pendingTipsCheckPos = pendingTipsCheckPos;
}
@Override
protected void convert(BaseViewHolder helper, ChatMultiItem item) {
ChatAiMsgEntity msgEntity = item.getMessage();
TextView tvContent = helper.getView(R.id.tv_text);
LinearLayout llThinking = helper.getView(R.id.linear_thinking);
LinearLayout llStop = helper.getView(R.id.linear_stop);
LinearLayout llTips = helper.getView(R.id.linear_tips);
int position = helper.getBindingAdapterPosition();
helper.addOnClickListener(R.id.img_jb);
// helper.addOnLongClickListener(R.id.tv_text);
if (item.getItemType() == ChatMultiItem.TYPE_TEXT_LEFT) {
String content = msgEntity.getContent();
if(TextUtils.isEmpty(content)){
llThinking.setVisibility(View.VISIBLE);
tvContent.setText("");
llStop.setVisibility(View.GONE);
} else {
llThinking.setVisibility(View.GONE);
// 优化流式输出更新逻辑
if (position == mCurrentStreamingPosition) {
// 当前正在流式输出的位置
try {
Spanned spanned = markwon.toMarkdown(content);
tvContent.setText(spanned);
} catch (Exception e) {
tvContent.setText(content);
}
// 显示停止标识(如果被停止)
if (stoppedPositions.containsKey(position) && stoppedPositions.get(position)) {
llStop.setVisibility(View.VISIBLE);
llTips.setVisibility(View.VISIBLE);
} else {
llStop.setVisibility(View.GONE);
}
} else {
// 历史消息,直接显示完整内容
try {
Spanned spanned = markwon.toMarkdown(content);
tvContent.setText(spanned);
} catch (Exception e) {
tvContent.setText(content);
}
// 历史消息也检查是否被停止
if (stoppedPositions.containsKey(position) && stoppedPositions.get(position)) {
llStop.setVisibility(View.VISIBLE);
llTips.setVisibility(View.VISIBLE);
} else {
llStop.setVisibility(View.GONE);
}
}
}
Log.i("mingdenglog","XXXXX---position======" + pendingTipsCheckPos);
if (pendingTipsCheckPos != null && position == pendingTipsCheckPos) {
Log.i("mingdenglog","position======" + position);
Log.i("mingdenglog","getItemCount() - 1 ------" + (getItemCount() - 1) );
// 仅当是最后一条才显示 llTips否则隐藏
llTips.setVisibility(position == getItemCount() - 1 ? View.VISIBLE : View.GONE);
// 用一次即清
// pendingTipsCheckPos = null;
}else{
llTips.setVisibility(View.GONE);
}
}
switch (item.getItemType()) {
case ChatMultiItem.TYPE_TEXT_RIGHT:
tvContent.setText(msgEntity.getContent());
break;
}
// //必须要在事件发生之前就watch
final XPopup.Builder builder = new XPopup.Builder(mContext)
.hasShadowBg(false).watchView(tvContent);
tvContent.setOnLongClickListener(new View.OnLongClickListener() {
@Override
public boolean onLongClick(View v) {
// 如果正在流式输出,则拦截长按事件,不执行任何操作
if (mCurrentStreamingPosition != -1) {
// 可以选择性地提示用户
ToastUtil.showShort(mContext, "Ai解答中请稍后操作");
return true; // 拦截事件
}
builder.asAttachList(new String[]{"复制", "举报"}, null, new OnSelectListener() {
@Override
public void onSelect(int menuPosition, String text) {
// 通过接口回调处理菜单项点击事件
if (mLongClickMenuListener != null) {
switch (menuPosition){
case 0: // 复制
mLongClickMenuListener.onCopyClick(item, position);
break;
case 1: // 举报
mLongClickMenuListener.onReportClick(item, position);
break;
}
}
}
}).show();
return false;
}
});
}
/**
* 清理缓存
*/
public void clearCache() {
streamerMap.clear();
stoppedPositions.clear();
mCurrentStreamingPosition = -1;
}
}

View File

@@ -1,38 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexEnterHintAdapter extends BaseQuickAdapter<String, BaseViewHolder> {
private Context mContext;
private int mSelPos = 0;
private String textColor;
private String bgColor;
public void setColor(String textColor,String bgColor){
this.textColor = textColor;
this.bgColor = bgColor;
}
public IndexEnterHintAdapter(Context context, int layoutResId, @Nullable List<String> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder helper, String item) {
helper.setText(R.id.tv_quick_ask_name,item);
}
}

View File

@@ -1,45 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexOptionAdapter extends BaseQuickAdapter<IndexTemplateEntity, BaseViewHolder> {
private Context mContext;
private int mSelPos = 0;
public IndexOptionAdapter(Context context,int layoutResId, @Nullable List<IndexTemplateEntity> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder helper, IndexTemplateEntity item) {
// helper.setText(R.id.tv_option_name,item.getTitle());
// if(helper.getLayoutPosition() == mSelPos){
// helper.setTextColor(R.id.tv_option_name,mContext.getColor(R.color.white));
// helper.setBackgroundRes(R.id.tv_option_name, R.drawable.shape_index_option_selected);
// }else{
// helper.setTextColor(R.id.tv_option_name,mContext.getColor(R.color.color_zhu));
// helper.setBackgroundRes(R.id.tv_option_name, R.drawable.shape_index_option_un_selected);
// }
}
public void setSelectPos(int position) {
this.mSelPos = position;
notifyDataSetChanged();
}
}

View File

@@ -1,58 +0,0 @@
package com.ckkj.water.chat.adapter;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.GradientDrawable;
import android.util.TypedValue;
import android.view.View;
import androidx.annotation.Nullable;
import androidx.core.content.ContextCompat;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.utils.manager.ColorManage;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/8
* @description TODO: 描述该类的作用
*/
public class IndexQuickAskAdapter extends BaseQuickAdapter<IndexTemplateEntity, BaseViewHolder> {
private Context context;
public IndexQuickAskAdapter(Context context,int layoutResId, @Nullable List<IndexTemplateEntity> data) {
super(layoutResId, data);
this.context = context;
}
@Override
protected void convert(BaseViewHolder helper, IndexTemplateEntity item) {
helper.setText(R.id.tv_quick_ask_name,item.getSpliteItemContent());
if(ColorManage.getInstance().isParsableColor(item.getColor())){
helper.setTextColor(R.id.tv_quick_ask_name, Color.parseColor(item.getColor()));
}else{
helper.setTextColor(R.id.tv_quick_ask_name, ContextCompat.getColor(mContext,R.color.color_zhu));
}
if(ColorManage.getInstance().isParsableColor(item.getBlackcolor())){
setRoundedBackground(helper.getView(R.id.tv_quick_ask_name),Color.parseColor(item.getBlackcolor()),30);
}else{
setRoundedBackground(helper.getView(R.id.tv_quick_ask_name),ContextCompat.getColor(mContext,R.color.color_E5F2FB),30);
}
}
private void setRoundedBackground(View view, int fillColor, float cornerRadiusDp) {
GradientDrawable drawable = new GradientDrawable();
drawable.setShape(GradientDrawable.RECTANGLE);
drawable.setColor(fillColor); // 设置填充色
float radiusPx = TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, cornerRadiusDp, view.getResources().getDisplayMetrics()
);
drawable.setCornerRadius(radiusPx); // 设置圆角半径单位px
view.setBackground(drawable); // 应用背景
}
}

View File

@@ -1,122 +0,0 @@
package com.ckkj.water.chat.entity;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/11
* @description TODO: 描述该类的作用
*/
public class CharHistoryEntity implements Serializable {
private int total;
private List<Sessions> sessions;
private int pages;
private int pageSize;
private long userId;
private int pageNum;
public void setTotal(int total) {
this.total = total;
}
public int getTotal() {
return total;
}
public void setSessions(List<Sessions> sessions) {
this.sessions = sessions;
}
public List<Sessions> getSessions() {
return sessions;
}
public void setPages(int pages) {
this.pages = pages;
}
public int getPages() {
return pages;
}
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public int getPageSize() {
return pageSize;
}
public void setUserId(long userId) {
this.userId = userId;
}
public long getUserId() {
return userId;
}
public void setPageNum(int pageNum) {
this.pageNum = pageNum;
}
public int getPageNum() {
return pageNum;
}
public static class Sessions implements Serializable{
private String sessionId;
private long userId;
private String sessionName;
private String numerologyType;
private String firstUserMessage;
private Date createTime;
private Date updateTime;
public void setSessionId(String sessionId) {
this.sessionId = sessionId;
}
public String getSessionId() {
return sessionId;
}
public void setUserId(long userId) {
this.userId = userId;
}
public long getUserId() {
return userId;
}
public void setSessionName(String sessionName) {
this.sessionName = sessionName;
}
public String getSessionName() {
return sessionName;
}
public void setNumerologyType(String numerologyType) {
this.numerologyType = numerologyType;
}
public String getNumerologyType() {
return numerologyType;
}
public void setFirstUserMessage(String firstUserMessage) {
this.firstUserMessage = firstUserMessage;
}
public String getFirstUserMessage() {
return firstUserMessage;
}
public void setCreateTime(Date createTime) {
this.createTime = createTime;
}
public Date getCreateTime() {
return createTime;
}
public void setUpdateTime(Date updateTime) {
this.updateTime = updateTime;
}
public Date getUpdateTime() {
return updateTime;
}
}
}

View File

@@ -1,75 +0,0 @@
package com.ckkj.water.chat.entity;
import java.io.Serializable;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class ChatAiMsgEntity implements Serializable {
private int id;
private String sessionId;
private String type;
private String content;
private String role;
private String messageOrder;
private String createTime;
public String getSessionId() {
return sessionId;
}
public void setSessionId(String sessionId) {
this.sessionId = sessionId;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getContent() {
return content;
}
public void setContent(String content) {
this.content = content;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getRole() {
return role;
}
public void setRole(String role) {
this.role = role;
}
public String getMessageOrder() {
return messageOrder;
}
public void setMessageOrder(String messageOrder) {
this.messageOrder = messageOrder;
}
public String getCreateTime() {
return createTime;
}
public void setCreateTime(String createTime) {
this.createTime = createTime;
}
}

View File

@@ -1,44 +0,0 @@
package com.ckkj.water.chat.entity;
import com.chad.library.adapter.base.entity.MultiItemEntity;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class ChatMultiItem implements MultiItemEntity {
public static final int TYPE_TEXT_LEFT = 1;
public static final int TYPE_TEXT_RIGHT = 2;
public static final int TYPE_IMAGE_LEFT = 3;
public static final int TYPE_IMAGE_RIGHT = 4;
public static final int TYPE_VOICE_LEFT = 5;
public static final int TYPE_VOICE_RIGHT = 6;
public static final int TYPE_TIME = 7; // 新增时间类型
private int itemType;
private ChatAiMsgEntity message;
public ChatMultiItem(int itemType, ChatAiMsgEntity message) {
this.itemType = itemType;
this.message = message;
}
@Override
public int getItemType() {
return itemType;
}
public void setItemType(int itemType) {
this.itemType = itemType;
}
public ChatAiMsgEntity getMessage() {
return message;
}
public void setMessage(ChatAiMsgEntity message) {
this.message = message;
}
}

View File

@@ -1,36 +0,0 @@
package com.ckkj.water.chat.entity;
import com.google.gson.annotations.SerializedName;
import java.io.Serializable;
import java.util.List;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author fengxiaoyang
* @date 2025/8/19
* @description TODO: 描述该类的作用
*/
@NoArgsConstructor
@Data
public class ChatQuestionEntity implements Serializable {
@SerializedName("teb")
private String teb;
@SerializedName("subheadings")
private List<SubheadingsDTO> subheadings;
@SerializedName("id")
private String id;
@NoArgsConstructor
@Data
public static class SubheadingsDTO {
@SerializedName("title")
private String title;
@SerializedName("content")
private String content;
}
}

View File

@@ -1,111 +0,0 @@
package com.ckkj.water.chat.entity;
import java.io.Serializable;
/**
* @author fengxiaoyang
* @date 2025/7/8
* @description TODO: 描述该类的作用
*/
public class IndexTemplateEntity implements Serializable {
private String id;
private String title;
private String titletp;
private String color;
private String blackcolor;
private String subheading;
private String intermediateContent;
private String quickQuestions;
private String hide;
private String type;
private String spliteItemContent;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getTitletp() {
return titletp;
}
public void setTitletp(String titletp) {
this.titletp = titletp;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
public String getBlackcolor() {
return blackcolor;
}
public void setBlackcolor(String blackcolor) {
this.blackcolor = blackcolor;
}
public String getSubheading() {
return subheading;
}
public void setSubheading(String subheading) {
this.subheading = subheading;
}
public String getIntermediateContent() {
return intermediateContent;
}
public void setIntermediateContent(String intermediateContent) {
this.intermediateContent = intermediateContent;
}
public String getQuickQuestions() {
return quickQuestions;
}
public void setQuickQuestions(String quickQuestions) {
this.quickQuestions = quickQuestions;
}
public String getHide() {
return hide;
}
public void setHide(String hide) {
this.hide = hide;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getSpliteItemContent() {
return spliteItemContent;
}
public void setSpliteItemContent(String spliteItemContent) {
this.spliteItemContent = spliteItemContent;
}
}

View File

@@ -1,78 +0,0 @@
package com.ckkj.water.chat.mvp;
import com.ckkj.water.base.IView;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.network.BaseBean;
import java.util.List;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexContract {
public interface DataModel{
//发送消息给 AI
void sendMsgToAi(Map<String,Object> map, CallBack callBack);
//发送消息给 AI
void sendMsgToAi(Map<String,Object> map, AiStreamCallback callBack);
//停止当前请求
void stopCurrentRequest();
//获取首页数据
void getIndexTemplateDatas(CallBack callBack);
//获取会话历史
void getHistoryChatDatas(Map<String,Object> map, CallBack callBack);
//删除会话
void deleteHistoryBySessionID(Map<String,Object> map, CallBack callBack);
//根据会话 id查询记录详情
void getChatDetailById(Map<String,Object> map, CallBack callBack);
//首页咨询模板
void getChatemplateDatas(CallBack callBack);
//举报好友
void commitReport(Map<String,Object> map,CallBack callBack);
}
public interface CallBack<T> {
void success(T msg);
void fail(String msg);
}
public interface AiStreamCallback {
void onMessage(String messageChunk); // 每次返回一段内容
void onError(String error);
void onComplete(String complateContent); // 结束
void onSessionReceived(String sessionId); // 新增接收sessionId
void loginLost();
}
public interface IndexView extends IView {
//发送消息给 AI获取结果
void getTalkResultSuccess(ChatAiMsgEntity bean);
//获取首页数据成功
void getIndexTemplateSuccess(List<IndexTemplateEntity> list);
// 新增流式回调方法
void onStreamMessageReceived(String messageChunk);
//完成
void onStreamComplete(String complateMsg);
//接收sessionId
void onSessionReceived(String sessionId);
//查询历史记录成功 g
void getHistoryDataSuccess(CharHistoryEntity entity);
//删除会话成功
void deleteHistorySuccess(BaseBean bean,int delPos);
//根据 id 查询会话详情
void getChatDetailSuccess(List<ChatAiMsgEntity> list);
//登录失效
void loginLost();
//获取首页聊天模板
void getChatZixunSuccess(List<ChatQuestionEntity> list);
//提交举报反馈成功
void commitReportSuccess(BaseBean bean);
}
}

View File

@@ -1,575 +0,0 @@
package com.ckkj.water.chat.mvp;
import static android.content.ContentValues.TAG;
import android.os.Handler;
import android.os.Looper;
import android.util.Log;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.ckkj.water.AppConfig;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.network.NetWorkManager;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URLEncoder;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;
import java.net.SocketTimeoutException;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexImpl implements IndexContract.DataModel{
@Override
public void sendMsgToAi(Map<String, Object> map, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().indexTalkToAi(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<ChatAiMsgEntity>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<ChatAiMsgEntity> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 发送消息给 AI - 流式版本
* @param map
* @param callBack
*/
private final OkHttpClient client = new OkHttpClient.Builder()
.connectTimeout(60, TimeUnit.SECONDS) // 连接超时60秒
.readTimeout(60, TimeUnit.SECONDS) // 读取超时60秒
.writeTimeout(60, TimeUnit.SECONDS) // 写入超时60秒
.callTimeout(60, TimeUnit.SECONDS) // 整个调用超时60秒
.build();
private Call currentCall = null; // 新增保存当前请求的Call对象
private volatile boolean isRequestStopped = false; // 新增:标记是否已停止请求
@Override
public void sendMsgToAi(Map<String, Object> map, IndexContract.AiStreamCallback callBack) {
try {
String finalUrl = AppConfig.BASE_URL + "mobile/context?" + buildQueryParams(map);
Log.d(TAG, "Request URL: " + finalUrl);
Request request = new Request.Builder()
.addHeader("Authorization", "Bearer " + AppConfig.USER_TOKEN)
.url(finalUrl)
.get()
.build();
currentCall = client.newCall(request);
isRequestStopped = false;
currentCall.enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
if (isRequestStopped) return; // 如果已停止,不处理失败回调
// 检查是否是超时异常
String errorMessage = e.getMessage();
if (e instanceof SocketTimeoutException ||
(errorMessage != null && errorMessage.contains("timeout"))) {
errorMessage = "请求超时,请稍后重试";
}
String finalErrorMessage = errorMessage;
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null) callBack.onError(finalErrorMessage);
});
}
@Override
public void onResponse(Call call, Response response) {
if (isRequestStopped) return;
if (!response.isSuccessful()) {
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null) callBack.onError("请求失败: " + response.code());
});
return;
}
InputStream inputStream = response.body().byteStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream));
try {
reader.mark(1024); // 标记流的当前位置
String peekLine = reader.readLine();
reader.reset(); // 回到标记位置
// 判断是否是标准 JSON非流式错误返回
if (peekLine != null && peekLine.trim().startsWith("{")) {
StringBuilder jsonBuilder = new StringBuilder();
String line;
while ((line = reader.readLine()) != null) {
jsonBuilder.append(line);
}
String responseJson = jsonBuilder.toString();
JSONObject json = new JSONObject(responseJson);
int code = json.optInt("code", 0);
String msg = json.optString("msg", "");
if (code == 401) {
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null) callBack.loginLost();
});
} else {
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null) callBack.onError("未知错误: " + msg);
});
}
return;
}
// 否则处理为 SSE 流式数据
handleSSEStream(reader, callBack);
} catch (Exception e) {
new Handler(Looper.getMainLooper()).post(() -> {
// if (callBack != null) callBack.onError("响应异常: " + e.getMessage());
});
} finally {
try {
reader.close();
response.close();
} catch (IOException ignored) {}
}
}
});
} catch (Exception e) {
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null) callBack.onError("请求异常: " + e.getMessage());
});
}
}
private void handleSSEStream(BufferedReader reader, IndexContract.AiStreamCallback callBack) throws IOException {
String line;
StringBuilder accumulatedContent = new StringBuilder();
StringBuilder lastLineBuffer = new StringBuilder();
String currentEvent = null;
String currentData = null;
String sessionId = "";
while ((line = reader.readLine()) != null) {
if (isRequestStopped) break;
if (line.startsWith("event:")) {
currentEvent = line.substring(6).trim();
} else if (line.startsWith("data:")) {
currentData = line.substring(5).trim();
if ("session".equals(currentEvent)) {
try {
JsonObject sessionData = JsonParser.parseString(currentData).getAsJsonObject();
sessionId = sessionData.get("sessionId").getAsString();
if (callBack != null && !isRequestStopped) {
callBack.onSessionReceived(sessionId);
}
} catch (Exception e) {
Log.e(TAG, "解析session数据失败", e);
}
} else if ("chunk".equals(currentEvent)) {
try {
JsonObject chunkData = JsonParser.parseString(currentData).getAsJsonObject();
String content = chunkData.get("content").getAsString();
boolean hasNewline = chunkData.get("hasNewline").getAsBoolean();
if (isTableLineFragment(lastLineBuffer.toString(), content)) {
lastLineBuffer.append(content);
if (hasNewline) {
accumulatedContent.append(lastLineBuffer).append("\n");
lastLineBuffer.setLength(0);
}
} else {
if (lastLineBuffer.length() > 0) {
accumulatedContent.append(lastLineBuffer);
lastLineBuffer.setLength(0);
}
lastLineBuffer.append(content);
if (hasNewline) {
accumulatedContent.append(lastLineBuffer).append("\n");
lastLineBuffer.setLength(0);
}
}
final String currentContent = accumulatedContent.toString();
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null && !isRequestStopped) {
callBack.onMessage(currentContent);
}
});
} catch (Exception e) {
accumulatedContent.append(currentData);
final String currentContent = accumulatedContent.toString();
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null && !isRequestStopped) {
callBack.onMessage(currentContent);
}
});
}
} else if ("complete".equals(currentEvent)) {
// 先处理剩余的 lastLineBuffer 内容,但不通过 onMessage 回调
if (lastLineBuffer.length() > 0) {
accumulatedContent.append(lastLineBuffer);
// 注意:这里不调用 callBack.onMessage(),避免触发 onStreamMessageReceived
}
String complateContent = "";
try {
JsonObject completeData = JsonParser.parseString(currentData).getAsJsonObject();
complateContent = completeData.get("fullResponse").getAsString();
} catch (Exception e) {
Log.e(TAG, "解析complete数据失败", e);
}
final String finalComplateContent = complateContent;
new Handler(Looper.getMainLooper()).post(() -> {
if (callBack != null && !isRequestStopped) {
callBack.onComplete(finalComplateContent); // 只调用 onComplete
}
});
}
}
}
// 处理结束前残留内容
// if (lastLineBuffer.length() > 0 && !isRequestStopped) {
// accumulatedContent.append(lastLineBuffer);
// final String finalContent = accumulatedContent.toString();
// new Handler(Looper.getMainLooper()).post(() -> {
// if (callBack != null && !isRequestStopped) {
// callBack.onMessage(finalContent);
// }
// });
// }
}
/**
* 停止当前请求
*/
public void stopCurrentRequest() {
isRequestStopped = true;
if (currentCall != null && !currentCall.isCanceled()) {
currentCall.cancel();
currentCall = null;
}
}
/**
* 判断是否是表格分隔线片段
*/
private boolean isTableLineFragment(String last, String curr) {
return (last.contains("|") && last.contains("-")) || (curr.contains("|") && curr.contains("-"));
}
// 构造 GET 参数
private String buildQueryParams(Map<String, Object> map) {
StringBuilder sb = new StringBuilder();
for (Map.Entry<String, Object> entry : map.entrySet()) {
try {
if (sb.length() > 0) sb.append("&");
sb.append(URLEncoder.encode(entry.getKey(), "UTF-8"));
sb.append("=");
sb.append(URLEncoder.encode(String.valueOf(entry.getValue()), "UTF-8"));
} catch (Exception e) {
Log.e(TAG, "Encoding error", e);
}
}
return sb.toString();
}
/**
* 获取首页数据
*/
@Override
public void getIndexTemplateDatas(IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getIndexTemplateDatas()
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<List<IndexTemplateEntity>>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<List<IndexTemplateEntity>> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 获取会话历史记录
* @param map
* @param callBack
*/
@Override
public void getHistoryChatDatas(Map<String, Object> map, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getHistoryList(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<CharHistoryEntity>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<CharHistoryEntity> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 删除历史会话
* @param map
* @param callBack
*/
@Override
public void deleteHistoryBySessionID(Map<String, Object> map, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().deleteHistoryBySessionID(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean bean) {
if(bean.getCode() == 200){
callBack.success(bean);
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 根据会话 id 查询详情
* @param map
* @param callBack
*/
@Override
public void getChatDetailById(Map<String, Object> map, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getChatDetailById(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<List<ChatAiMsgEntity>>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<List<ChatAiMsgEntity>> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 对话页,咨询模板获取
* @param callBack
*/
@Override
public void getChatemplateDatas(IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().aitebcontent()
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<List<ChatQuestionEntity>>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<List<ChatQuestionEntity>> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 举报反馈
* @param map
* @param callBack
*/
@Override
public void commitReport(Map<String, Object> map, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().commitReporting(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}

View File

@@ -1,249 +0,0 @@
package com.ckkj.water.chat.mvp;
import com.ckkj.water.EventMessage;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.network.BaseBean;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import de.greenrobot.event.EventBus;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class IndexPresenter extends BasePresenter<IndexContract.IndexView> {
private IndexImpl impl;
public IndexPresenter(IndexImpl impl) {
this.impl = impl;
}
/**
* 发送消息给 AI
*
* @param content
*/
// public void talkToAi(String content,String type) {
// Map<String,Object> map = new HashMap<>();
// map.put("content",content);
// map.put("type",type);
// map.put("sessionId","");
// impl.sendMsgToAi(map, new IndexContract.CallBack<ChatAiMsgEntity>() {
// @Override
// public void success(ChatAiMsgEntity bean) {
// if( IndexPresenter.this.getView() != null){
// IndexPresenter.this.getView().getTalkResultSuccess(bean);
// }
// }
//
// @Override
// public void fail(String msg) {
// if( IndexPresenter.this.getView() != null){
// IndexPresenter.this.getView().showError(msg);
// }
// }
// });
// }
public void talkToAi(String content, String type, String sessionID) {
Map<String, Object> map = new HashMap<>();
map.put("content", content);
map.put("type", type);
map.put("sessionId", sessionID);
impl.sendMsgToAi(map, new IndexContract.AiStreamCallback() {
@Override
public void onMessage(String messageChunk) {
// 流式数据到达时通知View更新UI
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().onStreamMessageReceived(messageChunk);
}
}
@Override
public void onError(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
@Override
public void onComplete(String complateMsg) {
// 流式传输完成
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().onStreamComplete(complateMsg);
}
}
@Override
public void onSessionReceived(String sessionId) {
// 接收到sessionId时通知View
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().onSessionReceived(sessionId);
}
}
@Override
public void loginLost() {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().loginLost();
}
}
});
}
/**
* 停止当前流式请求
*/
public void stopCurrentRequest() {
impl.stopCurrentRequest();
}
/**
* 首页模板消息数据获取
*/
public void getIndexTemplateDatas() {
impl.getIndexTemplateDatas(new IndexContract.CallBack<List<IndexTemplateEntity>>() {
@Override
public void success(List<IndexTemplateEntity> list) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().getIndexTemplateSuccess(list);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 获取历史记录
* @param mCurrentPage
*/
public void getHistoryDatas(int mCurrentPage) {
Map<String, Object> map = new HashMap<>();
map.put("pageNum", mCurrentPage);
map.put("pageSize", 10);
impl.getHistoryChatDatas(map, new IndexContract.CallBack<CharHistoryEntity>() {
@Override
public void success(CharHistoryEntity entity) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().getHistoryDataSuccess(entity);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 删除历史记录
* @param sessionID
*/
public void deleteHistoryBySessionID(String sessionID,int delPos) {
Map<String, Object> map = new HashMap<>();
map.put("sessionId", sessionID);
impl.deleteHistoryBySessionID(map, new IndexContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean entity) {
EventBus.getDefault().post(new EventMessage(EventMessage.HISTORY_SESSIONID_DELETE_SUCCESS,sessionID));
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().deleteHistorySuccess(entity,delPos);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 根据sessionID 查询消息记录
* @param sessionId
*/
public void getChatDetailByID(String sessionId) {
Map<String, Object> map = new HashMap<>();
map.put("sessionId", sessionId);
impl.getChatDetailById(map, new IndexContract.CallBack<List<ChatAiMsgEntity>>() {
@Override
public void success(List<ChatAiMsgEntity> list) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().getChatDetailSuccess(list);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 获取首页咨询会话模板
*/
public void getChatTemplateDatas() {
impl.getChatemplateDatas(new IndexContract.CallBack<List<ChatQuestionEntity>>() {
@Override
public void success(List<ChatQuestionEntity> list) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().getChatZixunSuccess(list);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 举报
* @param reason
*/
public void commitReport(String reason) {
Map<String, Object> map = new HashMap<>();
map.put("content", reason);
impl.commitReport(map, new IndexContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().commitReportSuccess(bean);
}
}
@Override
public void fail(String msg) {
if (IndexPresenter.this.getView() != null) {
IndexPresenter.this.getView().showError(msg);
}
}
});
}
}

View File

@@ -32,6 +32,10 @@ public class CustomRefreshHeader extends RelativeLayout implements RefreshHeader
private ImageView ivRefresh;
private ObjectAnimator rotateAnimator;
// 用于 onMoving 中的动态效果
private float mLastPercent = 0f;
// 记录当前缩放值,避免重复设置
private float mCurrentScale = 1f;
public CustomRefreshHeader(Context context) {
super(context);
@@ -47,11 +51,14 @@ public class CustomRefreshHeader extends RelativeLayout implements RefreshHeader
LayoutInflater.from(context).inflate(R.layout.view_refresh_header, this);
ivRefresh = findViewById(R.id.ivRefresh);
// 开启硬件加速,提升动画性能
setLayerType(LAYER_TYPE_HARDWARE, null);
// 初始化 ObjectAnimator
rotateAnimator = ObjectAnimator.ofFloat(ivRefresh, "rotation", 0f, 360f);
rotateAnimator.setDuration(1500);
rotateAnimator.setRepeatCount(ValueAnimator.INFINITE);
rotateAnimator.setInterpolator(new LinearInterpolator()); // 匀速旋转
rotateAnimator.setInterpolator(new LinearInterpolator());
}
@NonNull
@@ -72,16 +79,36 @@ public class CustomRefreshHeader extends RelativeLayout implements RefreshHeader
@Override
public int onFinish(@NonNull RefreshLayout layout, boolean success) {
if (rotateAnimator != null && rotateAnimator.isRunning()) {
// 为了平滑停止,先设置减速插值器,再 cancel 动画
rotateAnimator.setInterpolator(new DecelerateInterpolator());
postDelayed(() -> {
if (rotateAnimator != null) {
rotateAnimator.cancel();
rotateAnimator.setInterpolator(new LinearInterpolator()); // 恢复为匀速
rotateAnimator.setInterpolator(new LinearInterpolator());
}
}, 300); // 给一点缓冲时间
}, 300);
}
return 500; // 动画停止后延迟 500ms 收起 Header
// 动画过渡回正常大小
animateToNormalScale();
return 500;
}
/**
* 平滑动画过渡回正常大小
*/
private void animateToNormalScale() {
if (ivRefresh == null) return;
float startScale = mCurrentScale;
ValueAnimator scaleAnimator = ValueAnimator.ofFloat(startScale, 1f);
scaleAnimator.setDuration(300);
scaleAnimator.setInterpolator(new DecelerateInterpolator());
scaleAnimator.addUpdateListener(animation -> {
float value = (float) animation.getAnimatedValue();
ivRefresh.setScaleX(value);
ivRefresh.setScaleY(value);
mCurrentScale = value;
});
scaleAnimator.start();
}
// --- 必须实现的方法 ---
@@ -107,7 +134,24 @@ public class CustomRefreshHeader extends RelativeLayout implements RefreshHeader
@SuppressLint("RestrictedApi")
@Override
public void onMoving(boolean isDragging, float percent, int offset, int height, int maxDragHeight) {}
public void onMoving(boolean isDragging, float percent, int offset, int height, int maxDragHeight) {
// 只在拖动过程中处理,避免过度计算
if (percent != mLastPercent) {
mLastPercent = percent;
// 1. 动态缩放效果:从 0.5 放大到 1.2
// 使用 clamp 限制范围percent 0~1 -> scale 0.5~1.2
float targetScale = 0.5f + (0.7f * Math.min(percent, 1.0f));
if (Math.abs(targetScale - mCurrentScale) > 0.01f) {
mCurrentScale = targetScale;
ivRefresh.setScaleX(targetScale);
ivRefresh.setScaleY(targetScale);
}
// 2. 透明度渐变效果(可选)
// ivRefresh.setAlpha(Math.min(percent * 1.5f, 1.0f));
}
}
@SuppressLint("RestrictedApi")
@Override
@@ -125,6 +169,10 @@ public class CustomRefreshHeader extends RelativeLayout implements RefreshHeader
@SuppressLint("RestrictedApi")
@Override
public void onStateChanged(@NonNull RefreshLayout refreshLayout, @NonNull RefreshState oldState, @NonNull RefreshState newState) {
// 状态切换时平滑恢复
if (newState == RefreshState.PullDownCanceled) {
// 用户取消下拉,恢复到初始状态
animateToNormalScale();
}
}
}

View File

@@ -16,12 +16,12 @@ import androidx.annotation.NonNull;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.chat.mvp.IndexPresenter;
import com.ckkj.water.databinding.AddDeviceLayoutBinding;
import com.ckkj.water.device.mvp.DeviceContract;
import com.ckkj.water.device.mvp.DeviceImpl;
import com.ckkj.water.device.mvp.DevicePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.ThemeManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.gyf.immersionbar.ImmersionBar;
@@ -49,6 +49,7 @@ public class AddDeviceActivity extends BaseActivity<AddDeviceLayoutBinding, Devi
@Override
public void initData(Bundle savedInstanceState) {
super.initData(savedInstanceState);
ActivityManager.addActivity(this,getClass().getSimpleName() + "_" + ConstantUtil.ADD_DEVICE_FLAG);
ImmersionBar.with(this)
.statusBarColor(R.color.mainBackgroundColor) // 设置状态栏颜色
.statusBarDarkFont(ThemeManager.isAppThemeLight(mContext)) // 设置状态栏字体为黑色
@@ -186,4 +187,24 @@ public class AddDeviceActivity extends BaseActivity<AddDeviceLayoutBinding, Devi
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -8,6 +8,7 @@ import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.databinding.DeviceConnectLayoutBinding;
@@ -15,6 +16,7 @@ import com.ckkj.water.device.mvp.DeviceContract;
import com.ckkj.water.device.mvp.DeviceImpl;
import com.ckkj.water.device.mvp.DevicePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.gyf.immersionbar.ImmersionBar;
@@ -36,6 +38,7 @@ public class DeviceConnectActivity extends BaseActivity<DeviceConnectLayoutBindi
@Override
public void initData(Bundle savedInstanceState) {
super.initData(savedInstanceState);
ActivityManager.addActivity(this,getClass().getSimpleName() + "_" + ConstantUtil.ADD_DEVICE_FLAG);
ImmersionBar.with(this)
.statusBarColor(R.color.color_F9F9F9)
.statusBarDarkFont(true)
@@ -94,4 +97,24 @@ public class DeviceConnectActivity extends BaseActivity<DeviceConnectLayoutBindi
public void logOut(BaseBean bean) {
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -131,4 +131,24 @@ public class DeviceControlActivity extends BaseActivity<DeviceControlLayoutBindi
public void logOut(BaseBean bean) {
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -65,4 +65,24 @@ public class DeviceInfoActivity extends BaseActivity<DeviceInfoLayoutBinding, De
public void logOut(BaseBean bean) {
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -1,9 +1,11 @@
package com.ckkj.water.device;
import android.os.Bundle;
import android.os.Handler;
import android.text.TextUtils;
import android.view.View;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.databinding.SetDeviceNameLayoutBinding;
@@ -11,6 +13,7 @@ import com.ckkj.water.device.mvp.DeviceContract;
import com.ckkj.water.device.mvp.DeviceImpl;
import com.ckkj.water.device.mvp.DevicePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.gyf.immersionbar.ImmersionBar;
@@ -56,12 +59,33 @@ public class DeviceReNameActivity extends BaseActivity<SetDeviceNameLayoutBindin
ToastUtil.showShort(mContext,getString(R.string.input_device_name_hint));
return;
}
ToastUtil.showShort(mContext,"名称保存成功");
goTo(mContext,DeviceControlActivity.class,null);
// ToastUtil.showShort(mContext,"名称保存成功");
// goTo(mContext,DeviceControlActivity.class,null);
showLoadingDialog();
mPresenter.addDevice();
break;
}
}
/**
* 添加设备成功
* @param bean
*/
@Override
public void addDeviceSuccess(BaseBean bean) {
hideDialogLoading();
ToastUtil.showShort(mContext,"设备保存成功");
ActivityManager.removeActivityByTag(ConstantUtil.ADD_DEVICE_FLAG);
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
goTo(mContext,DeviceControlActivity.class,null);
finish();
}
},800);
}
@Override
public int getLayoutResId(Bundle savedInstanceState) {
return 0;
@@ -76,4 +100,20 @@ public class DeviceReNameActivity extends BaseActivity<SetDeviceNameLayoutBindin
public void logOut(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -140,4 +140,24 @@ public class DeviceSettingsActivity extends BaseActivity<DeviceSettingsLayoutBin
public void logOut(BaseBean bean) {
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
}

View File

@@ -24,6 +24,8 @@ import com.ckkj.water.device.mvp.DeviceContract;
import com.ckkj.water.device.mvp.DeviceImpl;
import com.ckkj.water.device.mvp.DevicePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.permission.PermissionActivity;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.ThemeManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.ckkj.water.utils.text.TextUtil;
@@ -55,7 +57,7 @@ public class SelectWifiActivity extends BaseActivity<DeviceResetWifiBinding, Dev
super.onCreate(savedInstanceState);
wifiManager = (WifiManager) getApplicationContext().getSystemService(Context.WIFI_SERVICE);
wifiScanReceiver = new WifiScanReceiver();
ActivityManager.addActivity(this,getClass().getSimpleName() + "_" + ConstantUtil.ADD_DEVICE_FLAG);
}
@Override
@@ -121,6 +123,14 @@ public class SelectWifiActivity extends BaseActivity<DeviceResetWifiBinding, Dev
break;
case R.id.tv_select_wifi:
String[] permission = {
Manifest.permission.ACCESS_FINE_LOCATION
};
boolean hasPermission = hasRecordPermission(permission);
if(!hasPermission){
goTo(mContext, PermissionActivity.class,null);
}else{
}
scanWifi();
break;
@@ -181,6 +191,26 @@ public class SelectWifiActivity extends BaseActivity<DeviceResetWifiBinding, Dev
}
}
@Override
public void addDeviceSuccess(BaseBean bean) {
}
@Override
public void editDeviceInfoSuccess(BaseBean bean) {
}
@Override
public void deleteDeviceSuccess(BaseBean bean) {
}
@Override
public void turnOnOffDeviceSuccess(BaseBean bean) {
}
private class WifiScanReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {

View File

@@ -1,6 +1,12 @@
package com.ckkj.water.device.mvp;
import com.ckkj.water.base.IView;
import com.ckkj.water.index.mvp.IndexContract;
import com.ckkj.water.network.BaseBean;
import org.json.JSONObject;
import java.util.Map;
public class DeviceContract {
public interface CallBack<T> {
@@ -8,8 +14,27 @@ public class DeviceContract {
void fail(String msg);
}
public interface DataModel{
//查询设备信息
void getDeviceInfomation(Map<String,String> map, IndexContract.CallBack callBack);
//添加设备
void addDevice(JSONObject json, IndexContract.CallBack callBack);
//修改设备信息
void editDeviceInfo(JSONObject json, IndexContract.CallBack callBack);
//删除设备信息
void deleteDevice(JSONObject json, IndexContract.CallBack callBack);
//手动开启关闭设备
void turnOnOffDevice(JSONObject json, IndexContract.CallBack callBack);
}
public interface DeviceView extends IView {
//添加设备成功g
void addDeviceSuccess(BaseBean bean);
void editDeviceInfoSuccess(BaseBean bean);
void deleteDeviceSuccess(BaseBean bean);
void turnOnOffDeviceSuccess(BaseBean bean);
}
}

View File

@@ -1,5 +1,78 @@
package com.ckkj.water.device.mvp;
import com.ckkj.water.index.mvp.IndexContract;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.network.NetWorkManager;
import org.json.JSONObject;
import java.util.Map;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
public class DeviceImpl implements DeviceContract.DataModel{
@Override
public void getDeviceInfomation(Map<String, String> map, IndexContract.CallBack callBack) {
}
/**
* 添加设备
* @param json
* @param callBack
*/
@Override
public void addDevice(JSONObject json, IndexContract.CallBack callBack) {
try {
NetWorkManager.getRequest().addDevice(NetWorkManager.getToken(), NetWorkManager.toRequestBody(json))
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean bean) {
if (bean.getCode() == 200) {
callBack.success(bean,0);
} else {
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public void editDeviceInfo(JSONObject json, IndexContract.CallBack callBack) {
}
@Override
public void deleteDevice(JSONObject json, IndexContract.CallBack callBack) {
}
@Override
public void turnOnOffDevice(JSONObject json, IndexContract.CallBack callBack) {
}
}

View File

@@ -1,6 +1,13 @@
package com.ckkj.water.device.mvp;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.index.mvp.IndexContract;
import com.ckkj.water.network.BaseBean;
import org.json.JSONException;
import org.json.JSONObject;
import java.util.Random;
public class DevicePresenter extends BasePresenter<DeviceContract.DeviceView> {
private DeviceImpl impl;
@@ -8,4 +15,33 @@ public class DevicePresenter extends BasePresenter<DeviceContract.DeviceView> {
public DevicePresenter(DeviceImpl impl) {
this.impl = impl;
}
public void addDevice() {
try {
JSONObject json = new JSONObject();
json.put("deviceNo",System.currentTimeMillis() + "");
json.put("deviceName",new Random().nextInt(99) + "号设备");
json.put("wifiName","橙空科技WiFi");
json.put("wifiPassword","12321212");
json.put("deviceEm","213123123123");
json.put("deviceSn","sdfsd32423gdfgdf3");
json.put("fwVer","fwVer-56565644");
json.put("macAddress","2E:8H:00:KK:N7");
impl.addDevice(json, new IndexContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean,int total) {
if(DevicePresenter.this.getView() != null){
DevicePresenter.this.getView().addDeviceSuccess(bean);
}
}
@Override
public void fail(String msg) {
}
});
} catch (JSONException e) {
throw new RuntimeException(e);
}
}
}

View File

@@ -1,52 +0,0 @@
package com.ckkj.water.fate.adapter;
import android.content.Context;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.utils.color.FateDataUtil;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/24
* @description TODO: 描述该类的作用
*/
public class FateHistoryAdapter extends BaseQuickAdapter<FateHistoryEntity.HistoryList, BaseViewHolder> {
private Context mContext;
public FateHistoryAdapter(Context context,int layoutResId, @Nullable List<FateHistoryEntity.HistoryList> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder holder, FateHistoryEntity.HistoryList item) {
holder.setText(R.id.tv_date,item.getRecordDate());
holder.setText(R.id.tv_week,item.getDayOfWeek());
if(item.isToday()){
holder.setVisible(R.id.tv_today,true);
}else{
holder.setVisible(R.id.tv_today,false);
}
holder.setText(R.id.tv_name,item.getName());
holder.setText(R.id.tv_location,item.getCurrentPlace());
holder.setText(R.id.tv_weather,item.getWeatherCondition());
holder.setText(R.id.tv_star,item.getConstellation());
holder.setText(R.id.tv_score,item.getOverallScore() + "");
holder.setText(R.id.tv_syy_score,item.getCareerScore() + "");
holder.setText(R.id.tv_gqy_score,item.getLoveScore() + "");
holder.setText(R.id.tv_jky_score,item.getHealthScore() + "");
holder.setText(R.id.tv_cfy_score,item.getWealthScore() + "");
holder.setTextColor(R.id.tv_score, FateDataUtil.getScoreColor(item.getOverallScore()));
holder.setTextColor(R.id.tv_syy_score, FateDataUtil.getScoreColor(item.getCareerScore()));
holder.setTextColor(R.id.tv_gqy_score, FateDataUtil.getScoreColor(item.getLoveScore()));
holder.setTextColor(R.id.tv_jky_score, FateDataUtil.getScoreColor(item.getHealthScore()));
holder.setTextColor(R.id.tv_cfy_score, FateDataUtil.getScoreColor(item.getWealthScore()));
}
}

View File

@@ -1,50 +0,0 @@
package com.ckkj.water.fate.adapter;
import android.content.Context;
import androidx.annotation.Nullable;
import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.BaseViewHolder;
import com.ckkj.water.R;
import com.ckkj.water.fate.entity.CityDataEntity;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/18
* @description TODO: 描述该类的作用
*/
public class SelectCityAdapter extends BaseQuickAdapter<CityDataEntity, BaseViewHolder> {
private Context mContext;
private int mSelPos = -1;
public SelectCityAdapter(Context context,int layoutResId, @Nullable List<CityDataEntity> data) {
super(layoutResId, data);
this.mContext = context;
}
@Override
protected void convert(BaseViewHolder helper, CityDataEntity item) {
helper.setText(R.id.tv_city_name,item.getCityName());
if(mSelPos == helper.getLayoutPosition()){
helper.setVisible(R.id.img_select,true);
}else{
helper.setVisible(R.id.img_select,false);
}
}
public void setSelPos(int pos){
this.mSelPos = pos;
notifyDataSetChanged();
}
public int getmSelPos() {
return mSelPos;
}
public void setmSelPos(int mSelPos) {
this.mSelPos = mSelPos;
}
}

View File

@@ -1,203 +0,0 @@
package com.ckkj.water.fate.entity;
import java.io.Serializable;
/**
* @author fengxiaoyang
* @date 2025/7/18
* @description TODO: 描述该类的作用
*/
public class CityDataEntity implements Serializable {
private int id;
private String cityCode;
private String cityName;
private String cityNameEn;
private String provinceCode;
private String provinceName;
private int cityLevel;
private String cityType;
private double longitude;
private double latitude;
private String population;
private String area;
private String gdp;
private String zipCode;
private String phoneCode;
private int isCapital;
private int isActive;
private int sortOrder;
private String remark;
private String createdTime;
private String updatedTime;
private String capitalCity;
public String getCapitalCity() {
return capitalCity;
}
public void setCapitalCity(String capitalCity) {
this.capitalCity = capitalCity;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getCityCode() {
return cityCode;
}
public void setCityCode(String cityCode) {
this.cityCode = cityCode;
}
public String getCityName() {
return cityName;
}
public void setCityName(String cityName) {
this.cityName = cityName;
}
public String getCityNameEn() {
return cityNameEn;
}
public void setCityNameEn(String cityNameEn) {
this.cityNameEn = cityNameEn;
}
public String getProvinceCode() {
return provinceCode;
}
public void setProvinceCode(String provinceCode) {
this.provinceCode = provinceCode;
}
public String getProvinceName() {
return provinceName;
}
public void setProvinceName(String provinceName) {
this.provinceName = provinceName;
}
public int getCityLevel() {
return cityLevel;
}
public void setCityLevel(int cityLevel) {
this.cityLevel = cityLevel;
}
public String getCityType() {
return cityType;
}
public void setCityType(String cityType) {
this.cityType = cityType;
}
public double getLongitude() {
return longitude;
}
public void setLongitude(double longitude) {
this.longitude = longitude;
}
public double getLatitude() {
return latitude;
}
public void setLatitude(double latitude) {
this.latitude = latitude;
}
public String getPopulation() {
return population;
}
public void setPopulation(String population) {
this.population = population;
}
public String getArea() {
return area;
}
public void setArea(String area) {
this.area = area;
}
public String getGdp() {
return gdp;
}
public void setGdp(String gdp) {
this.gdp = gdp;
}
public String getZipCode() {
return zipCode;
}
public void setZipCode(String zipCode) {
this.zipCode = zipCode;
}
public String getPhoneCode() {
return phoneCode;
}
public void setPhoneCode(String phoneCode) {
this.phoneCode = phoneCode;
}
public int getIsCapital() {
return isCapital;
}
public void setIsCapital(int isCapital) {
this.isCapital = isCapital;
}
public int getIsActive() {
return isActive;
}
public void setIsActive(int isActive) {
this.isActive = isActive;
}
public int getSortOrder() {
return sortOrder;
}
public void setSortOrder(int sortOrder) {
this.sortOrder = sortOrder;
}
public String getRemark() {
return remark;
}
public void setRemark(String remark) {
this.remark = remark;
}
public void setCreatedTime(String createdTime) {
this.createdTime = createdTime;
}
public void setUpdatedTime(String updatedTime) {
this.updatedTime = updatedTime;
}
}

View File

@@ -1,139 +0,0 @@
package com.ckkj.water.fate.entity;
import java.io.Serializable;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/25
* @description TODO: 描述该类的作用
*/
public class FateHistoryEntity {
private List<HistoryList> list;
private int total;
public void setList(List<HistoryList> list) {
this.list = list;
}
public List<HistoryList> getList() {
return list;
}
public void setTotal(int total) {
this.total = total;
}
public int getTotal() {
return total;
}
public static class HistoryList implements Serializable{
private String recordDate;
private String dayOfWeek;
private String name;
private String currentPlace;
private String weatherCondition;
private String constellation;
private int overallScore;
private int careerScore;
private int loveScore;
private int healthScore;
private int wealthScore;
private boolean isToday;
public String getRecordDate() {
return recordDate;
}
public void setRecordDate(String recordDate) {
this.recordDate = recordDate;
}
public String getDayOfWeek() {
return dayOfWeek;
}
public void setDayOfWeek(String dayOfWeek) {
this.dayOfWeek = dayOfWeek;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getCurrentPlace() {
return currentPlace;
}
public void setCurrentPlace(String currentPlace) {
this.currentPlace = currentPlace;
}
public String getWeatherCondition() {
return weatherCondition;
}
public void setWeatherCondition(String weatherCondition) {
this.weatherCondition = weatherCondition;
}
public String getConstellation() {
return constellation;
}
public void setConstellation(String constellation) {
this.constellation = constellation;
}
public int getOverallScore() {
return overallScore;
}
public void setOverallScore(int overallScore) {
this.overallScore = overallScore;
}
public int getCareerScore() {
return careerScore;
}
public void setCareerScore(int careerScore) {
this.careerScore = careerScore;
}
public int getLoveScore() {
return loveScore;
}
public void setLoveScore(int loveScore) {
this.loveScore = loveScore;
}
public int getHealthScore() {
return healthScore;
}
public void setHealthScore(int healthScore) {
this.healthScore = healthScore;
}
public int getWealthScore() {
return wealthScore;
}
public void setWealthScore(int wealthScore) {
this.wealthScore = wealthScore;
}
public boolean isToday() {
return isToday;
}
public void setToday(boolean today) {
isToday = today;
}
}
}

View File

@@ -1,66 +0,0 @@
package com.ckkj.water.fate.entity;
import java.io.Serializable;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/16
* @description TODO: 描述该类的作用
*/
public class LunarYearEntity implements Serializable {
public String year; // 年份
public List<LunarMonth> month; // 月份列表
// Gson需要无参构造
public LunarYearEntity() {}
public String getYear() {
return year;
}
public void setYear(String year) {
this.year = year;
}
public List<LunarMonth> getMonth() {
return month;
}
public void setMonth(List<LunarMonth> month) {
this.month = month;
}
public static class LunarMonth implements Serializable{
public String name; // 月份数字(字符串形式)
public int isRun; // 是否闰月0=否1=是)
public int isAllDay; // 是否包含三十0=29天1=30天
// Gson需要无参构造
public LunarMonth() {}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getIsRun() {
return isRun;
}
public void setIsRun(int isRun) {
this.isRun = isRun;
}
public int getIsAllDay() {
return isAllDay;
}
public void setIsAllDay(int isAllDay) {
this.isAllDay = isAllDay;
}
}
}

View File

@@ -1,526 +0,0 @@
package com.ckkj.water.fate.entity;
import com.ckkj.water.base.entity.UserInfoEntity;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/21
* @description TODO: 描述该类的作用
*/
public class TodayFateEntity implements Serializable {
private FortuneAnalysis fortuneAnalysis;
private UserInfoEntity userInfo;
private TodayInfo todayInfo;
private String weatherCondition;
private String weatherTemperature;
private int todayVisitCount;
private int totalVisitDays;
public void setFortuneAnalysis(FortuneAnalysis fortuneAnalysis) {
this.fortuneAnalysis = fortuneAnalysis;
}
public FortuneAnalysis getFortuneAnalysis() {
return fortuneAnalysis;
}
public void setUserInfo(UserInfoEntity userInfo) {
this.userInfo = userInfo;
}
public UserInfoEntity getUserInfo() {
return userInfo;
}
public void setTodayInfo(TodayInfo todayInfo) {
this.todayInfo = todayInfo;
}
public TodayInfo getTodayInfo() {
return todayInfo;
}
public void setWeatherCondition(String weatherCondition) {
this.weatherCondition = weatherCondition;
}
public String getWeatherCondition() {
return weatherCondition;
}
public void setWeatherTemperature(String weatherTemperature) {
this.weatherTemperature = weatherTemperature;
}
public String getWeatherTemperature() {
return weatherTemperature;
}
public void setTodayVisitCount(int todayVisitCount) {
this.todayVisitCount = todayVisitCount;
}
public int getTodayVisitCount() {
return todayVisitCount;
}
public void setTotalVisitDays(int totalVisitDays) {
this.totalVisitDays = totalVisitDays;
}
public int getTotalVisitDays() {
return totalVisitDays;
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class TodayInfo implements Serializable{
private Date date;
private String weekDay;
private int year;
private int month;
private int day;
public void setDate(Date date) {
this.date = date;
}
public Date getDate() {
return date;
}
public void setWeekDay(String weekDay) {
this.weekDay = weekDay;
}
public String getWeekDay() {
return weekDay;
}
public void setYear(int year) {
this.year = year;
}
public int getYear() {
return year;
}
public void setMonth(int month) {
this.month = month;
}
public int getMonth() {
return month;
}
public void setDay(int day) {
this.day = day;
}
public int getDay() {
return day;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class FortuneAnalysis implements Serializable{
private int overallScore;
private String overallDescription;
private String destiny;
private String todayGanzhi;
private BaziAnalysis baziAnalysis;
private Weather weather;
private AstrologyInfluence astrologyInfluence;
private LuckyInfo luckyInfo;
private int careerScore;
private String careerDescription;
private int loveScore;
private String loveDescription;
private int healthScore;
private String healthDescription;
private int wealthScore;
private String wealthDescription;
private Suggestions suggestions;
private String fiveElementsAnalysis;
public void setOverallScore(int overallScore) {
this.overallScore = overallScore;
}
public int getOverallScore() {
return overallScore;
}
public void setOverallDescription(String overallDescription) {
this.overallDescription = overallDescription;
}
public String getOverallDescription() {
return overallDescription;
}
public void setDestiny(String destiny) {
this.destiny = destiny;
}
public String getDestiny() {
return destiny;
}
public void setTodayGanzhi(String todayGanzhi) {
this.todayGanzhi = todayGanzhi;
}
public String getTodayGanzhi() {
return todayGanzhi;
}
public void setBaziAnalysis(BaziAnalysis baziAnalysis) {
this.baziAnalysis = baziAnalysis;
}
public BaziAnalysis getBaziAnalysis() {
return baziAnalysis;
}
public void setWeather(Weather weather) {
this.weather = weather;
}
public Weather getWeather() {
return weather;
}
public void setAstrologyInfluence(AstrologyInfluence astrologyInfluence) {
this.astrologyInfluence = astrologyInfluence;
}
public AstrologyInfluence getAstrologyInfluence() {
return astrologyInfluence;
}
public void setLuckyInfo(LuckyInfo luckyInfo) {
this.luckyInfo = luckyInfo;
}
public LuckyInfo getLuckyInfo() {
return luckyInfo;
}
public void setCareerScore(int careerScore) {
this.careerScore = careerScore;
}
public int getCareerScore() {
return careerScore;
}
public void setCareerDescription(String careerDescription) {
this.careerDescription = careerDescription;
}
public String getCareerDescription() {
return careerDescription;
}
public void setLoveScore(int loveScore) {
this.loveScore = loveScore;
}
public int getLoveScore() {
return loveScore;
}
public void setLoveDescription(String loveDescription) {
this.loveDescription = loveDescription;
}
public String getLoveDescription() {
return loveDescription;
}
public void setHealthScore(int healthScore) {
this.healthScore = healthScore;
}
public int getHealthScore() {
return healthScore;
}
public void setHealthDescription(String healthDescription) {
this.healthDescription = healthDescription;
}
public String getHealthDescription() {
return healthDescription;
}
public void setWealthScore(int wealthScore) {
this.wealthScore = wealthScore;
}
public int getWealthScore() {
return wealthScore;
}
public void setWealthDescription(String wealthDescription) {
this.wealthDescription = wealthDescription;
}
public String getWealthDescription() {
return wealthDescription;
}
public void setSuggestions(Suggestions suggestions) {
this.suggestions = suggestions;
}
public Suggestions getSuggestions() {
return suggestions;
}
public void setFiveElementsAnalysis(String fiveElementsAnalysis) {
this.fiveElementsAnalysis = fiveElementsAnalysis;
}
public String getFiveElementsAnalysis() {
return fiveElementsAnalysis;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class Suggestions implements Serializable{
private String positive;
private String negative;
public void setPositive(String positive) {
this.positive = positive;
}
public String getPositive() {
return positive;
}
public void setNegative(String negative) {
this.negative = negative;
}
public String getNegative() {
return negative;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class LuckyInfo implements Serializable{
private String[] numbers;
private String color;
private String direction;
private List<LuckyTimes> luckyTimes;
private String flower;
private String food;
public String[] getNumbers() {
return numbers;
}
public void setNumbers(String[] numbers) {
this.numbers = numbers;
}
public void setColor(String color) {
this.color = color;
}
public String getColor() {
return color;
}
public void setDirection(String direction) {
this.direction = direction;
}
public String getDirection() {
return direction;
}
public void setLuckyTimes(List<LuckyTimes> luckyTimes) {
this.luckyTimes = luckyTimes;
}
public List<LuckyTimes> getLuckyTimes() {
return luckyTimes;
}
public void setFlower(String flower) {
this.flower = flower;
}
public String getFlower() {
return flower;
}
public void setFood(String food) {
this.food = food;
}
public String getFood() {
return food;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class LuckyTimes implements Serializable{
private String time;
private String description;
public void setTime(String time) {
this.time = time;
}
public String getTime() {
return time;
}
public void setDescription(String description) {
this.description = description;
}
public String getDescription() {
return description;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class AstrologyInfluence implements Serializable{
private String constellation;
private String value;
private String description;
public void setConstellation(String constellation) {
this.constellation = constellation;
}
public String getConstellation() {
return constellation;
}
public void setValue(String value) {
this.value = value;
}
public String getValue() {
return value;
}
public void setDescription(String description) {
this.description = description;
}
public String getDescription() {
return description;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class Weather implements Serializable{
private String condition;
private String temperature;
public void setCondition(String condition) {
this.condition = condition;
}
public String getCondition() {
return condition;
}
public void setTemperature(String temperature) {
this.temperature = temperature;
}
public String getTemperature() {
return temperature;
}
}
/**
* Copyright 2025 bejson.com
*/
/**
* Auto-generated: 2025-07-21 17:23:17
*
* @author bejson.com (i@bejson.com)
* @website http://www.bejson.com/java2pojo/
*/
public static class BaziAnalysis implements Serializable{
private String nianzhu;
private String yuezhu;
private String rizhu;
private String shizhu;
private String todayInfluence;
public void setNianzhu(String nianzhu) {
this.nianzhu = nianzhu;
}
public String getNianzhu() {
return nianzhu;
}
public void setYuezhu(String yuezhu) {
this.yuezhu = yuezhu;
}
public String getYuezhu() {
return yuezhu;
}
public void setRizhu(String rizhu) {
this.rizhu = rizhu;
}
public String getRizhu() {
return rizhu;
}
public void setShizhu(String shizhu) {
this.shizhu = shizhu;
}
public String getShizhu() {
return shizhu;
}
public void setTodayInfluence(String todayInfluence) {
this.todayInfluence = todayInfluence;
}
public String getTodayInfluence() {
return todayInfluence;
}
}
}

View File

@@ -1,56 +0,0 @@
package com.ckkj.water.fate.mvp;
import com.ckkj.water.base.IView;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.fate.entity.TodayFateEntity;
import com.ckkj.water.network.BaseBean;
import org.json.JSONObject;
import java.util.List;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/15
* @description TODO: 描述该类的作用
*/
public class FateContract {
public interface CallBack<T> {
void success(T msg);
void fail(String msg);
}
public interface DataModel{
//查询所有城市
void getAllCityDatas(Map<String,Object> map, CallBack callBack);
//保存用户生日信息
void saveUserBirthInfo(JSONObject json, CallBack callBack);
//用户修改生日信息
void saveUserEditBirthInfo(JSONObject json, CallBack callBack);
//查询用户今日运势
void getUserTodayFateDatas(Map<String,Object> map, CallBack callBack);
//查询历史运势
void getUserFateHistory(Map<String,Object> map, CallBack callBack);
}
public interface FateView extends IView{
//查询所有城市成功
void getAllCitySuccess(List<CityDataEntity> list);
//获取今日运势成功
void getUserTodayFateDataSuccess(TodayFateEntity entity);
//获取历史运势成功
void getFateHistorySuccess(FateHistoryEntity entity);
//用户保存生辰八字成功
void userSaveBirthInfoSuccess(TodayFateEntity bean);
//用户信息
void getUserInfoSuccess(MineUserInfoBean bean);
//提交举报反馈成功
void commitReportSuccess(BaseBean bean);
}
}

View File

@@ -1,232 +0,0 @@
package com.ckkj.water.fate.mvp;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.fate.entity.TodayFateEntity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.network.NetWorkManager;
import org.json.JSONObject;
import java.util.List;
import java.util.Map;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
/**
* @author fengxiaoyang
* @date 2025/7/15
* @description TODO: 描述该类的作用
*/
public class FateImpl implements FateContract.DataModel{
/**
* 所有城市
* @param map
* @param callBack
*/
@Override
public void getAllCityDatas(Map<String, Object> map, FateContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getCityDatas(NetWorkManager.getToken(),map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<List<CityDataEntity>>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<List<CityDataEntity>> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 保存用户生辰信息
* @param json
* @param callBack
*/
@Override
public void saveUserBirthInfo(JSONObject json, FateContract.CallBack callBack) {
try {
NetWorkManager.getRequest().saveUserBirthInfo(NetWorkManager.getToken(),NetWorkManager.toRequestBody(json))
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean bean) {
if(bean.getCode() == 200){
callBack.success(bean);
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 用户修改生辰八字
* @param json
* @param callBack
*/
@Override
public void saveUserEditBirthInfo(JSONObject json, FateContract.CallBack callBack) {
try {
NetWorkManager.getRequest().saveUserEditBirthInfo(NetWorkManager.getToken(),NetWorkManager.toRequestBody(json))
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<TodayFateEntity>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<TodayFateEntity> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 获取今日运势
* @param map
* @param callBack
*/
@Override
public void getUserTodayFateDatas(Map<String, Object> map, FateContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getUserTodayFateDatas(NetWorkManager.getToken())
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<TodayFateEntity>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<TodayFateEntity> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 获取历史数据
* @param map
* @param callBack
*/
@Override
public void getUserFateHistory(Map<String, Object> map, FateContract.CallBack callBack) {
try {
NetWorkManager.getRequest().getUserFateHistory(NetWorkManager.getToken())
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<FateHistoryEntity>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<FateHistoryEntity> bean) {
if(bean.getCode() == 200){
callBack.success(bean.getData());
}else{
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
}

View File

@@ -1,191 +0,0 @@
package com.ckkj.water.fate.mvp;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.chat.mvp.IndexContract;
import com.ckkj.water.chat.mvp.IndexImpl;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.fate.entity.TodayFateEntity;
import com.ckkj.water.login.mvp.LoginContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.network.BaseBean;
import org.json.JSONObject;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/15
* @description TODO: 描述该类的作用
*/
public class FatePresenter extends BasePresenter<FateContract.FateView> {
private FateImpl impl;
public FatePresenter(FateImpl impl) {
this.impl = impl;
}
/**
* 获取城市列表
*/
public void getCityDatas() {
Map<String, Object> map = new HashMap<>();
impl.getAllCityDatas(map, new FateContract.CallBack<List<CityDataEntity>>() {
@Override
public void success(List<CityDataEntity> list) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().getAllCitySuccess(list);
}
}
@Override
public void fail(String msg) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 保存用户生辰
* @param json
*/
public void saveUserBirthInfo(JSONObject json) {
impl.saveUserBirthInfo(json, new FateContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().userSaveBirthInfoSuccess(null);
}
}
@Override
public void fail(String msg) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 获取今日运势
*/
public void getTodayFateDatas() {
impl.getUserTodayFateDatas(new HashMap<>(), new FateContract.CallBack<TodayFateEntity>() {
@Override
public void success(TodayFateEntity bean) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().getUserTodayFateDataSuccess(bean);
}
}
@Override
public void fail(String msg) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 获取历史运势
* @param page
*/
public void getHistoryDatas(int page) {
Map<String, Object> map = new HashMap<>();
map.put("pageNum", page);
map.put("pageSize", 10);
impl.getUserFateHistory(map, new FateContract.CallBack<FateHistoryEntity>() {
@Override
public void success(FateHistoryEntity entity) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().getFateHistorySuccess(entity);
}
}
@Override
public void fail(String msg) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 用户修改的生辰八字保存
* @param json
*/
public void saveEditBirthInfo(JSONObject json) {
impl.saveUserEditBirthInfo(json, new FateContract.CallBack<TodayFateEntity>() {
@Override
public void success(TodayFateEntity bean) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().userSaveBirthInfoSuccess(bean);
}
}
@Override
public void fail(String msg) {
if(FatePresenter.this.getView() != null){
FatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 获取个人信息
*/
public void getUserInfo() {
Map<String,Object> map = new HashMap<>();
// new MineImpl().getUserInfo(map, new LoginContract.CallBack<MineUserInfoBean>() {
// @Override
// public void success(MineUserInfoBean bean) {
// if( FatePresenter.this.getView() != null){
// FatePresenter.this.getView().getUserInfoSuccess(bean);
// }
// }
//
// @Override
// public void fail(String msg) {
// if( FatePresenter.this.getView() != null){
// FatePresenter.this.getView().showError(msg);
// }
// }
// });
}
/**
* 举报
* @param reason
*/
public void commitReport(String reason) {
Map<String, Object> map = new HashMap<>();
map.put("content", reason);
new IndexImpl().commitReport(map, new IndexContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if (FatePresenter.this.getView() != null) {
FatePresenter.this.getView().commitReportSuccess(bean);
}
}
@Override
public void fail(String msg) {
if (FatePresenter.this.getView() != null) {
FatePresenter.this.getView().showError(msg);
}
}
});
}
}

View File

@@ -1,75 +0,0 @@
package com.ckkj.water.fate.util;
import android.content.Context;
import androidx.annotation.Nullable;
import org.json.JSONArray;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
public class LunarDateLoader {
// 缓存静态变量
private static JSONArray cachedLunarJsonArray = null;
/**
* 初始化缓存(异步调用,建议在 Application 中调用)
*/
public static void preloadLunarJson(final Context context) {
if (cachedLunarJsonArray != null) return; // 已加载过则跳过
new Thread(() -> {
try {
InputStream inputStream = context.getAssets().open("lunar_1899_2099.json");
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int len;
while ((len = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, len);
}
inputStream.close();
String jsonStr = outputStream.toString("UTF-8");
cachedLunarJsonArray = new JSONArray(jsonStr);
} catch (Exception e) {
e.printStackTrace();
}
}).start();
}
/**
* 获取缓存的农历 JSON 数据(同步获取)
* 可在页面中直接调用
*/
@Nullable
public static JSONArray getCachedLunarJson() {
return cachedLunarJsonArray;
}
/**
* 同步加载(兜底)
*/
@Nullable
public static JSONArray loadJsonFromAssets(Context context, String fileName) {
try {
InputStream inputStream = context.getAssets().open(fileName);
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int len;
while ((len = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, len);
}
inputStream.close();
String jsonStr = outputStream.toString("UTF-8");
return new JSONArray(jsonStr);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
}

View File

@@ -1,96 +0,0 @@
package com.ckkj.water.fate.util;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.ckkj.water.fate.entity.LunarYearEntity;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.List;
public class LunarDatePicker {
private List<LunarYearEntity> lunarYears; // 所有年份数据
private List<LunarYearEntity.LunarMonth> currentYearMonths; // 当前选中年的月份数据
// 月份名称映射(数字->中文)
private static final String[] MONTH_NAMES = {
"正月", "二月", "三月", "四月", "五月", "六月",
"七月", "八月", "九月", "十月", "冬月", "腊月"
};
// 日期名称列表(初一到三十)
private static final String[] DAY_NAMES = {
"初一", "初二", "初三", "初四", "初五", "初六", "初七", "初八", "初九", "初十",
"十一", "十二", "十三", "十四", "十五", "十六", "十七", "十八", "十九", "二十",
"廿一", "廿二", "廿三", "廿四", "廿五", "廿六", "廿七", "廿八", "廿九", "三十"
};
public LunarDatePicker(String jsonData) {
// 解析JSON数据
parseLunarData(jsonData);
}
// 解析JSON数据
private void parseLunarData(String jsonData) {
Gson gson = new Gson();
Type type = new TypeToken<List<LunarYearEntity>>(){}.getType();
lunarYears = gson.fromJson(jsonData, type);
}
// 获取年份列表用于年的WheelView
public List<String> getYearList() {
List<String> years = new ArrayList<>();
for (LunarYearEntity year : lunarYears) {
years.add(year.getYear());
}
return years;
}
// 根据选中的年份索引获取月份列表用于月的WheelView
public List<String> getMonthList(int yearIndex) {
if (yearIndex < 0 || yearIndex >= lunarYears.size()) {
return new ArrayList<>();
}
LunarYearEntity selectedYear = lunarYears.get(yearIndex);
currentYearMonths = selectedYear.getMonth(); // 保存当前年的月份数据
List<String> monthList = new ArrayList<>();
for (LunarYearEntity.LunarMonth month : selectedYear.month) {
int monthNum = Integer.parseInt(month.name);
String monthName = MONTH_NAMES[monthNum - 1]; // 数组索引从0开始
// 处理闰月
if (month.isRun == 1) {
monthName = "" + monthName;
}
monthList.add(monthName);
}
return monthList;
}
// 根据选中的月份索引获取日期列表用于日的WheelView
public List<String> getDayList(int monthIndex) {
if (currentYearMonths == null || monthIndex < 0 || monthIndex >= currentYearMonths.size()) {
return new ArrayList<>();
}
LunarYearEntity.LunarMonth selectedMonth = currentYearMonths.get(monthIndex);
int days = selectedMonth.isAllDay == 1 ? 30 : 29; // 确定天数
List<String> dayList = new ArrayList<>();
for (int i = 0; i < days; i++) {
dayList.add(DAY_NAMES[i]);
}
return dayList;
}
// 获取选中的完整日期(年、月、日索引)
public String getSelectedDate(int yearIndex, int monthIndex, int dayIndex) {
String year = lunarYears.get(yearIndex).year + "";
String month = getMonthList(yearIndex).get(monthIndex);
String day = getDayList(monthIndex).get(dayIndex);
return year + month + day;
}
}

View File

@@ -1,758 +0,0 @@
package com.ckkj.water.fate.view;
import static android.app.Activity.RESULT_OK;
import static com.qweather.sdk.QWeather.instance;
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.AnimatorSet;
import android.animation.ObjectAnimator;
import android.animation.ValueAnimator;
import android.content.Intent;
import android.graphics.Rect;
import android.os.Bundle;
import android.text.TextUtils;
import android.util.Log;
import android.view.View;
import android.view.animation.AccelerateDecelerateInterpolator;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.amap.api.services.core.AMapException;
import com.amap.api.services.core.LatLonPoint;
import com.amap.api.services.geocoder.GeocodeAddress;
import com.amap.api.services.geocoder.GeocodeQuery;
import com.amap.api.services.geocoder.GeocodeResult;
import com.amap.api.services.geocoder.GeocodeSearch;
import com.google.android.material.progressindicator.CircularProgressIndicator;
import com.google.android.material.progressindicator.LinearProgressIndicator;
import com.ckkj.water.AppConfig;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.EventMessage;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.custom.view.CustomRefreshHeader;
import com.ckkj.water.databinding.FateLayoutBinding;
import com.ckkj.water.dialog.ContentReportDialog;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.fate.entity.TodayFateEntity;
import com.ckkj.water.fate.mvp.FateContract;
import com.ckkj.water.fate.mvp.FateImpl;
import com.ckkj.water.fate.mvp.FatePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.WeatherIconUtil;
import com.ckkj.water.utils.click.ClickUtil;
import com.ckkj.water.utils.color.FateDataUtil;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.number.NumberDecimalFilter;
import com.ckkj.water.utils.show.ToastUtil;
import com.ckkj.water.utils.time.ZYTimeUtils;
import com.qweather.sdk.Callback;
import com.qweather.sdk.JWTGenerator;
import com.qweather.sdk.QWeather;
import com.qweather.sdk.basic.Lang;
import com.qweather.sdk.basic.Unit;
import com.qweather.sdk.parameter.weather.WeatherParameter;
import com.qweather.sdk.response.error.ErrorResponse;
import com.qweather.sdk.response.geo.GeoPoiResponse;
import com.qweather.sdk.response.weather.WeatherNowResponse;
import com.scwang.smart.refresh.layout.api.RefreshHeader;
import java.util.List;
import java.util.Calendar;
import android.os.Handler;
import android.os.Looper;
import de.greenrobot.event.Subscribe;
import de.greenrobot.event.ThreadMode;
import pub.devrel.easypermissions.EasyPermissions;
/**
* @author fengxiaoyang
* @date 2025/7/7
* @description TODO: 描述该类的作用
*/
public class FateFragment extends BaseFragment<FateLayoutBinding, FatePresenter>
implements FateContract.FateView , EasyPermissions.PermissionCallbacks{
private TodayFateEntity mTodayEntity;
// 添加动画执行标志位
private boolean isCareerAnimPlayed = false;
private boolean isLoveAnimPlayed = false;
private boolean isHealthAnimPlayed = false;
private boolean isWealthAnimPlayed = false;
private boolean isOverallAnimPlayed = false;
//是否已经加载过
private boolean hasLoaded = false;
// 添加Toast相关的成员变量
private Handler toastHandler = new Handler(Looper.getMainLooper());
private Runnable toastRunnable;
private boolean isToastTaskRunning = false;
private int currentToastIndex = 0;
private String[] toastMessages = {
"正在查看您的今日能量值",
"让我帮你看看今天的星座运势",
"正在生成您的幸运元素",
"别着急,让我来想想今天的事宜"
};
@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
super.setUserVisibleHint(isVisibleToUser);
}
@Override
protected void onResumeInitData() {
super.onResumeInitData();
// 确保在Fragment可见时检查动画
viewBinding.getRoot().postDelayed(() -> {
checkAndAnimateProgressBars();
}, 300);
if(AppConfig.USER_LOGIN){
mPresenter.getUserInfo();
}else{
viewBinding.llInput.setVisibility(View.VISIBLE);
}
if (getUserVisibleHint() && !hasLoaded) {
if(AppConfig.USER_LOGIN){
showLoadingDialog();
// 调用接口并启动延迟Toast任务
startFateDataRequest();
hasLoaded = true;
}
}
}
@Override
public void initData(Bundle state) {
//请求定位权限
// String permission = Manifest.permission.ACCESS_FINE_LOCATION;
// if(!hasRecordPermission(permission)){
// getPermissionRequst(permission,"定位权限申请","叮叮车需要您的授权,获取您当前所在的城市",REQUEST_EVENT_CODE_10002);
// }else{
// AMapLocationClient.updatePrivacyAgree(mContext, true);
// initLocationInfo();
// }
// 设置当前日期和星期几
setCurrentDate();
//和风天气 init
try {
JWTGenerator jwt = new JWTGenerator(
"-----BEGIN PRIVATE KEY-----\n" +
"MC4CAQAwBQYDK2VwBCIEIFH+qB/0rER1mEpgAIwpBiAShW9pnSAj8OipGY/eFLRb\n" +
"-----END PRIVATE KEY-----",//密钥
"2A89MF5WVU",//项目 ID
"K5PU3M4P2A");//凭据 ID
instance = QWeather.getInstance(mContext, "mr3597qqpv.re.qweatherapi.com")
.setTokenGenerator(jwt)
.setLogEnable(true);
Log.d(TAG,"和风天气初始化成功");
} catch (Throwable e) {
Log.d(TAG,"和风天气初始化异常");
throw new RuntimeException(e);
}
// 添加视图可见性监听
setupProgressAnimations();
ClickUtil.addClickPart(viewBinding.imgHistory,60);
// 设置自定义刷新头
RefreshHeader header = new CustomRefreshHeader(mContext);
viewBinding.refresh.setRefreshHeader(header);
// viewBinding.refresh.setRefreshFooter(new ClassicsFooter(mContext));
viewBinding.refresh.setOnRefreshListener(layout -> {
if(AppConfig.USER_LOGIN){
showLoadingDialog();
// 调用接口并启动延迟Toast任务
startFateDataRequest();
hasLoaded = true;
}
});
}
/**
* 设置当前日期和星期几
*/
private void setCurrentDate() {
Calendar calendar = Calendar.getInstance();
int month = calendar.get(Calendar.MONTH) + 1; // Calendar.MONTH 从0开始所以要+1
int day = calendar.get(Calendar.DAY_OF_MONTH);
int dayOfWeek = calendar.get(Calendar.DAY_OF_WEEK);
// 将数字星期转换为中文
String[] weekDays = {"星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六"};
String weekDayStr = weekDays[dayOfWeek - 1]; // Calendar.DAY_OF_WEEK 从1开始星期日=1
// 格式化日期字符串:例如 "9 月 9 日 星期三"
String dateStr = month + "" + day + "" + weekDayStr;
// 设置到TextView
viewBinding.tvDate.setText(dateStr);
}
private void setupProgressAnimations() {
// 监听父滚动视图假设外层是NestedScrollView
View scrollView = viewBinding.getRoot().findViewById(R.id.nesd_scrollview); // 替换为你的NestedScrollView id
if (scrollView != null) {
scrollView.getViewTreeObserver().addOnScrollChangedListener(() -> {
checkAndAnimateProgressBars();
});
}
// 初始检查(如果视图已经可见)
viewBinding.getRoot().postDelayed(() -> {
checkAndAnimateProgressBars();
}, 300); // 延迟300ms确保布局完成
}
private void checkAndAnimateProgressBars() {
if(mTodayEntity == null){
return;
}
// 圆形进度条(运势分数)
if (isViewVisible(viewBinding.includedTodayFateDatas.progressIndicator) && !isOverallAnimPlayed) {
animateCircularProgress(
viewBinding.includedTodayFateDatas.progressIndicator,
mTodayEntity.getFortuneAnalysis().getOverallScore()
);
isOverallAnimPlayed = true;
}
// 检查每个进度条是否需要执行动画
if (isViewVisible(viewBinding.includedSyy.proSyy) && !isCareerAnimPlayed) {
animateProgress(viewBinding.includedSyy.proSyy,
mTodayEntity.getFortuneAnalysis().getCareerScore());
isCareerAnimPlayed = true;
}
if (isViewVisible(viewBinding.includedSyy.proGqy) && !isLoveAnimPlayed) {
animateProgress(viewBinding.includedSyy.proGqy,
mTodayEntity.getFortuneAnalysis().getLoveScore());
isLoveAnimPlayed = true;
}
if (isViewVisible(viewBinding.includedSyy.proJky) && !isHealthAnimPlayed) {
animateProgress(viewBinding.includedSyy.proJky,
mTodayEntity.getFortuneAnalysis().getHealthScore());
isHealthAnimPlayed = true;
}
if (isViewVisible(viewBinding.includedSyy.proCfy) && !isWealthAnimPlayed) {
animateProgress(viewBinding.includedSyy.proCfy,
mTodayEntity.getFortuneAnalysis().getWealthScore());
isWealthAnimPlayed = true;
}
}
// 判断视图是否可见
private boolean isViewVisible(View view) {
if (view == null) return false;
Rect scrollBounds = new Rect();
View scrollView = viewBinding.getRoot().findViewById(R.id.nesd_scrollview);
if (scrollView != null) {
scrollView.getHitRect(scrollBounds);
return view.getLocalVisibleRect(scrollBounds);
}
return false;
}
// 执行进度条动画
private void animateProgress(LinearProgressIndicator progressBar, int targetProgress) {
// 保存原始进度值
final int originalProgress = progressBar.getProgress();
// 先重置为0
progressBar.setProgress(0);
// 创建动画
ObjectAnimator animator = ObjectAnimator.ofInt(progressBar, "progress", 0, targetProgress);
animator.setDuration(800); // 动画时长800ms
animator.setInterpolator(new AccelerateDecelerateInterpolator());
// 添加脉冲效果
animator.addUpdateListener(animation -> {
float fraction = animation.getAnimatedFraction();
float scale = 1 + 0.2f * (float) Math.sin(fraction * Math.PI);
progressBar.setScaleX(scale);
progressBar.setScaleY(scale);
});
animator.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
// 恢复原始大小
progressBar.animate()
.scaleX(1f)
.scaleY(1f)
.setDuration(200)
.start();
}
});
animator.start();
}
// 执行圆形进度条动画(带旋转效果)
private void animateCircularProgress(CircularProgressIndicator progressBar, int targetProgress) {
// 保存原始进度值
final int originalProgress = progressBar.getProgress();
// 先重置为0
progressBar.setProgress(0);
// 创建进度动画
ValueAnimator progressAnimator = ValueAnimator.ofInt(0, targetProgress);
progressAnimator.setDuration(1000); // 动画时长1000ms
progressAnimator.setInterpolator(new AccelerateDecelerateInterpolator());
// 创建旋转动画
ObjectAnimator rotationAnimator = ObjectAnimator.ofFloat(progressBar, "rotation", 0f, 360f);
rotationAnimator.setDuration(800);
rotationAnimator.setInterpolator(new AccelerateDecelerateInterpolator());
// 组合动画
AnimatorSet animatorSet = new AnimatorSet();
animatorSet.playTogether(progressAnimator, rotationAnimator);
// 添加脉冲缩放效果
progressAnimator.addUpdateListener(animation -> {
int progress = (int) animation.getAnimatedValue();
progressBar.setProgress(progress);
// 脉冲效果:在动画过程中轻微缩放
float fraction = animation.getAnimatedFraction();
float scale = 1 + 0.12f * (float) Math.sin(fraction * Math.PI);
progressBar.setScaleX(scale);
progressBar.setScaleY(scale);
});
animatorSet.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
// 恢复原始大小
progressBar.animate()
.scaleX(1f)
.scaleY(1f)
.setDuration(200)
.start();
}
});
animatorSet.start();
}
@Override
public FatePresenter createPresenter() {
return new FatePresenter(new FateImpl());
}
@Override
public void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(data != null){
if(resultCode == RESULT_OK){
switch (requestCode){
case REQUEST_EVENT_CODE_10002:
break;
case REQUEST_EVENT_CODE_10001:
break;
}
}
}
}
@Subscribe(threadMode = ThreadMode.MainThread)
public void onGetMessage(EventMessage message) {
switch (message.msg){
case EventMessage.DATA_REFRESH_EVENT:
showLoadingDialog();
startFateDataRequest();
break;
case EventMessage.USER_LOGIN_SUCCESS:
startFateDataRequest();
break;
}
}
/**
* 启动今日运势数据请求并开始延迟Toast任务
*/
private void startFateDataRequest() {
// 停止之前的Toast任务如果有的话
stopToastTask();
// 调用接口
mPresenter.getTodayFateDatas();
// 启动延迟Toast任务
startDelayedToastTask();
}
/**
* 启动延迟Toast任务
*/
private void startDelayedToastTask() {
// 5秒后开始显示Toast
toastHandler.postDelayed(() -> {
if (!isToastTaskRunning) {
isToastTaskRunning = true;
currentToastIndex = 0;
startToastLoop();
}
}, 5000);
}
/**
* 开始Toast循环显示
*/
private void startToastLoop() {
if (!isToastTaskRunning) {
return;
}
toastRunnable = new Runnable() {
@Override
public void run() {
if (isToastTaskRunning && currentToastIndex < toastMessages.length) {
// 显示当前Toast
ToastUtil.showLong(mContext, toastMessages[currentToastIndex]);
currentToastIndex++;
// 如果还有下一条消息5秒后显示
if (currentToastIndex < toastMessages.length && isToastTaskRunning) {
toastHandler.postDelayed(this, 5000);
} else {
// 所有消息显示完毕,重新开始循环
if (isToastTaskRunning) {
currentToastIndex = 0;
toastHandler.postDelayed(this, 5000);
}
}
}
}
};
// 立即执行第一次
toastRunnable.run();
}
/**
* 停止Toast任务
*/
private void stopToastTask() {
isToastTaskRunning = false;
if (toastRunnable != null) {
toastHandler.removeCallbacks(toastRunnable);
}
// 移除所有待执行的任务
toastHandler.removeCallbacksAndMessages(null);
}
/**
* 今日运势请求成功
* @param entity
*/
@Override
public void getUserTodayFateDataSuccess(TodayFateEntity entity) {
// 立即停止Toast任务
stopToastTask();
hideDialogLoading();
mTodayEntity = entity;
getLatLngByCityName(entity.getUserInfo().getCurrentPlace());
setDataShow();
viewBinding.refresh.finishRefresh(300);
}
@Override
public void getFateHistorySuccess(FateHistoryEntity entity) {
}
@Override
public void userSaveBirthInfoSuccess(TodayFateEntity bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
if(bean != null){
MingDengUserInfoManager.getInstance().setUserInfo(bean.getUserInfo());
SharePreUtil.putBoolean(ConstantUtil.SHARE_PRE_NAME,mContext,ConstantUtil.USER_HAS_SET_BIRTH,bean.isHasEightCharacters());
AppConfig.USER_SET_BIRTH_INFO = bean.isHasEightCharacters();
//是否设置过生辰
if(AppConfig.USER_SET_BIRTH_INFO){
viewBinding.llInput.setVisibility(View.GONE);
viewBinding.refresh.setVisibility(View.VISIBLE);
}else{
viewBinding.llInput.setVisibility(View.VISIBLE);
viewBinding.refresh.setVisibility(View.GONE);
}
}
}
/**
* 提交举报成功
* @param bean
*/
@Override
public void commitReportSuccess(BaseBean bean) {
ToastUtil.showShort(mContext, "星语明灯感谢您的反馈");
hideDialogLoading();
}
/**
* 设置显示内容
*/
private void setDataShow() {
//出生日期
String birthDay = mTodayEntity.getUserInfo().getBirthTime();
viewBinding.includedBirthInfo.tvBirthdayTime.setText(ZYTimeUtils.formatDateString(birthDay));
//真太阳时
String realSunTime = mTodayEntity.getUserInfo().getTrueSolarTime();
viewBinding.includedBirthInfo.tvZhentaiyangValue.setText(TextUtils.isEmpty(realSunTime) ?
"未知":ZYTimeUtils.formatToChineseDate(realSunTime));
//命格
viewBinding.includedBirthInfo.tvMingge.setText(TextUtils.isEmpty(mTodayEntity.getFortuneAnalysis().getDestiny()) ?
"未知": mTodayEntity.getFortuneAnalysis().getDestiny());
//经纬度
String lng = NumberDecimalFilter.truncateToTwoDecimal(Double.parseDouble(mTodayEntity.getUserInfo().getLongitude()));
String lat = NumberDecimalFilter.truncateToTwoDecimal(Double.parseDouble(mTodayEntity.getUserInfo().getLatitude()));
viewBinding.includedBirthInfo.tvLonglat.setText(lng + "," + lat);
//出生地
viewBinding.includedBirthInfo.tvBirthAddress.setText(mTodayEntity.getUserInfo().getBirthPlace());
//星座
viewBinding.includedBirthInfo.tvXingzuo.setText(mTodayEntity.getUserInfo().getConstellation());
//运势分数
int todayScore = mTodayEntity.getFortuneAnalysis().getOverallScore();
int color = FateDataUtil.getScoreColor(todayScore);
viewBinding.includedTodayFateDatas.progressIndicator.setIndicatorColor(color);
// viewBinding.includedTodayFateDatas.progressIndicator.setProgress(todayScore,true);
viewBinding.includedTodayFateDatas.tvFeenValue.setText(String.valueOf(todayScore));
viewBinding.includedTodayFateDatas.tvFeenValue.setTextColor(color);
//运势内容
viewBinding.includedTodayFateDatas.tvYunshiContent.setText(TextUtils.isEmpty(mTodayEntity.getFortuneAnalysis().getOverallDescription())?
"暂无内容" : mTodayEntity.getFortuneAnalysis().getOverallDescription());
//今日吉时
viewBinding.includedTodayFateDatas.tvTimeZc.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(0).getTime());
viewBinding.includedTodayFateDatas.tvThingZc.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(0).getDescription());
viewBinding.includedTodayFateDatas.tvTimeZw.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(1).getTime());
viewBinding.includedTodayFateDatas.tvThingZw.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(1).getDescription());
viewBinding.includedTodayFateDatas.tvTimeXw.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(2).getTime());
viewBinding.includedTodayFateDatas.tvThingXw.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(2).getDescription());
//天象星座
viewBinding.includedXingzuo.tvXingzuo.setText(mTodayEntity.getUserInfo().getConstellation());
viewBinding.includedXingzuo.tvWendu.setText(mTodayEntity.getWeatherTemperature());
viewBinding.includedXingzuo.tvTianqi.setText(mTodayEntity.getWeatherCondition());
viewBinding.includedXingzuo.tvXzType.setText(FateDataUtil.getConstellationType(mTodayEntity.getUserInfo().getConstellation()));
viewBinding.includedXingzuo.tvXingzuoYingxiang.setText(mTodayEntity.getFortuneAnalysis().getAstrologyInfluence().getDescription());
//事业运
viewBinding.includedSyy.tvSyyScore.setText(String.valueOf(mTodayEntity.getFortuneAnalysis().getCareerScore()));
// viewBinding.includedSyy.proSyy.setProgress(mTodayEntity.getFortuneAnalysis().getCareerScore());
viewBinding.includedSyy.tvSyyContent.setText(mTodayEntity.getFortuneAnalysis().getCareerDescription());
//事业运
viewBinding.includedSyy.tvGqyScore.setText(String.valueOf(mTodayEntity.getFortuneAnalysis().getLoveScore()));
// viewBinding.includedSyy.proGqy.setProgress(mTodayEntity.getFortuneAnalysis().getLoveScore());
viewBinding.includedSyy.tvGqyContent.setText(mTodayEntity.getFortuneAnalysis().getLoveDescription());
//事业运
viewBinding.includedSyy.tvJkyScore.setText(String.valueOf(mTodayEntity.getFortuneAnalysis().getHealthScore()));
// viewBinding.includedSyy.proJky.setProgress(mTodayEntity.getFortuneAnalysis().getHealthScore());
viewBinding.includedSyy.tvJkyContent.setText(mTodayEntity.getFortuneAnalysis().getHealthDescription());
//事业运
viewBinding.includedSyy.tvCfyScore.setText(String.valueOf(mTodayEntity.getFortuneAnalysis().getWealthScore()));
// viewBinding.includedSyy.proCfy.setProgress(mTodayEntity.getFortuneAnalysis().getWealthScore());
viewBinding.includedSyy.tvCfyContent.setText(mTodayEntity.getFortuneAnalysis().getWealthDescription());
//幸运数字
String [] numbers = mTodayEntity.getFortuneAnalysis().getLuckyInfo().getNumbers();
StringBuilder sb = new StringBuilder();
for (int i = 0; i < numbers.length; i++) {
sb.append(numbers[i]);
if (i < numbers.length - 1) {
sb.append("");
}
}
viewBinding.includeXingyun.tvLuckNum.setText(sb.toString());
//幸运颜色
viewBinding.includeXingyun.tvLuckColor.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getColor());
//幸运方位
viewBinding.includeXingyun.tvLuckFw.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getDirection());
//幸运时间
viewBinding.includeXingyun. tvLuckTime.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getLuckyTimes().get(0).getTime());
//幸运花卉
viewBinding.includeXingyun.tvLuckFlower.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getFlower());
//幸运方位
viewBinding.includeXingyun.tvLuckFood.setText(mTodayEntity.getFortuneAnalysis().getLuckyInfo().getFood());
//宜 忌
String positive = mTodayEntity.getFortuneAnalysis().getSuggestions().getPositive();
String negative = mTodayEntity.getFortuneAnalysis().getSuggestions().getNegative();
viewBinding.includeYsjy.tvPositive.setText(positive);
viewBinding.includeYsjy.tvNegative.setText(negative);
//五行分析
viewBinding.includeYsjy.tvFive.setText(mTodayEntity.getFortuneAnalysis().getFiveElementsAnalysis());
// 重置动画标志位
resetAnimationFlags();
}
/**
* 通过城市逆地理编码,获取经纬度
* @param cityName
*/
private void getLatLngByCityName(String cityName) {
try {
GeocodeSearch geocodeSearch = new GeocodeSearch(mContext);
geocodeSearch.setOnGeocodeSearchListener(new GeocodeSearch.OnGeocodeSearchListener() {
@Override
public void onRegeocodeSearched(com.amap.api.services.geocoder.RegeocodeResult regeocodeResult, int i) {
// Not used here
}
@Override
public void onGeocodeSearched(GeocodeResult geocodeResult, int rCode) {
if (rCode == AMapException.CODE_AMAP_SUCCESS) {
List<GeocodeAddress> addressList = geocodeResult.getGeocodeAddressList();
if (addressList != null && !addressList.isEmpty()) {
GeocodeAddress address = addressList.get(0);
LatLonPoint latLonPoint = address.getLatLonPoint();
String lat = String.valueOf(NumberDecimalFilter.roundToTwoDecimalPlaces(latLonPoint.getLatitude()));
String lng = String.valueOf(NumberDecimalFilter.roundToTwoDecimalPlaces(latLonPoint.getLongitude()));
WeatherParameter parameter = new WeatherParameter(lng + "," + lat)
.lang(Lang.ZH_HANS)
.unit(Unit.METRIC);
instance.weatherNow(parameter, new Callback<WeatherNowResponse>() {
@Override
public void onSuccess(WeatherNowResponse response) {
mContext.runOnUiThread(new Runnable() {
@Override
public void run() {
try {
WeatherIconUtil.loadWeatherIcon(mContext,viewBinding.includedBirthInfo.imgWeather,response.getNow().getIcon());
viewBinding.includedBirthInfo.tvTianqi.setText(response.getNow().getText() + " " +response.getNow().getTemp() + "");
} catch (Exception e) {
throw new RuntimeException(e);
}
}
});
}
@Override
public void onFailure(ErrorResponse errorResponse) {
Log.d(TAG,"调用和风 API--onFailure" + errorResponse.toString());
}
@Override
public void onException(Throwable e) {
Log.d(TAG,"调用和风 API--onException" + e.getMessage());
e.printStackTrace();
}
});
} else {
Log.d("GeoUtil", "未找到城市: " + cityName);
}
} else {
Log.e("GeoUtil", "查询失败,错误码: " + rCode);
}
}
});
// 创建 GeocodeQuery第一个参数是城市名第二个参数可指定省份可选
GeocodeQuery query = new GeocodeQuery(cityName, null);
geocodeSearch.getFromLocationNameAsyn(query); // 异步查询
} catch (AMapException e) {
throw new RuntimeException(e);
}
}
// 重置动画标志位
private void resetAnimationFlags() {
isOverallAnimPlayed = false;
isCareerAnimPlayed = false;
isLoveAnimPlayed = false;
isHealthAnimPlayed = false;
isWealthAnimPlayed = false;
}
@Override
public void onPause() {
super.onPause();
// 停止Toast任务
stopToastTask();
// 重置标志位以便下次可见时重新动画
resetAnimationFlags();
}
@Override
public void onDestroy() {
super.onDestroy();
// 清理资源
stopToastTask();
}
@Override
public void onNetChange(int netModel) {
}
@Override
public void showError(String message) {
// 停止Toast任务
stopToastTask();
hideDialogLoading();
ToastUtil.showShort(mContext,message);
}
@Override
public void logOut(BaseBean bean) {
}
@Override
public void getAllCitySuccess(List<CityDataEntity> list) {
}
private void getCurrentCityWeather(GeoPoiResponse response) {
}
@Override
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
}
@Override
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
EasyPermissions.onRequestPermissionsResult(requestCode, permissions, grantResults, this);
hidePermissionDialog();
if(requestCode == REQUEST_EVENT_CODE_10002){
if(grantResults[0] == 0){
ToastUtil.showShort(mContext,"定位获取成功");
}
}
}
}

View File

@@ -122,6 +122,11 @@ public class GuideActivity extends BaseActivity<GuideActivityLayoutBinding, Logi
super.initWidget();
}
@Override
public void registerSuccess(BaseBean bean) {
}
@Override
public void getPhoneCodeSuccess(BaseBean bean) {
}

View File

@@ -5,7 +5,10 @@ import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import com.ckkj.water.AppConfig;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.login.RegisterActivity;
import com.ckkj.water.login.RegisterSuccessActivity;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.MyApplication;
@@ -88,9 +91,15 @@ public class LaunchActivity extends BaseActivity<GuideLayoutBinding, MainPresent
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
Intent intent = new Intent(mContext, MainActivity.class);
startActivity(intent);
finish();
if(AppConfig.USER_LOGIN){
Intent intent = new Intent(mContext, MainActivity.class);
startActivity(intent);
finish();
}else{
goTo(mContext, LoginActivity.class,null);
finish();
}
}
}, 2000);

View File

@@ -10,6 +10,7 @@ import androidx.annotation.Nullable;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.custom.view.CustomRefreshHeader;
import com.ckkj.water.databinding.IndexFragmentLayoutBinding;
import com.ckkj.water.device.AddDeviceActivity;
import com.ckkj.water.device.DeviceControlActivity;
@@ -19,9 +20,12 @@ import com.ckkj.water.index.mvp.IndexContract;
import com.ckkj.water.index.mvp.IndexImpl;
import com.ckkj.water.index.mvp.IndexPresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.permission.PermissionActivity;
import com.ckkj.water.utils.show.ToastUtil;
import com.maning.mlkitscanner.scan.MNScanManager;
import com.maning.mlkitscanner.scan.callback.act.MNScanCallback;
import com.scwang.smart.refresh.footer.ClassicsFooter;
import com.scwang.smart.refresh.layout.api.RefreshHeader;
import java.util.ArrayList;
import java.util.List;
@@ -33,6 +37,7 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
private DeviceAdapter deviceAdapter;
private List<IndexDeviceEntity> devList = new ArrayList<>();
private int mCurrentPage = 1;
@Override
protected void initArgs(Bundle bundle) {
@@ -40,14 +45,21 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
@Override
public void initData(@Nullable Bundle savedInstanceState) {
IndexDeviceEntity entity = new IndexDeviceEntity("智能浇水设备A1","YA226641000101","工作中",100);
IndexDeviceEntity entity2 = new IndexDeviceEntity("智能浇水设备B1","YA22664100000","工作中",80);
IndexDeviceEntity entity3 = new IndexDeviceEntity("智能浇水设备C5","YA234534000101","工作中",70);
IndexDeviceEntity entity4 = new IndexDeviceEntity("智能浇水设备D6","YA2266678543101","工作中",50);
devList.add(entity);
devList.add(entity2);
devList.add(entity3);
devList.add(entity4);
// 设置自定义刷新头
RefreshHeader header = new CustomRefreshHeader(mContext);
viewBinding.refresh.setRefreshHeader(header);
viewBinding.refresh.setRefreshFooter(new ClassicsFooter(mContext));
viewBinding.refresh.setOnRefreshListener(layout -> {
mCurrentPage = 1;
mPresenter.getDevicesList(mCurrentPage);
});
viewBinding.refresh.setOnLoadMoreListener(layout -> {
mCurrentPage++;
mPresenter.getDevicesList(mCurrentPage);
});
showLoadingDialog();
mPresenter.getDevicesList(mCurrentPage);
}
@Override
@@ -86,7 +98,13 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
break;
case R.id.img_add:
goTo(mContext, AddDeviceActivity.class,null);
String permission = Manifest.permission.ACCESS_FINE_LOCATION;
boolean hasPermission = hasRecordPermission(permission);
if(!hasPermission){
goTo(mContext, PermissionActivity.class,null);
}else{
goTo(mContext, AddDeviceActivity.class,null);
}
break;
}
}
@@ -122,6 +140,42 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
});
}
/**
* 获取设备列表成功
*/
@Override
public void getDeviceListSuccess(List<IndexDeviceEntity> list,int total) {
hideDialogLoading();
viewBinding.refresh.finishRefresh(300);
viewBinding.refresh.finishLoadMore(300);
if (mCurrentPage == 1) {
devList.clear(); // 只在刷新时清除
devList = list;
} else {
devList.addAll(list);
}
deviceAdapter.setNewData(devList);
// 4. 判断是否还有更多数据
if (total == deviceAdapter.getItemCount() || list == null || list.size() == 0) {
// ✅ 告诉 SmartRefreshLayout 没有更多数据了
viewBinding.refresh.setNoMoreData(true);
viewBinding.relNoMore.setVisibility(View.VISIBLE); // 自定义底部提示“暂无更多数据”
} else {
viewBinding.refresh.setNoMoreData(false); // 重置状态
viewBinding.relNoMore.setVisibility(View.GONE);
}
// 5. 控制空布局和内容显示
if (deviceAdapter.getItemCount() != 0) {
viewBinding.refresh.setVisibility(View.VISIBLE);
viewBinding.relNoresult.setVisibility(View.GONE);
} else {
viewBinding.refresh.setVisibility(View.GONE);
viewBinding.relNoresult.setVisibility(View.VISIBLE);
}
}
@Override
public void onDestroyView() {
super.onDestroyView();
@@ -133,6 +187,8 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
@Override
public void showError(String message) {
hideDialogLoading();
ToastUtil.showShort(mContext,message);
}
@Override
@@ -148,4 +204,6 @@ public class IndexFragment extends BaseFragment<IndexFragmentLayoutBinding, Inde
scanQrcode();
}
}
}

View File

@@ -27,10 +27,10 @@ public class DeviceAdapter extends BaseQuickAdapter<IndexDeviceEntity, BaseViewH
@Override
protected void convert(BaseViewHolder holder, IndexDeviceEntity item) {
holder.setText(R.id.tv_device_name,item.getDeviceNames());
holder.setText(R.id.tv_device_serial,item.getDeviceSerials());
holder.setText(R.id.tv_device_status,item.getDeviceStatuses());
holder.setText(R.id.tv_battery_level,item.getBatteryLevels() + "");
holder.setText(R.id.tv_device_name,item.getDeviceName());
holder.setText(R.id.tv_device_serial,item.getDeviceSn());
holder.setText(R.id.tv_device_status,"工作中");
holder.setText(R.id.tv_battery_level,"80");
}

View File

@@ -2,48 +2,44 @@ package com.ckkj.water.index.entity;
import java.io.Serializable;
import lombok.Data;
import lombok.NoArgsConstructor;
@NoArgsConstructor
@Data
public class IndexDeviceEntity implements Serializable {
private String deviceNames;
private String deviceSerials;
private String deviceStatuses;
private int batteryLevels;
public IndexDeviceEntity(String deviceNames, String deviceSerials, String deviceStatuses, int batteryLevels) {
this.deviceNames = deviceNames;
this.deviceSerials = deviceSerials;
this.deviceStatuses = deviceStatuses;
this.batteryLevels = batteryLevels;
}
/**
* id : 2056638783822123010
* deviceNo : 1779175872972
* userId : 2056543507514097665
* deviceName : 50号设备
* deviceImg : null
* status : 0
* powerLevel : null
* powerLevelUpdatatime : null
* wifiName : 橙空科技WiFi
* wifiPassword : 12321212
* deviceEm : 213123123123
* deviceSn : sdfsd32423gdfgdf3
* fwVer : fwVer-56565644
* macAddress : 2E:8H:00:KK:N7
* expirationTime : null
*/
public String getDeviceNames() {
return deviceNames;
}
public void setDeviceNames(String deviceNames) {
this.deviceNames = deviceNames;
}
public String getDeviceSerials() {
return deviceSerials;
}
public void setDeviceSerials(String deviceSerials) {
this.deviceSerials = deviceSerials;
}
public String getDeviceStatuses() {
return deviceStatuses;
}
public void setDeviceStatuses(String deviceStatuses) {
this.deviceStatuses = deviceStatuses;
}
public int getBatteryLevels() {
return batteryLevels;
}
public void setBatteryLevels(int batteryLevels) {
this.batteryLevels = batteryLevels;
}
private String id;
private String deviceNo;
private String userId;
private String deviceName;
private Object deviceImg;
private String status;
private Object powerLevel;
private Object powerLevelUpdatatime;
private String wifiName;
private String wifiPassword;
private String deviceEm;
private String deviceSn;
private String fwVer;
private String macAddress;
private Object expirationTime;
}

View File

@@ -1,11 +1,15 @@
package com.ckkj.water.index.mvp;
import com.ckkj.water.base.IView;
import com.ckkj.water.index.entity.IndexDeviceEntity;
import com.ckkj.water.login.entity.LoginEntity;
import com.ckkj.water.network.BaseBean;
import org.json.JSONObject;
import java.util.List;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/26
@@ -14,12 +18,17 @@ import org.json.JSONObject;
public class IndexContract {
public interface CallBack<T> {
void success(T msg);
void success(T msg,int total);
void fail(String msg);
}
public interface DataModel{
//获取设备列表
void getDeviceList(Map<String,String> map,CallBack callBack);
}
public interface IndexView extends IView{
void getDeviceListSuccess(List<IndexDeviceEntity> list,int total);
}
}

View File

@@ -1,5 +1,54 @@
package com.ckkj.water.index.mvp;
import com.ckkj.water.index.entity.IndexDeviceEntity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.network.NetWorkManager;
import org.json.JSONObject;
import java.util.List;
import java.util.Map;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
public class IndexImpl implements IndexContract.DataModel{
/**
* 设备列表
* @param map
* @param callBack
*/
@Override
public void getDeviceList(Map<String, String> map, IndexContract.CallBack callBack) {
NetWorkManager.getRequest().getIndexDeviceList(NetWorkManager.getToken())
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<List<IndexDeviceEntity>>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<List<IndexDeviceEntity>> bean) {
if (bean.getCode() == 200) {
callBack.success(bean.getRows(),bean.getTotal());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
}
}

View File

@@ -1,8 +1,10 @@
package com.ckkj.water.index.mvp;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.login.mvp.LoginImpl;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.index.entity.IndexDeviceEntity;
import java.util.HashMap;
import java.util.List;
public class IndexPresenter extends BasePresenter<IndexContract.IndexView>{
@@ -12,4 +14,25 @@ public class IndexPresenter extends BasePresenter<IndexContract.IndexView>{
this.mImpl = mImpl;
}
/**
* 查询设备列表
*/
public void getDevicesList(int mCurrentPage) {
mImpl.getDeviceList(new HashMap<>(), new IndexContract.CallBack<List<IndexDeviceEntity>>() {
@Override
public void success(List<IndexDeviceEntity> list, int total) {
if(IndexPresenter.this.getView() != null){
IndexPresenter.this.getView().getDeviceListSuccess(list,total);
}
}
@Override
public void fail(String msg) {
if(IndexPresenter.this.getView() != null){
IndexPresenter.this.getView().showError(msg);
}
}
});
}
}

View File

@@ -102,6 +102,11 @@ public class ForgetPasswordActivity extends BaseActivity<RegisterLayoutBinding,
};
@Override
public void registerSuccess(BaseBean bean) {
}
@Override
public void getPhoneCodeSuccess(BaseBean bean) {

View File

@@ -2,8 +2,10 @@ package com.ckkj.water.login;
import static android.view.View.GONE;
import static android.view.View.INVISIBLE;
import static android.view.View.VISIBLE;
import android.graphics.Color;
import android.graphics.Typeface;
import android.os.Bundle;
import android.os.CountDownTimer;
@@ -20,8 +22,6 @@ import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.core.content.ContextCompat;
import com.ckkj.water.custom.view.PhotoViewActivity;
import com.ckkj.water.utils.DownFileUtil;
import com.google.gson.Gson;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.AppConfig;
@@ -34,11 +34,10 @@ import com.ckkj.water.login.mvp.LoginContract;
import com.ckkj.water.login.mvp.LoginImpl;
import com.ckkj.water.login.mvp.LoginPresenter;
import com.ckkj.water.main.activity.MainActivity;
import com.ckkj.water.mine.WebviewUserAgreement;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.click.ClickUtil;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.number.PhoneNumberUtils;
import com.ckkj.water.utils.show.ToastUtil;
import com.lxj.xpopup.XPopup;
@@ -79,6 +78,7 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
setClick(viewBinding.tvGoRegister);
setClick(viewBinding.tvLanguage);
setClick(viewBinding.tvResetPsd);
setClick(viewBinding.checkboxRead);
}
private void setClick(View view) {
@@ -86,59 +86,75 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
}
private void setupAgreementText() {
String prefix = getString(R.string.login_agreement_prefix);
String privacy = getString(R.string.login_privacy_policy);
String and = getString(R.string.login_and);
String userAgreement = getString(R.string.login_user_agreement);
String content = prefix + privacy + and + userAgreement;
//勾选协议,增加点击区域
ClickUtil.addClickPart(viewBinding.checkboxRead,100);
TextView tvAgreement = findViewById(R.id.tv_agreement_full);
String content = "我已经阅读并同意智能浇灌《用户协议》、《隐私政策》";
SpannableString spannableString = new SpannableString(content);
int privacyStart = prefix.length();
int privacyEnd = privacyStart + privacy.length();
ClickableSpan privacyPolicySpan = new ClickableSpan() {
@Override
public void onClick(@NonNull View widget) {
Bundle bundle = new Bundle();
bundle.putInt("from_requse_code", WebviewUserAgreement.PRIVACY_CODE);
goToWihoutNoPresent(mContext, WebviewUserAgreement.class, bundle);
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setColor(ContextCompat.getColor(mContext, R.color.color_zhu));
ds.setUnderlineText(false);
}
};
spannableString.setSpan(privacyPolicySpan, privacyStart, privacyEnd, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
int userStart = privacyEnd + and.length();
int userEnd = userStart + userAgreement.length();
// 设置“用户协议”可点击
ClickableSpan userAgreementSpan = new ClickableSpan() {
@Override
public void onClick(@NonNull View widget) {
Bundle bundle = new Bundle();
bundle.putInt("from_requse_code", WebviewUserAgreement.AGREEMENT_CODE);
goToWihoutNoPresent(mContext, WebviewUserAgreement.class, bundle);
// 跳转用户协议
// Bundle bundle = new Bundle();
// bundle.putInt("from_requse_code", WebviewUserAgreement.AGREEMENT_CODE);
// goToWihoutNoPresent(mContext, WebviewUserAgreement.class,bundle);
ToastUtil.showShort(mContext,"用户协议");
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setColor(ContextCompat.getColor(mContext, R.color.color_zhu));
ds.setColor(ContextCompat.getColor(mContext, R.color.color_zhu)); // 设置颜色
ds.setUnderlineText(false); // 去掉下划线
}
};
int start1 = content.indexOf("《用户协议》");
int end1 = start1 + "《用户协议》".length();
spannableString.setSpan(userAgreementSpan, start1, end1, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
// 设置“隐私政策”可点击
ClickableSpan privacyPolicySpan = new ClickableSpan() {
@Override
public void onClick(@NonNull View widget) {
// 跳转隐私政策
// Bundle bundleYS = new Bundle();
// bundleYS.putInt("from_requse_code",WebviewUserAgreement.PRIVACY_CODE);
// goToWihoutNoPresent(mContext, WebviewUserAgreement.class,bundleYS);
ToastUtil.showShort(mContext,"跳转隐私政策");
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setColor(ContextCompat.getColor(mContext, R.color.color_zhu)); // 设置颜色
ds.setUnderlineText(false);
}
};
spannableString.setSpan(userAgreementSpan, userStart, userEnd, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
int start2 = content.indexOf("《隐私政策》");
int end2 = start2 + "《隐私政策》".length();
spannableString.setSpan(privacyPolicySpan, start2, end2, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
// viewBinding.tvAgreement.setText(spannableString);
// viewBinding.tvAgreement.setMovementMethod(LinkMovementMethod.getInstance());
tvAgreement.setText(spannableString);
tvAgreement.setMovementMethod(LinkMovementMethod.getInstance()); // 开启点击事件
tvAgreement.setHighlightColor(Color.TRANSPARENT);
}
public void onClick(View v) {
switch (v.getId()) {
case R.id.checkbox_read:
if(mYinsiConfirm){
mYinsiConfirm = false;
viewBinding.checkboxRead.setChecked(false);
}else{
mYinsiConfirm = true;
viewBinding.checkboxRead.setChecked(true);
}
break;
case R.id.tv_go_register:
goTo(mContext, RegisterActivity.class,null);
break;
@@ -151,7 +167,7 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
viewBinding.tvLoginByPsd.setTextColor(mContext.getResources().getColor(R.color.color_999999));
viewBinding.tvLoginByPsd.setTypeface(Typeface.DEFAULT);
viewBinding.viewLinePsd.setVisibility(GONE);
viewBinding.viewLinePsd.setVisibility(INVISIBLE);
viewBinding.linearVerfiCode.setVisibility(VISIBLE);
viewBinding.linearPsd.setVisibility(GONE);
@@ -166,7 +182,7 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
viewBinding.tvLoginByCode.setTextColor(mContext.getResources().getColor(R.color.color_999999));
viewBinding.tvLoginByCode.setTypeface(Typeface.DEFAULT);
viewBinding.viewLineCode.setVisibility(GONE);
viewBinding.viewLineCode.setVisibility(INVISIBLE);
viewBinding.linearVerfiCode.setVisibility(GONE);
viewBinding.linearPsd.setVisibility(VISIBLE);
@@ -183,11 +199,10 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_invalid));
return;
}
cdTimer.start();
// showLoadingDialog();
// mPresenter.getPhoneCode(
// viewBinding.edPhoneInput.getText().toString().trim(),
// AppConfig.SMS_CODE_TYPE_LOGIN);
// cdTimer.start();
showLoadingDialog();
//发送短信
mPresenter.getPhoneCode(viewBinding.etAccount.getText().toString(),"");
break;
case R.id.tv_language:
@@ -215,33 +230,47 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
// viewBinding.checkboxRead.setChecked(true);
// }
// break;
// case R.id.tv_login_confirm:
// if (TextUtils.isEmpty(viewBinding.edPhoneInput.getText().toString())) {
// ToastUtil.showShort(mContext, getString(R.string.login_error_phone_empty));
// return;
// }
// if (!PhoneNumberUtils.checkPhoneNum(viewBinding.edPhoneInput.getText().toString().trim())) {
// ToastUtil.showShort(mContext, getString(R.string.login_error_phone_invalid));
// return;
// }
// if (TextUtils.isEmpty(viewBinding.edCodeInput.getText().toString())) {
// ToastUtil.showShort(mContext, getString(R.string.login_error_code_empty));
// return;
// }
// if (viewBinding.edCodeInput.getText().toString().trim().length() < 6) {
// ToastUtil.showShort(mContext, getString(R.string.login_error_code_invalid));
// return;
// }
// if (!mYinsiConfirm) {
// ToastUtil.showShort(mContext, getString(R.string.login_error_agreement));
// return;
// }
// showLoadingDialog();
// mPresenter.loginBySmsCode(
// viewBinding.edPhoneInput.getText().toString().trim(),
// viewBinding.edCodeInput.getText().toString().trim());
case R.id.tv_login:
if (TextUtils.isEmpty(viewBinding.etAccount.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_empty));
return;
}
if (!PhoneNumberUtils.checkPhoneNum(viewBinding.etAccount.getText().toString().trim()) &&
!PhoneNumberUtils.checkEmail(viewBinding.etAccount.getText().toString().trim())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_invalid));
return;
}
String loginType = "sms";
if(LOGIN_TYPE_STATUS_CODE == 100){//验证码登录
loginType = "sms";
if (TextUtils.isEmpty(viewBinding.edCodeInput.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_code_empty));
return;
}
if (viewBinding.edCodeInput.getText().toString().trim().length() < 6) {
ToastUtil.showShort(mContext, getString(R.string.login_error_code_invalid));
return;
}
}else{//密码登录
loginType = "password";
if (TextUtils.isEmpty(viewBinding.etInputPsd.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_psd_empty));
return;
}
}
if (!mYinsiConfirm) {
ToastUtil.showShort(mContext, getString(R.string.login_error_agreement));
return;
}
showLoadingDialog();
mPresenter.loginBySmsCode(loginType,
viewBinding.etAccount.getText().toString().trim(),
viewBinding.edCodeInput.getText().toString().trim(),
viewBinding.etInputPsd.getText().toString());
// new Handler().postDelayed(() -> hideDialogLoading(), 1000);
// break;
break;
}
@@ -267,11 +296,16 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
}
};
@Override
public void registerSuccess(BaseBean bean) {
}
@Override
public void getPhoneCodeSuccess(BaseBean bean) {
hideDialogLoading();
ToastUtil.showShort(mContext, getString(R.string.login_code_sent));
cdTimer.start();
ToastUtil.showLong(mContext, getString(R.string.login_code_sent) + ":" + bean.getDataString());
// cdTimer.start();
}
@Override
@@ -280,16 +314,12 @@ public class LoginActivity extends BaseActivity<LoginLayoutBinding, LoginPresent
ToastUtil.showShort(mContext, getString(R.string.login_success));
SharePreUtil.putBoolean(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_LOGIN, true);
SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_TOKEN, entity.getAccess_token());
SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_NICKNAME, entity.getUser_info().getNickname());
SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_ID, String.valueOf(entity.getUser_info().getUserId()));
MingDengUserInfoManager.getInstance().setEntity(entity);
MingDengUserInfoManager.getInstance().setUserInfo(entity.getUser_info());
Gson gson = new Gson();
String userInfoJson = gson.toJson(entity);
SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_INFO_JSON_CONTENT, userInfoJson);
WaterUserInfoManager.getInstance().setEntity(entity);
// Gson gson = new Gson();
// String userInfoJson = gson.toJson(entity);
// SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME, mContext, ConstantUtil.USER_INFO_JSON_CONTENT, userInfoJson);
AppConfig.USER_LOGIN = true;
AppConfig.USER_TOKEN = entity.getAccess_token();
AppConfig.USER_ID = String.valueOf(entity.getUser_info().getUserId());
new Handler().postDelayed(() -> {
goTo(mContext, MainActivity.class, null);
finish();

View File

@@ -69,11 +69,49 @@ public class RegisterActivity extends BaseActivity<RegisterLayoutBinding, LoginP
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_invalid));
return;
}
cdTimer.start();
//发送短信
mPresenter.getPhoneCode(viewBinding.etAccount.getText().toString(),"");
// cdTimer.start();
break;
case R.id.tv_commit:
goTo(mContext, RegisterSuccessActivity.class,null);
if (TextUtils.isEmpty(viewBinding.etAccount.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_empty));
return;
}
if (!PhoneNumberUtils.checkPhoneNum(viewBinding.etAccount.getText().toString().trim()) &&
!PhoneNumberUtils.checkEmail(viewBinding.etAccount.getText().toString().trim())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_invalid));
return;
}
if (TextUtils.isEmpty(viewBinding.etVerfiCode.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_empty));
return;
}
if (TextUtils.isEmpty(viewBinding.etVerfiCode.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_phone_empty));
return;
}
if (TextUtils.isEmpty(viewBinding.etInputPsd.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_psd_empty));
return;
}
if (TextUtils.isEmpty(viewBinding.etInputPsdAgin.getText().toString())) {
ToastUtil.showShort(mContext, getString(R.string.login_error_psd_agin_empty));
return;
}
if(!(viewBinding.etInputPsd.getText().toString()).equals(
viewBinding.etInputPsdAgin.getText().toString())){
ToastUtil.showShort(mContext, getString(R.string.hint_input_psd_not_match));
return;
}
showLoadingDialog();
mPresenter.registerAccount(viewBinding.etAccount.getText().toString(),
viewBinding.etVerfiCode.getText().toString(),
viewBinding.etInputPsd.getText().toString());
break;
}
}
@@ -100,6 +138,13 @@ public class RegisterActivity extends BaseActivity<RegisterLayoutBinding, LoginP
};
@Override
public void registerSuccess(BaseBean bean) {
hideDialogLoading();
ToastUtil.showShort(mContext,"注册成功");
finish();
}
@Override
public void getPhoneCodeSuccess(BaseBean bean) {
@@ -112,6 +157,7 @@ public class RegisterActivity extends BaseActivity<RegisterLayoutBinding, LoginP
@Override
public void showError(String message) {
hideDialogLoading();
ToastUtil.showShort(mContext,message);
}

View File

@@ -79,6 +79,11 @@ public class RegisterSuccessActivity extends BaseActivity<RegisterSuccessLayoutB
return 0;
}
@Override
public void registerSuccess(BaseBean bean) {
}
@Override
public void getPhoneCodeSuccess(BaseBean bean) {

View File

@@ -1,41 +1,35 @@
package com.ckkj.water.login.entity;
import com.ckkj.water.base.entity.UserInfoEntity;
import java.io.Serializable;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author fengxiaoyang
* @date 2025/7/28
* @description TODO: 描述该类的作用
*/
@NoArgsConstructor
@Data
public class LoginEntity implements Serializable {
/**
* scope : null
* openid : null
* access_token : eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJsb2dpblR5cGUiOiJsb2dpbiIsImxvZ2luSWQiOiJhcHBfdXNlcjoyMDU2NTQzNTA3NTE0MDk3NjY1Iiwicm5TdHIiOiJFOVE4a1VzT2dJbjRCZWtGY0pTRXZGdkljNjhFOG1FQSIsImNsaWVudGlkIjoiNDI4YTgzMTBjZDQ0Mjc1N2FlNjk5ZGY1ZDg5NGYwNTEiLCJ0ZW5hbnRJZCI6IjAwMDAwMCIsInVzZXJJZCI6MjA1NjU0MzUwNzUxNDA5NzY2NX0.nh38mcgK2JOtuBR4ogQlcnQbMTiLJ_TXln_BGFhlUkU
* refresh_token : null
* expire_in : 60480000
* refresh_expire_in : null
* client_id : 428a8310cd442757ae699df5d894f051
*/
private Object scope;
private Object openid;
private String access_token;
private UserInfoEntity user_info;
private long expires_in;
public String getAccess_token() {
return access_token;
}
public void setAccess_token(String access_token) {
this.access_token = access_token;
}
public UserInfoEntity getUser_info() {
return user_info;
}
public void setUser_info(UserInfoEntity user_info) {
this.user_info = user_info;
}
public long getExpires_in() {
return expires_in;
}
public void setExpires_in(long expires_in) {
this.expires_in = expires_in;
}
private Object refresh_token;
private int expire_in;
private Object refresh_expire_in;
private String client_id;
}

View File

@@ -6,6 +6,8 @@ import com.ckkj.water.network.BaseBean;
import org.json.JSONObject;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/26
@@ -18,13 +20,17 @@ public class LoginContract {
void fail(String msg);
}
public interface DataModel{
//手机验证码登录
void register(JSONObject json, CallBack callBack);
//获取手机验证码
void getPhoneCode(JSONObject json, CallBack callBack);
void getPhoneCode(Map<String,Object> map, CallBack callBack);
//手机验证码登录
void loginBySmsCode(JSONObject json, CallBack callBack);
}
public interface LoginView extends IView{
void registerSuccess(BaseBean bean);
//获取验证码
void getPhoneCodeSuccess(BaseBean bean);
//验证码登录成功

View File

@@ -7,6 +7,8 @@ import com.ckkj.water.network.NetWorkManager;
import org.json.JSONObject;
import java.util.Map;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
@@ -21,15 +23,57 @@ import io.reactivex.schedulers.Schedulers;
public class LoginImpl implements LoginContract.DataModel {
/**
* 获取验证码
*
* 注册
* @param json
* @param callBack
*/
@Override
public void getPhoneCode(JSONObject json, LoginContract.CallBack callBack) {
public void register(JSONObject json, LoginContract.CallBack callBack) {
try {
NetWorkManager.getRequest().sendPhoneCode(NetWorkManager.getToken(), NetWorkManager.toRequestBody(json))
NetWorkManager.getRequest().register(NetWorkManager.toRequestBody(json))
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean bean) {
if (bean.getCode() == 200) {
callBack.success(bean.getData());
// 登录成功时调用
LoginStateManager.reset();
} else {
callBack.fail(bean.getMessage());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* 获取验证码
*
* @param map
* @param callBack
*/
@Override
public void getPhoneCode(Map<String,Object> map, LoginContract.CallBack callBack) {
try {
NetWorkManager.getRequest().sendPhoneCode(NetWorkManager.getToken(), map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())

View File

@@ -1,16 +1,9 @@
package com.ckkj.water.login.mvp;
import com.ckkj.water.AppConfig;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.EventMessage;
import com.ckkj.water.MyApplication;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.login.entity.LoginEntity;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import org.json.JSONException;
import org.json.JSONObject;
@@ -18,8 +11,6 @@ import org.json.JSONObject;
import java.util.HashMap;
import java.util.Map;
import de.greenrobot.event.EventBus;
/**
* @author fengxiaoyang
* @date 2025/7/26
@@ -33,16 +24,26 @@ public class LoginPresenter extends BasePresenter<LoginContract.LoginView> {
this.mImpl = mImpl;
}
public void getPhoneCode(String phone, String codeType) {
/**
* 注册
* @param account
* @param code
* @param psd
*/
public void registerAccount(String account, String code, String psd) {
try {
JSONObject json = new JSONObject();
json.put("mobile",phone);
json.put("type",codeType);
mImpl.getPhoneCode(json, new LoginContract.CallBack<BaseBean>() {
json.put("clientId",AppConfig.APP_CLIENT_ID);
json.put("username",account);
json.put("code",code);
json.put("password",psd);
json.put("grantType",psd);
json.put("userType",AppConfig.APP_USER_TYPE);
mImpl.register(json, new LoginContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if(LoginPresenter.this.getView() != null){
LoginPresenter.this.getView().getPhoneCodeSuccess(bean);
LoginPresenter.this.getView().registerSuccess(bean);
}
}
@@ -53,27 +54,57 @@ public class LoginPresenter extends BasePresenter<LoginContract.LoginView> {
}
}
});
} catch (JSONException e) {
throw new RuntimeException(e);
}
}
public void getPhoneCode(String phone, String codeType) {
Map<String,Object> map = new HashMap<>();
map.put("username",phone);
mImpl.getPhoneCode(map, new LoginContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if(LoginPresenter.this.getView() != null){
LoginPresenter.this.getView().getPhoneCodeSuccess(bean);
}
}
@Override
public void fail(String msg) {
if(LoginPresenter.this.getView() != null){
LoginPresenter.this.getView().showError(msg);
}
}
});
}
/**
* 通过手机验证码登录
* @param phone
* @param account
* @param code
*/
public void loginBySmsCode(String phone, String code) {
public void loginBySmsCode(String loginType,String account, String code,String psd) {
try {
JSONObject json = new JSONObject();
json.put("mobile",phone);
json.put("code",code);
json.put("grantType",loginType);
if(loginType.equals("sms")){
json.put("phonenumber",account);
json.put("smsCode",code);
}else{
json.put("username",account);
json.put("password",psd);
}
json.put("clientId",AppConfig.APP_CLIENT_ID);
json.put("userType",AppConfig.APP_USER_TYPE);
mImpl.loginBySmsCode(json, new LoginContract.CallBack<LoginEntity>() {
@Override
public void success(LoginEntity bean) {
if(LoginPresenter.this.getView() != null){
LoginPresenter.this.getView().loginBySmsCodeSuccess(bean);
EventBus.getDefault().post(new EventMessage(EventMessage.USER_LOGIN_SUCCESS));
// EventBus.getDefault().post(new EventMessage(EventMessage.USER_LOGIN_SUCCESS));
//获取个人信息
// getUserInfo();
}
@@ -113,4 +144,6 @@ public class LoginPresenter extends BasePresenter<LoginContract.LoginView> {
// }
// });
}
}

View File

@@ -25,21 +25,17 @@ import com.ckkj.water.R;
import com.ckkj.water.adapter.ViewPageAdapter;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.chat.ChatFragment;
import com.ckkj.water.databinding.MainActivityLayoutBinding;
import com.ckkj.water.dialog.DialogAppUpdate;
import com.ckkj.water.fate.view.FateFragment;
import com.ckkj.water.main.MainContract;
import com.ckkj.water.main.MainImpl;
import com.ckkj.water.main.MainPresenter;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.MineFragment;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.plate.PlateFragment;
import com.ckkj.water.utils.AppInfoUtil;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.show.ToastUtil;
import org.jetbrains.annotations.NotNull;
@@ -109,7 +105,7 @@ public class MainActivity extends BaseActivity<MainActivityLayoutBinding, MainPr
@Override
public void initData(Bundle savedInstanceState) {
super.initData(savedInstanceState);
mPresenter.checkNewVersion();
// mPresenter.checkNewVersion();
// 清空Fragment列表避免状态恢复问题
mFragmentList.clear();
mFragmentList.add(new IndexFragment());
@@ -233,8 +229,6 @@ public class MainActivity extends BaseActivity<MainActivityLayoutBinding, MainPr
// 设置底部导航栏选中状态
viewBinding.navView.setSelectedItemId(R.id.navigation_index);
// 将参数传递给IndexFragment
passBundleToIndexFragment(extras);
});
}
}
@@ -253,28 +247,10 @@ public class MainActivity extends BaseActivity<MainActivityLayoutBinding, MainPr
// 设置底部导航栏选中状态
viewBinding.navView.setSelectedItemId(R.id.navigation_index);
// 将参数传递给IndexFragment
passBundleToIndexFragment(extras);
});
}
}
/**
* 将Bundle参数传递给IndexFragment
*/
private void passBundleToIndexFragment(Bundle bundle) {
// 获取IndexFragment实例
Fragment indexFragment = mFragmentList.get(1);
if (indexFragment instanceof ChatFragment) {
// 设置参数到Fragment
indexFragment.setArguments(bundle);
// 如果Fragment已经创建可以调用其方法来处理参数
if (indexFragment.isAdded()) {
((ChatFragment) indexFragment).handleBirthInfoBundle(bundle);
}
}
}
@Override
@@ -289,9 +265,7 @@ public class MainActivity extends BaseActivity<MainActivityLayoutBinding, MainPr
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
if(bean != null){
MingDengUserInfoManager.getInstance().setUserInfo(bean.getUserInfo());
SharePreUtil.putBoolean(ConstantUtil.SHARE_PRE_NAME,mContext,ConstantUtil.USER_HAS_SET_BIRTH,bean.isHasEightCharacters());
AppConfig.USER_SET_BIRTH_INFO = bean.isHasEightCharacters();
WaterUserInfoManager.getInstance().setUserInfo(bean);
}
}

View File

@@ -5,6 +5,7 @@ import android.view.View;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.AppThemeChangeLayoutBinding;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
@@ -96,4 +97,9 @@ public class AppThemActivity extends BaseActivity<AppThemeChangeLayoutBinding, M
public void logOut(BaseBean bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -2,30 +2,22 @@ package com.ckkj.water.mine;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.Handler;
import android.text.TextUtils;
import android.view.View;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.AppConfig;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.ChangePhoneActivityBinding;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.number.PhoneNumberUtils;
import com.ckkj.water.utils.show.ToastUtil;
import java.util.List;
/**
* @Description TODO
@@ -54,7 +46,6 @@ public class ChangePhoneActivity extends BaseActivity<ChangePhoneActivityBinding
.titleBar(viewBinding.rlTitle)
.init();
viewBinding.includeTitle.tvTitle.setText("更换手机号");
viewBinding.tvUserPhone.setText(MingDengUserInfoManager.getInstance().getUserInfo().getMobile());
initListener();
}
@@ -140,4 +131,9 @@ public class ChangePhoneActivity extends BaseActivity<ChangePhoneActivityBinding
public void logOut(BaseBean bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -5,6 +5,8 @@ import static android.view.View.INVISIBLE;
import android.os.Bundle;
import android.view.View;
import com.ckkj.water.AppConfig;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.base.entity.MineUserInfoBean;
@@ -16,8 +18,11 @@ import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.ThemeManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.google.gson.Gson;
import com.gyf.immersionbar.ImmersionBar;
import com.lxj.xpopup.XPopup;
import com.lxj.xpopup.interfaces.OnSelectListener;
@@ -43,6 +48,14 @@ public class MineCenterFragment extends BaseFragment<MineFragmentLayoutBinding,
initListener();
}
@Override
protected void onResumeInitData() {
super.onResumeInitData();
if(AppConfig.USER_LOGIN){
mPresenter.getUserinfo();
}
}
private void initListener() {
setClick(viewBinding.imgAvatar);
setClick(viewBinding.linearLanguage);
@@ -91,6 +104,19 @@ public class MineCenterFragment extends BaseFragment<MineFragmentLayoutBinding,
}
}
/**
* 获取个人信息
* @param bean
*/
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
Gson gson = new Gson();
String userInfoJson = gson.toJson(bean);
SharePreUtil.putString(ConstantUtil.SHARE_PRE_NAME,mContext,ConstantUtil.USER_INFO_JSON_CONTENT,userInfoJson);
WaterUserInfoManager.getInstance().setUserInfo(bean);
}
@Override
public MinePresenter createPresenter() {
return new MinePresenter(new MineImpl());
@@ -111,4 +137,5 @@ public class MineCenterFragment extends BaseFragment<MineFragmentLayoutBinding,
public void logOut(BaseBean bean) {
}
}

View File

@@ -14,19 +14,16 @@ import androidx.annotation.Nullable;
import com.alibaba.sdk.android.oss.ClientException;
import com.alibaba.sdk.android.oss.ServiceException;
import com.bumptech.glide.Glide;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.esafirm.imagepicker.features.ImagePicker;
import com.esafirm.imagepicker.model.Image;
import com.ckkj.water.AppConfig;
import com.ckkj.water.EventMessage;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.base.inter.UploadCallback;
import com.ckkj.water.databinding.MineFragmentBinding;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
@@ -35,10 +32,9 @@ import com.ckkj.water.utils.LubanCompressUtil;
import com.ckkj.water.utils.PreviewFileUtil;
import com.ckkj.water.utils.click.ClickUtil;
import com.ckkj.water.utils.dataUtil.FileUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.oss.OssUploadHelper;
import com.ckkj.water.utils.show.ToastUtil;
import com.ckkj.water.utils.time.ZYTimeUtils;
import com.lxj.xpopup.XPopup;
import com.lxj.xpopup.interfaces.OnSelectListener;
import com.yalantis.ucrop.UCrop;
@@ -112,8 +108,8 @@ public class MineFragment extends BaseFragment<MineFragmentBinding, MinePresente
}
break;
case 1:
String suffix = FileUtil.getFileSuffixWithQuestion(MingDengUserInfoManager.getInstance().getUserInfo().getAvatar());
PreviewFileUtil.previewFiles(mContext, suffix, MingDengUserInfoManager.getInstance().getUserInfo().getAvatar());
// String suffix = FileUtil.getFileSuffixWithQuestion(WaterUserInfoManager.getInstance().getUserInfo().getAvatar());
// PreviewFileUtil.previewFiles(mContext, suffix, WaterUserInfoManager.getInstance().getUserInfo().getAvatar());
break;
}
}
@@ -266,4 +262,8 @@ public class MineFragment extends BaseFragment<MineFragmentBinding, MinePresente
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -3,21 +3,16 @@ package com.ckkj.water.mine;
import android.Manifest;
import android.content.Intent;
import android.os.Bundle;
import android.text.TextUtils;
import android.view.View;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.alibaba.sdk.android.oss.ClientException;
import com.alibaba.sdk.android.oss.ServiceException;
import com.bumptech.glide.Glide;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.MineInformationLayoutBinding;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
@@ -25,7 +20,7 @@ import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.LubanCompressUtil;
import com.ckkj.water.utils.PreviewFileUtil;
import com.ckkj.water.utils.dataUtil.FileUtil;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.show.ToastUtil;
import com.esafirm.imagepicker.features.ImagePicker;
import com.esafirm.imagepicker.model.Image;
@@ -34,7 +29,6 @@ import com.lxj.xpopup.XPopup;
import com.lxj.xpopup.interfaces.OnSelectListener;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import pub.devrel.easypermissions.EasyPermissions;
@@ -98,8 +92,8 @@ public class MineInfomationActivity extends BaseActivity<MineInformationLayoutBi
}
break;
case 1:
String suffix = FileUtil.getFileSuffixWithQuestion(MingDengUserInfoManager.getInstance().getUserInfo().getAvatar());
PreviewFileUtil.previewFiles(mContext, suffix, MingDengUserInfoManager.getInstance().getUserInfo().getAvatar());
// String suffix = FileUtil.getFileSuffixWithQuestion(WaterUserInfoManager.getInstance().getUserInfo().getAvatar());
// PreviewFileUtil.previewFiles(mContext, suffix, WaterUserInfoManager.getInstance().getUserInfo().getAvatar());
break;
}
}
@@ -211,4 +205,9 @@ public class MineInfomationActivity extends BaseActivity<MineInformationLayoutBi
}
}
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -5,6 +5,7 @@ import android.view.View;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.PasswordManLayoutBinding;
import com.ckkj.water.login.ForgetPasswordActivity;
import com.ckkj.water.mine.mvp.MineContract;
@@ -79,4 +80,9 @@ public class PsdManageActivity extends BaseActivity<PasswordManLayoutBinding, Mi
public void logOut(BaseBean bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -6,6 +6,7 @@ import android.view.View;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.ResetPsdLayoutBinding;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
@@ -95,4 +96,9 @@ public class ResetPsdActivity extends BaseActivity<ResetPsdLayoutBinding, MinePr
public void logOut(BaseBean bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -6,29 +6,25 @@ import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.AppConfig;
import com.ckkj.water.EventMessage;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.ActivitySettingsLayoutBinding;
import com.ckkj.water.dialog.DialogAppUpdate;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.AppInfoUtil;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.show.ToastUtil;
import java.io.File;
import java.util.List;
import de.greenrobot.event.EventBus;
@@ -54,7 +50,7 @@ public class SettingsActivity extends BaseActivity<ActivitySettingsLayoutBinding
viewBinding.includeTitle.tvTitle.setText("设置");
viewBinding.includeTitle.imgBack.setOnClickListener(c -> finish());
if(AppConfig.USER_LOGIN){
viewBinding.tvUserPhone.setText(MingDengUserInfoManager.getInstance().getUserInfo().getMobile());
// viewBinding.tvUserPhone.setText(WaterUserInfoManager.getInstance().getUserInfo().getMobile());
viewBinding.tvLogOut.setVisibility(View.VISIBLE);
}
//获取本应用所占用的缓存
@@ -119,7 +115,7 @@ public class SettingsActivity extends BaseActivity<ActivitySettingsLayoutBinding
@Override
public void onConfirmClick() {
MingDengUserInfoManager.getInstance().clearUser(mContext);
WaterUserInfoManager.getInstance().clearUser(mContext);
ActivityManager.removeAllActivity();
goTo(mContext, LoginActivity.class,null);
EventBus.getDefault().post(new EventMessage(EventMessage.USER_LOGIN_LOST));
@@ -205,4 +201,9 @@ public class SettingsActivity extends BaseActivity<ActivitySettingsLayoutBinding
}
return dir.delete();
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -2,30 +2,23 @@ package com.ckkj.water.mine;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.Handler;
import android.text.TextUtils;
import android.view.View;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.gyf.immersionbar.ImmersionBar;
import com.ckkj.water.AppConfig;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseActivity;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.databinding.UserLogOffActivityBinding;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.mvp.MineContract;
import com.ckkj.water.mine.mvp.MineImpl;
import com.ckkj.water.mine.mvp.MinePresenter;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.ActivityManager;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.ckkj.water.utils.number.PhoneNumberUtils;
import com.ckkj.water.utils.show.ToastUtil;
import java.util.List;
/**
* @Description 用户注销账号
@@ -56,10 +49,10 @@ public class UserLogOffAccountActivity extends BaseActivity<UserLogOffActivityBi
.init();
viewBinding.includeTitle.tvTitle.setText("注销账号");
if(AppConfig.USER_LOGIN){
String phoneNum = MingDengUserInfoManager.getInstance().getUserInfo().getMobile();
if(!TextUtils.isEmpty(phoneNum)){
viewBinding.tvUserPhone.setText(PhoneNumberUtils.hidePhoneNumber(phoneNum));
}
// String phoneNum = WaterUserInfoManager.getInstance().getUserInfo().getMobile();
// if(!TextUtils.isEmpty(phoneNum)){
// viewBinding.tvUserPhone.setText(PhoneNumberUtils.hidePhoneNumber(phoneNum));
// }
}
}
@@ -118,4 +111,9 @@ public class UserLogOffAccountActivity extends BaseActivity<UserLogOffActivityBi
public void logOut(BaseBean bean) {
}
@Override
public void getUserInfoSuccess(MineUserInfoBean bean) {
}
}

View File

@@ -27,11 +27,15 @@ public class MineContract {
void fail(String msg);
}
public interface DataModel{
//获取个人信息
void getUserInfo(Map<String,Object> map, CallBack callBack);
}
public interface MineView extends IView {
void getUserInfoSuccess(MineUserInfoBean bean);
}
public interface RecommendModel{

View File

@@ -25,4 +25,38 @@ import io.reactivex.schedulers.Schedulers;
public class MineImpl implements MineContract.DataModel {
/**
* 获取个人信息
* @param map
* @param callBack
*/
@Override
public void getUserInfo(Map<String, Object> map, MineContract.CallBack callBack) {
NetWorkManager.getRequest().getMineUserInfo(NetWorkManager.getToken(), map)
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<BaseBean<MineUserInfoBean>>() {
@Override
public void onSubscribe(@NonNull Disposable d) {
}
@Override
public void onNext(@NonNull BaseBean<MineUserInfoBean> bean) {
if (bean.getCode() == 200) {
callBack.success(bean.getData());
}
}
@Override
public void onError(@NonNull Throwable e) {
callBack.fail(e.getMessage());
}
@Override
public void onComplete() {
}
});
}
}

View File

@@ -2,23 +2,15 @@ package com.ckkj.water.mine.mvp;
import android.text.TextUtils;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.base.entity.UserInfoEntity;
import com.ckkj.water.login.mvp.LoginContract;
import com.ckkj.water.login.mvp.LoginImpl;
import com.ckkj.water.main.MainContract;
import com.ckkj.water.main.MainImpl;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.utils.manager.MingDengUserInfoManager;
import org.json.JSONException;
import org.json.JSONObject;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
import com.ckkj.water.utils.manager.WaterUserInfoManager;
import com.google.gson.Gson;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
@@ -38,4 +30,23 @@ public class MinePresenter extends BasePresenter<MineContract.MineView> {
/**
* 获取个人信息
*/
public void getUserinfo() {
Map<String,Object> map = new HashMap<>();
impl.getUserInfo(map, new MineContract.CallBack<MineUserInfoBean>() {
@Override
public void success(MineUserInfoBean bean) {
if(MinePresenter.this.getView() != null){
MinePresenter.this.getView().getUserInfoSuccess(bean);
}
}
@Override
public void fail(String msg) {
if(MinePresenter.this.getView() != null){
MinePresenter.this.getView().showError(msg);
}
}
});
}
}

View File

@@ -20,6 +20,8 @@ public class BaseBean<T> implements Serializable {
private String msg;
private int code;
private T data;
private T rows;
private int pages;
private int total;
private int size;
@@ -47,6 +49,10 @@ public class BaseBean<T> implements Serializable {
this.code = code;
}
public T getRows() {
return rows;
}
public T getData() {
return data;
}

View File

@@ -337,6 +337,7 @@ public class NetWorkManager {
Map<String, String> map = new HashMap<>();
try {
map.put("Authorization", "Bearer " + AppConfig.USER_TOKEN);
map.put("clientId", AppConfig.APP_CLIENT_ID);
// map.put("Authorization", "Bearer " + "eyJhbGciOiJIUzUxMiJ9.eyJ1c2VyX2lkIjoxOTI1NzYwMTgxMTMyNzI2MDIyLCJ1c2VyX2tleSI6IjY0YjVmMjRjLTIyM2ItNDRkZC1iMDJlLTI0ZTRiNzNmODgxZCIsInVzZXJuYW1lIjoiMTg2NDU5MDQzMDIifQ.PiIjBZlQ9UtOuotfhd5mZZO2e8SbMpbXU7VDvVeiWZIecsFDUd51Rae09EFxQ_MJmBUEvIdyysnyqYiBC2AEfw");
} catch (Exception e) {
e.printStackTrace();

View File

@@ -3,19 +3,9 @@ package com.ckkj.water.network;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.chat.entity.ChatQuestionEntity;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.fate.entity.FateHistoryEntity;
import com.ckkj.water.fate.entity.TodayFateEntity;
import com.ckkj.water.chat.entity.CharHistoryEntity;
import com.ckkj.water.chat.entity.ChatAiMsgEntity;
import com.ckkj.water.chat.entity.IndexTemplateEntity;
import com.ckkj.water.index.entity.IndexDeviceEntity;
import com.ckkj.water.login.entity.LoginEntity;
import com.ckkj.water.main.entity.CheckVersionEntity;
import com.ckkj.water.mine.entity.InviteeRecordEntity;
import com.ckkj.water.mine.entity.MemberComboEntity;
import com.ckkj.water.mine.entity.RecommendDataEntity;
import com.ckkj.water.mine.entity.RewardRecordEntity;
import com.ckkj.water.plate.entity.BaziResultBean;
import com.ckkj.water.plate.entity.BaziSaveSuccessEntity;
import com.ckkj.water.plate.entity.PaipanHistoryEntity;
@@ -36,66 +26,38 @@ import retrofit2.http.QueryMap;
*/
public interface Request {
//发送验证码
@GET("resource/code")
Observable<BaseBean> sendPhoneCode(@HeaderMap Map<String, String> headMap,@QueryMap Map<String, Object> map);
//注册
@POST("user/api/adduser")
Observable<BaseBean> register(@QueryMap Map<String, Object> map);
//获取验证码
@POST("user/api/phone")
Observable<BaseBean> getSmsCode(@QueryMap Map<String, Object> map);
//版本检测更新
@POST("auth/register")
Observable<BaseBean> register(@Body RequestBody requestBody);
//登录
@POST("auth/login")
Observable<BaseBean<LoginEntity>> loginBySmsCode(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//获取个人信息
@GET("app/v1/getUserInfo")
Observable<BaseBean<MineUserInfoBean>> getMineUserInfo(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//首页设备列表
@GET("app/v1/deviceList")
Observable<BaseBean<List<IndexDeviceEntity>>> getIndexDeviceList(@HeaderMap Map<String, String> headMap);
//添加设备
@POST("app/v1/addDevice")
Observable<BaseBean> addDevice(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
@POST("mobile/version?end=android")
Observable<BaseBean<CheckVersionEntity>> checkVersionCode(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//输入激活码,临时会员
@POST("user/api/useActivationCode")
Observable<BaseBean> activationVip(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//版本检测更新
@POST("mine/api/versionNum")
Observable<BaseBean<CheckVersionEntity>> getVersionCheck(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//版本检测更新
@POST("mobile/context")
Observable<BaseBean<ChatAiMsgEntity>> indexTalkToAi(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//首页模板消息数据获取
@POST("mobile/homeInfo")
Observable<BaseBean<List<IndexTemplateEntity>>> getIndexTemplateDatas();
//会话底部模板数据获取
@POST("mobile/aitebcontent")
Observable<BaseBean<List<ChatQuestionEntity>>> aitebcontent();
//对话历史记录
@POST("mobile/mySessions")
Observable<BaseBean<CharHistoryEntity>> getHistoryList(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//删除历史记录
@POST("mobile/deleteSession")
Observable<BaseBean> deleteHistoryBySessionID(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//根据 id 查询会话详情
@POST("mobile/sessionMessages")
Observable<BaseBean<List<ChatAiMsgEntity>>> getChatDetailById(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//获取城市列表
@GET("mobile/chinaCites")
Observable<BaseBean<List<CityDataEntity>>> getCityDatas(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//保存用户的生辰八字
@POST("mobile/yourhoroscope")
Observable<BaseBean> saveUserBirthInfo(@HeaderMap Map<String, String> headMap,@Body RequestBody requestBody);
//修改用户的生辰八字
@POST("mobile/yourhoroscope/modify")
Observable<BaseBean<TodayFateEntity>> saveUserEditBirthInfo(@HeaderMap Map<String, String> headMap,@Body RequestBody requestBody);
//发送验证码
@POST("mobile/sendCode")
Observable<BaseBean> sendPhoneCode(@HeaderMap Map<String, String> headMap,@Body RequestBody requestBody);
//登录
@POST("mobile/login")
Observable<BaseBean<LoginEntity>> loginBySmsCode(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//获取个人信息
@GET("mobile/userInfo")
Observable<BaseBean<MineUserInfoBean>> getMineUserInfo(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//更新用户头像
@POST("mobile/modifyAvatar")
Observable<BaseBean> updateUseravatar(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//获取今日运势
@POST("mobile/yourhoroscope/today")
Observable<BaseBean<TodayFateEntity>> getUserTodayFateDatas(@HeaderMap Map<String, String> headMap);
//获取运势历史列表
@GET("mobile/yourhoroscope/history")
Observable<BaseBean<FateHistoryEntity>> getUserFateHistory(@HeaderMap Map<String, String> headMap);
//保存排盘结果
@POST("mobile/paiPan")
Observable<BaseBean<BaziSaveSuccessEntity>> startPaipan(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
@@ -111,35 +73,7 @@ public interface Request {
//删除历史记录
@POST("mobile/paiPan/record")
Observable<BaseBean> deletePaipanRecordById(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//修改手机号
@POST("mobile/modifyPhone")
Observable<BaseBean> modifyPhone(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//注销账号
@POST("mobile/DeactivateAccount")
Observable<BaseBean> logoffAccount(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//查询会员套餐
@GET("mobile/memberInFo")
Observable<BaseBean<List<MemberComboEntity>>> getMemberComboList(@HeaderMap Map<String, String> headMap);
//获取支付信息
@POST("mobile/alipay")
Observable<BaseBean> getPayOrderInfo(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//问题反馈
@POST("mobile/appfeedback")
Observable<BaseBean> commitFeedback(@HeaderMap Map<String, String> headMap,@QueryMap Map<String, Object> map);
//问题反馈
@POST("mobile/reporting")
Observable<BaseBean> commitReporting(@HeaderMap Map<String, String> headMap,@QueryMap Map<String, Object> map);
//邀请数据
@GET("mobile/invitationStatistics")
Observable<BaseBean<RecommendDataEntity>> getRecommendDatas(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//邀请记录
@GET("mobile/myInvitees")
Observable<BaseBean<InviteeRecordEntity>> myInvitees(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
//注销账号
@POST("mobile/bind")
Observable<BaseBean> bindInvterCode(@HeaderMap Map<String, String> headMap, @Body RequestBody requestBody);
//奖励记录
@GET("mobile/rewardHistoryDetail")
Observable<BaseBean<RewardRecordEntity>> getRewardRecords(@HeaderMap Map<String, String> headMap, @QueryMap Map<String, Object> map);
/***************************钱包********************************/
}

View File

@@ -72,12 +72,11 @@ public class PermissionActivity extends BaseActivity<PermissionLayoutBinding, Ma
case R.id.tv_commit:
String[] permission = {
Manifest.permission.BLUETOOTH_SCAN,
Manifest.permission.ACCESS_FINE_LOCATION
};
boolean hasPermission = hasRecordPermission(permission);
if(!hasPermission){
getMorePermissionRequst(permission,"权限申请","智溉管家需要您的授权获取以下权限",REQUEST_EVENT_CODE_10001);
getMorePermissionRequst(permission,"权限申请","智溉管家需要您的授权获取位置权限,用于添加设备",REQUEST_EVENT_CODE_10001);
}
break;
}
@@ -128,7 +127,7 @@ public class PermissionActivity extends BaseActivity<PermissionLayoutBinding, Ma
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
if (requestCode == REQUEST_EVENT_CODE_10001) {
ToastUtil.showShort(mContext,"权限获取成功");
hidePermissionDialog();
finish();
}
}

View File

@@ -1,114 +1,114 @@
package com.ckkj.water.plate;
import android.os.Bundle;
import android.view.View;
import androidx.annotation.NonNull;
import androidx.fragment.app.Fragment;
import com.ckkj.water.AppConfig;
import com.ckkj.water.R;
import com.ckkj.water.base.BaseFragment;
import com.ckkj.water.databinding.PlateFragmentBinding;
import com.ckkj.water.login.LoginActivity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.plate.adapter.ViewPagerAdapter;
import com.ckkj.water.plate.entity.BaziResultBean;
import com.ckkj.water.plate.entity.BaziSaveSuccessEntity;
import com.ckkj.water.plate.entity.PaipanHistoryEntity;
import com.ckkj.water.plate.mvp.PlateContract;
import com.ckkj.water.plate.mvp.PlateImpl;
import com.ckkj.water.plate.mvp.PlatePresenter;
import java.util.ArrayList;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/7/30
* @description TODO: 排盘页面
*/
public class PlateFragment extends BaseFragment<PlateFragmentBinding, PlatePresenter>
implements PlateContract.PlateView {
private List<Fragment> mFragmentList = new ArrayList<>();
@Override
public PlatePresenter createPresenter() {
return new PlatePresenter(new PlateImpl());
}
@Override
public void initData(Bundle state) {
viewBinding.includedTitle.imgBack.setVisibility(View.GONE);
viewBinding.includedTitle.tvTitle.setText("信息录入");
ViewPagerAdapter adapter = new ViewPagerAdapter(this, mFragmentList);
viewBinding.viewpage.setAdapter(adapter);
viewBinding.tvPaipan.setSelected(true);
viewBinding.viewpage.setCurrentItem(0);
//viewpage2 特有的 api禁止滑动
viewBinding.viewpage.setUserInputEnabled(false);
}
@Override
public void onNetChange(int netModel) {
}
@Override
public void showError(String message) {
}
@Override
public void logOut(BaseBean bean) {
}
@Override
public void getPaipanResult(BaziResultBean bean) {
}
@Override
public void saveBaziResultSuccess(BaziSaveSuccessEntity bean) {
}
@Override
public void getHistorySuccess(PaipanHistoryEntity entity) {
}
@Override
public void deletePaipanHistorySuccess(int pos) {
}
@Override
public void onStreamMessageReceived(String messageChunk) {
}
@Override
public void onStreamComplete(String complateMsg) {
}
@Override
public void commitReportSuccess(BaseBean bean) {
}
@Override
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
}
@Override
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
}
}
//package com.ckkj.water.plate;
//
//import android.os.Bundle;
//import android.view.View;
//
//import androidx.annotation.NonNull;
//import androidx.fragment.app.Fragment;
//
//import com.ckkj.water.AppConfig;
//import com.ckkj.water.R;
//import com.ckkj.water.base.BaseFragment;
//import com.ckkj.water.databinding.PlateFragmentBinding;
//import com.ckkj.water.login.LoginActivity;
//import com.ckkj.water.network.BaseBean;
//import com.ckkj.water.plate.adapter.ViewPagerAdapter;
//import com.ckkj.water.plate.entity.BaziResultBean;
//import com.ckkj.water.plate.entity.BaziSaveSuccessEntity;
//import com.ckkj.water.plate.entity.PaipanHistoryEntity;
//import com.ckkj.water.plate.mvp.PlateContract;
//import com.ckkj.water.plate.mvp.PlateImpl;
//import com.ckkj.water.plate.mvp.PlatePresenter;
//
//import java.util.ArrayList;
//import java.util.List;
//
//
///**
// * @author fengxiaoyang
// * @date 2025/7/30
// * @description TODO: 排盘页面
// */
//
//public class PlateFragment extends BaseFragment<PlateFragmentBinding, PlatePresenter>
// implements PlateContract.PlateView {
// private List<Fragment> mFragmentList = new ArrayList<>();
//
// @Override
// public PlatePresenter createPresenter() {
// return new PlatePresenter(new PlateImpl());
// }
//
// @Override
// public void initData(Bundle state) {
// viewBinding.includedTitle.imgBack.setVisibility(View.GONE);
// viewBinding.includedTitle.tvTitle.setText("信息录入");
// ViewPagerAdapter adapter = new ViewPagerAdapter(this, mFragmentList);
// viewBinding.viewpage.setAdapter(adapter);
// viewBinding.tvPaipan.setSelected(true);
// viewBinding.viewpage.setCurrentItem(0);
// //viewpage2 特有的 api禁止滑动
// viewBinding.viewpage.setUserInputEnabled(false);
// }
//
//
// @Override
// public void onNetChange(int netModel) {
//
// }
//
// @Override
// public void showError(String message) {
//
// }
//
// @Override
// public void logOut(BaseBean bean) {
//
// }
//
// @Override
// public void getPaipanResult(BaziResultBean bean) {
//
// }
//
// @Override
// public void saveBaziResultSuccess(BaziSaveSuccessEntity bean) {
//
// }
//
// @Override
// public void getHistorySuccess(PaipanHistoryEntity entity) {
//
// }
//
// @Override
// public void deletePaipanHistorySuccess(int pos) {
//
// }
//
// @Override
// public void onStreamMessageReceived(String messageChunk) {
//
// }
//
// @Override
// public void onStreamComplete(String complateMsg) {
//
// }
//
// @Override
// public void commitReportSuccess(BaseBean bean) {
//
// }
//
// @Override
// public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
//
// }
//
// @Override
// public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
//
// }
//}

View File

@@ -1,228 +1,225 @@
package com.ckkj.water.plate.mvp;
import com.ckkj.water.base.BasePresenter;
import com.ckkj.water.chat.mvp.IndexContract;
import com.ckkj.water.chat.mvp.IndexImpl;
import com.ckkj.water.fate.entity.CityDataEntity;
import com.ckkj.water.network.BaseBean;
import com.ckkj.water.plate.entity.BaziResultBean;
import com.ckkj.water.plate.entity.BaziSaveSuccessEntity;
import com.ckkj.water.plate.entity.PaipanHistoryEntity;
import org.json.JSONException;
import org.json.JSONObject;
import java.util.HashMap;
import java.util.Map;
/**
* @author fengxiaoyang
* @date 2025/7/30
* @description TODO: 描述该类的作用
*/
public class PlatePresenter extends BasePresenter<PlateContract.PlateView> {
private PlateImpl impl;
public PlatePresenter(PlateImpl impl) {
this.impl = impl;
}
/**
* 排盘,直接调用缘份居 Api
* @param map
*/
public void startPaiPan(Map<String, Object> map) {
impl.startPaiPanByYfjApi(map, new PlateContract.CallBack<BaziResultBean>() {
@Override
public void success(BaziResultBean entity) {
if(PlatePresenter.this.getView() != null){
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().getPaipanResult(entity);
}
}
}
@Override
public void fail(String msg) {
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 上传八字结果
*
* @param result
* @param cityData
* @param timeType
*/
public void uploadBaziResult(BaziResultBean result, CityDataEntity cityData, int timeType) {
try {
BaziResultBean.BaseInfoDTO baseInfoDTO = result.getBaseInfo();
BaziResultBean.DetailInfoDTO.SizhuInfoDTO sizhuInfoDTO = result.getDetailInfo().getSizhuInfo();
JSONObject json = new JSONObject();
json.put("name",baseInfoDTO.getName());
json.put("gender",baseInfoDTO.getSex().equals("乾造")? "0" : "1");
json.put("birthType",timeType == 2001 ? "1":"0");
json.put("yangLiBirthTime",baseInfoDTO.getGongli());
json.put("yinLiBirthTime",baseInfoDTO.getNongli());
json.put("birthPlace",cityData == null ? "北京市": cityData.getCityName());
json.put("province",cityData == null ? "北京市": cityData.getProvinceName());
json.put("city",cityData == null ? "北京": cityData.getCityName());
json.put("openSolarTime","2");
json.put("nianZhu",sizhuInfoDTO.getYear().getTg() + "," + sizhuInfoDTO.getYear().getDz());
json.put("yueZhu",sizhuInfoDTO.getMonth().getTg() + "," + sizhuInfoDTO.getMonth().getDz());
json.put("riZhu",sizhuInfoDTO.getDay().getTg() + "," + sizhuInfoDTO.getDay().getDz());
json.put("shiZhu",sizhuInfoDTO.getHour().getTg() + "," + sizhuInfoDTO.getHour().getDz());
impl.saveUserBirthInfo(json, new PlateContract.CallBack<BaziSaveSuccessEntity>() {
@Override
public void success(BaziSaveSuccessEntity bean) {
if(PlatePresenter.this.getView() != null){
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().saveBaziResultSuccess(bean);
}
}
}
@Override
public void fail(String msg) {
if(PlatePresenter.this.getView() != null){
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().showError(msg);
}
}
}
});
} catch (JSONException e) {
throw new RuntimeException(e);
}
}
/**
* 获取历史运势
* @param page
*/
public void getHistoryDatas(int page) {
Map<String, Object> map = new HashMap<>();
map.put("pageNum", page);
map.put("pageSize", 10);
impl.getPaipanHistoryList(map, new PlateContract.CallBack<PaipanHistoryEntity>() {
@Override
public void success(PaipanHistoryEntity entity) {
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().getHistorySuccess(entity);
}
}
@Override
public void fail(String msg) {
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* 删除记录
* @param id
*/
public void deleteRecordByID(String id,int pos) {
Map<String, Object> map = new HashMap<>();
map.put("recordId", id);
impl.deleteRecordByID(map, new PlateContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().deletePaipanHistorySuccess(pos);
}
}
@Override
public void fail(String msg) {
if(PlatePresenter.this.getView() != null){
PlatePresenter.this.getView().showError(msg);
}
}
});
}
/**
* ai 分析八字
* @param mSaveEntity
*/
public void AiParseBaziResult(BaziSaveSuccessEntity mSaveEntity) {
try {
JSONObject json = new JSONObject();
json.put("resultId", mSaveEntity.getRecordId());
impl.sendMsgToAi(json, new PlateContract.AiStreamCallback() {
@Override
public void onMessage(String messageChunk) {
if (PlatePresenter.this.getView() != null) {
PlatePresenter.this.getView().onStreamMessageReceived(messageChunk);
}
}
@Override
public void onError(String error) {
if (PlatePresenter.this.getView() != null) {
PlatePresenter.this.getView().showError(error);
}
}
@Override
public void onComplete(String complateContent) {
if (PlatePresenter.this.getView() != null) {
PlatePresenter.this.getView().onStreamComplete(complateContent);
}
}
@Override
public void onSessionReceived(String sessionId) {
// 这个回调在当前场景下可能不需要,但保留接口一致性
// Log.d("PlatePresenter", "Session received: " + sessionId);
}
@Override
public void loginLost() {
if (PlatePresenter.this.getView() != null) {
// 处理登录失效的情况
// 这里可以根据需要跳转到登录页面
// Log.w("PlatePresenter", "Login lost");
}
}
});
} catch (JSONException e) {
throw new RuntimeException(e);
}
}
/**
* 举报
* @param reason
*/
public void commitReport(String reason) {
Map<String, Object> map = new HashMap<>();
map.put("content", reason);
new IndexImpl().commitReport(map, new IndexContract.CallBack<BaseBean>() {
@Override
public void success(BaseBean bean) {
if (PlatePresenter.this.getView() != null) {
PlatePresenter.this.getView().commitReportSuccess(bean);
}
}
@Override
public void fail(String msg) {
if (PlatePresenter.this.getView() != null) {
PlatePresenter.this.getView().showError(msg);
}
}
});
}
}
//package com.ckkj.water.plate.mvp;
//
//import com.ckkj.water.base.BasePresenter;
//import com.ckkj.water.network.BaseBean;
//import com.ckkj.water.plate.entity.BaziResultBean;
//import com.ckkj.water.plate.entity.BaziSaveSuccessEntity;
//import com.ckkj.water.plate.entity.PaipanHistoryEntity;
//
//import org.json.JSONException;
//import org.json.JSONObject;
//
//import java.util.HashMap;
//import java.util.Map;
//
///**
// * @author fengxiaoyang
// * @date 2025/7/30
// * @description TODO: 描述该类的作用
// */
//
//public class PlatePresenter extends BasePresenter<PlateContract.PlateView> {
// private PlateImpl impl;
//
// public PlatePresenter(PlateImpl impl) {
// this.impl = impl;
// }
//
// /**
// * 排盘,直接调用缘份居 Api
// * @param map
// */
// public void startPaiPan(Map<String, Object> map) {
// impl.startPaiPanByYfjApi(map, new PlateContract.CallBack<BaziResultBean>() {
// @Override
// public void success(BaziResultBean entity) {
// if(PlatePresenter.this.getView() != null){
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().getPaipanResult(entity);
// }
// }
// }
//
// @Override
// public void fail(String msg) {
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().showError(msg);
// }
// }
// });
// }
//
// /**
// * 上传八字结果
// *
// * @param result
// * @param cityData
// * @param timeType
// */
// public void uploadBaziResult(BaziResultBean result, CityDataEntity cityData, int timeType) {
// try {
// BaziResultBean.BaseInfoDTO baseInfoDTO = result.getBaseInfo();
// BaziResultBean.DetailInfoDTO.SizhuInfoDTO sizhuInfoDTO = result.getDetailInfo().getSizhuInfo();
// JSONObject json = new JSONObject();
// json.put("name",baseInfoDTO.getName());
// json.put("gender",baseInfoDTO.getSex().equals("乾造")? "0" : "1");
// json.put("birthType",timeType == 2001 ? "1":"0");
// json.put("yangLiBirthTime",baseInfoDTO.getGongli());
// json.put("yinLiBirthTime",baseInfoDTO.getNongli());
// json.put("birthPlace",cityData == null ? "北京市": cityData.getCityName());
// json.put("province",cityData == null ? "北京市": cityData.getProvinceName());
// json.put("city",cityData == null ? "北京": cityData.getCityName());
// json.put("openSolarTime","2");
// json.put("nianZhu",sizhuInfoDTO.getYear().getTg() + "," + sizhuInfoDTO.getYear().getDz());
// json.put("yueZhu",sizhuInfoDTO.getMonth().getTg() + "," + sizhuInfoDTO.getMonth().getDz());
// json.put("riZhu",sizhuInfoDTO.getDay().getTg() + "," + sizhuInfoDTO.getDay().getDz());
// json.put("shiZhu",sizhuInfoDTO.getHour().getTg() + "," + sizhuInfoDTO.getHour().getDz());
// impl.saveUserBirthInfo(json, new PlateContract.CallBack<BaziSaveSuccessEntity>() {
// @Override
// public void success(BaziSaveSuccessEntity bean) {
// if(PlatePresenter.this.getView() != null){
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().saveBaziResultSuccess(bean);
// }
// }
// }
//
// @Override
// public void fail(String msg) {
// if(PlatePresenter.this.getView() != null){
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().showError(msg);
// }
// }
// }
// });
// } catch (JSONException e) {
// throw new RuntimeException(e);
// }
// }
//
// /**
// * 获取历史运势
// * @param page
// */
// public void getHistoryDatas(int page) {
// Map<String, Object> map = new HashMap<>();
// map.put("pageNum", page);
// map.put("pageSize", 10);
// impl.getPaipanHistoryList(map, new PlateContract.CallBack<PaipanHistoryEntity>() {
//
// @Override
// public void success(PaipanHistoryEntity entity) {
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().getHistorySuccess(entity);
// }
// }
//
// @Override
// public void fail(String msg) {
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().showError(msg);
// }
// }
// });
// }
//
// /**
// * 删除记录
// * @param id
// */
// public void deleteRecordByID(String id,int pos) {
// Map<String, Object> map = new HashMap<>();
// map.put("recordId", id);
// impl.deleteRecordByID(map, new PlateContract.CallBack<BaseBean>() {
// @Override
// public void success(BaseBean bean) {
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().deletePaipanHistorySuccess(pos);
// }
// }
//
// @Override
// public void fail(String msg) {
// if(PlatePresenter.this.getView() != null){
// PlatePresenter.this.getView().showError(msg);
// }
// }
// });
// }
//
// /**
// * ai 分析八字
// * @param mSaveEntity
// */
// public void AiParseBaziResult(BaziSaveSuccessEntity mSaveEntity) {
// try {
// JSONObject json = new JSONObject();
// json.put("resultId", mSaveEntity.getRecordId());
// impl.sendMsgToAi(json, new PlateContract.AiStreamCallback() {
// @Override
// public void onMessage(String messageChunk) {
// if (PlatePresenter.this.getView() != null) {
// PlatePresenter.this.getView().onStreamMessageReceived(messageChunk);
// }
// }
//
// @Override
// public void onError(String error) {
// if (PlatePresenter.this.getView() != null) {
// PlatePresenter.this.getView().showError(error);
// }
// }
//
// @Override
// public void onComplete(String complateContent) {
// if (PlatePresenter.this.getView() != null) {
// PlatePresenter.this.getView().onStreamComplete(complateContent);
// }
// }
//
// @Override
// public void onSessionReceived(String sessionId) {
// // 这个回调在当前场景下可能不需要,但保留接口一致性
// // Log.d("PlatePresenter", "Session received: " + sessionId);
// }
//
// @Override
// public void loginLost() {
// if (PlatePresenter.this.getView() != null) {
// // 处理登录失效的情况
// // 这里可以根据需要跳转到登录页面
// // Log.w("PlatePresenter", "Login lost");
// }
// }
// });
// } catch (JSONException e) {
// throw new RuntimeException(e);
// }
// }
//
//
// /**
// * 举报
// * @param reason
// */
// public void commitReport(String reason) {
// Map<String, Object> map = new HashMap<>();
// map.put("content", reason);
// new IndexImpl().commitReport(map, new IndexContract.CallBack<BaseBean>() {
// @Override
// public void success(BaseBean bean) {
// if (PlatePresenter.this.getView() != null) {
// PlatePresenter.this.getView().commitReportSuccess(bean);
// }
// }
//
// @Override
// public void fail(String msg) {
// if (PlatePresenter.this.getView() != null) {
// PlatePresenter.this.getView().showError(msg);
// }
// }
// });
// }
//}

View File

@@ -1,171 +1,170 @@
package com.ckkj.water.utils;
import android.content.Context;
import android.util.Log;
import com.ckkj.water.fate.entity.CityDataEntity;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;
/**
* @author fengxiaoyang
* @date 2025/8/11
* @description 城市信息JSON处理工具类
*/
public class YfjJsonHadnlerUtil {
private static final String TAG = "YfjJsonHadnlerUtil";
private static final String CITY_INFO_FILE = "yfj_city_info.json";
private static JSONObject cityInfoJson = null;
/**
* 初始化城市信息数据
* @param context 上下文
*/
public static void initCityInfo(Context context) {
if (cityInfoJson == null) {
cityInfoJson = loadCityInfoFromAssets(context);
}
}
/**
* 从assets文件夹加载城市信息JSON文件
* @param context 上下文
* @return JSONObject 城市信息数据
*/
private static JSONObject loadCityInfoFromAssets(Context context) {
try {
InputStream inputStream = context.getAssets().open(CITY_INFO_FILE);
int size = inputStream.available();
byte[] buffer = new byte[size];
inputStream.read(buffer);
inputStream.close();
String jsonString = new String(buffer, StandardCharsets.UTF_8);
return new JSONObject(jsonString);
} catch (IOException | JSONException e) {
Log.e(TAG, "加载城市信息文件失败: " + e.getMessage());
return null;
}
}
/**
* 根据城市名称查找匹配的城市信息
* @param cityEntity 城市名称,如"济宁市"、"北京市"、"XX地区"
* @return 匹配的城市名称,如果找不到则返回空字符串
*/
public static String findCityByName(CityDataEntity cityEntity) {
String cityResult = "";
if (cityInfoJson == null) {
Log.e(TAG, "城市信息未初始化请先调用initCityInfo方法");
return "";
}
if (cityEntity == null || cityEntity.getCityName().trim().isEmpty()) {
return "";
}
try {
// 遍历所有省份/直辖市
JSONArray provinceNames = cityInfoJson.names();
if (provinceNames != null) {
for (int i = 0; i < provinceNames.length(); i++) {
String provinceName = provinceNames.getString(i);
// 检查省份名称是否包含城市名称
if (cityEntity.getCityName().contains(provinceName) || provinceName.contains(cityEntity.getCityName())) {
String proName = provinceName.replace("","");
return proName;
}else if(cityEntity.getCityType().equals("特别行政区")){
}
if(cityEntity.getProvinceName().equals(provinceName)){
// 获取该省份下的城市列表
JSONArray cityList = cityInfoJson.getJSONArray(provinceName);
if (cityList != null) {
for (int j = 0; j < cityList.length(); j++) {
String city = cityList.getString(j);
// 检查城市名称是否包含城市名称参数,或者城市名称参数是否包含城市名称
if ((cityEntity.getCityName().contains(city) || city.contains(cityEntity.getCityName()))
&& cityEntity.getProvinceName().equals(provinceName)) {
cityResult = city;
return cityResult;
}else{
cityResult = cityEntity.getCapitalCity();
}
}
}
}
}
}
} catch (JSONException e) {
Log.e(TAG, "解析城市信息失败: " + e.getMessage());
}
return cityResult;
}
/**
* 获取所有省份名称
* @return 省份名称列表
*/
public static List<String> getAllProvinces() {
List<String> provinces = new ArrayList<>();
if (cityInfoJson == null) {
return provinces;
}
try {
JSONArray provinceNames = cityInfoJson.names();
if (provinceNames != null) {
for (int i = 0; i < provinceNames.length(); i++) {
provinces.add(provinceNames.getString(i));
}
}
} catch (JSONException e) {
Log.e(TAG, "获取省份列表失败: " + e.getMessage());
}
return provinces;
}
/**
* 根据省份名称获取该省份下的城市列表
* @param provinceName 省份名称
* @return 城市列表
*/
public static List<String> getCitiesByProvince(String provinceName) {
List<String> cities = new ArrayList<>();
if (cityInfoJson == null || provinceName == null || provinceName.trim().isEmpty()) {
return cities;
}
try {
if (cityInfoJson.has(provinceName)) {
JSONArray cityList = cityInfoJson.getJSONArray(provinceName);
if (cityList != null) {
for (int i = 0; i < cityList.length(); i++) {
cities.add(cityList.getString(i));
}
}
}
} catch (JSONException e) {
Log.e(TAG, "获取城市列表失败: " + e.getMessage());
}
return cities;
}
}
//package com.ckkj.water.utils;
//
//import android.content.Context;
//import android.util.Log;
//
//
//import org.json.JSONArray;
//import org.json.JSONException;
//import org.json.JSONObject;
//
//import java.io.IOException;
//import java.io.InputStream;
//import java.nio.charset.StandardCharsets;
//import java.util.ArrayList;
//import java.util.List;
//
///**
// * @author fengxiaoyang
// * @date 2025/8/11
// * @description 城市信息JSON处理工具类
// */
//
//public class YfjJsonHadnlerUtil {
//
// private static final String TAG = "YfjJsonHadnlerUtil";
// private static final String CITY_INFO_FILE = "yfj_city_info.json";
//
// private static JSONObject cityInfoJson = null;
//
// /**
// * 初始化城市信息数据
// * @param context 上下文
// */
// public static void initCityInfo(Context context) {
// if (cityInfoJson == null) {
// cityInfoJson = loadCityInfoFromAssets(context);
// }
// }
//
// /**
// * 从assets文件夹加载城市信息JSON文件
// * @param context 上下文
// * @return JSONObject 城市信息数据
// */
// private static JSONObject loadCityInfoFromAssets(Context context) {
// try {
// InputStream inputStream = context.getAssets().open(CITY_INFO_FILE);
// int size = inputStream.available();
// byte[] buffer = new byte[size];
// inputStream.read(buffer);
// inputStream.close();
//
// String jsonString = new String(buffer, StandardCharsets.UTF_8);
// return new JSONObject(jsonString);
// } catch (IOException | JSONException e) {
// Log.e(TAG, "加载城市信息文件失败: " + e.getMessage());
// return null;
// }
// }
//
// /**
// * 根据城市名称查找匹配的城市信息
// * @param cityEntity 城市名称,如"济宁市"、"北京市"、"XX地区"
// * @return 匹配的城市名称,如果找不到则返回空字符串
// */
// public static String findCityByName(CityDataEntity cityEntity) {
// String cityResult = "";
// if (cityInfoJson == null) {
// Log.e(TAG, "城市信息未初始化请先调用initCityInfo方法");
// return "";
// }
//
// if (cityEntity == null || cityEntity.getCityName().trim().isEmpty()) {
// return "";
// }
//
// try {
// // 遍历所有省份/直辖市
// JSONArray provinceNames = cityInfoJson.names();
// if (provinceNames != null) {
// for (int i = 0; i < provinceNames.length(); i++) {
// String provinceName = provinceNames.getString(i);
//
// // 检查省份名称是否包含城市名称
// if (cityEntity.getCityName().contains(provinceName) || provinceName.contains(cityEntity.getCityName())) {
// String proName = provinceName.replace("市","");
// return proName;
// }else if(cityEntity.getCityType().equals("特别行政区")){
//
// }
// if(cityEntity.getProvinceName().equals(provinceName)){
// // 获取该省份下的城市列表
// JSONArray cityList = cityInfoJson.getJSONArray(provinceName);
// if (cityList != null) {
// for (int j = 0; j < cityList.length(); j++) {
// String city = cityList.getString(j);
//
// // 检查城市名称是否包含城市名称参数,或者城市名称参数是否包含城市名称
// if ((cityEntity.getCityName().contains(city) || city.contains(cityEntity.getCityName()))
// && cityEntity.getProvinceName().equals(provinceName)) {
// cityResult = city;
// return cityResult;
// }else{
// cityResult = cityEntity.getCapitalCity();
// }
// }
// }
// }
// }
// }
// } catch (JSONException e) {
// Log.e(TAG, "解析城市信息失败: " + e.getMessage());
// }
//
// return cityResult;
// }
//
// /**
// * 获取所有省份名称
// * @return 省份名称列表
// */
// public static List<String> getAllProvinces() {
// List<String> provinces = new ArrayList<>();
//
// if (cityInfoJson == null) {
// return provinces;
// }
//
// try {
// JSONArray provinceNames = cityInfoJson.names();
// if (provinceNames != null) {
// for (int i = 0; i < provinceNames.length(); i++) {
// provinces.add(provinceNames.getString(i));
// }
// }
// } catch (JSONException e) {
// Log.e(TAG, "获取省份列表失败: " + e.getMessage());
// }
//
// return provinces;
// }
//
// /**
// * 根据省份名称获取该省份下的城市列表
// * @param provinceName 省份名称
// * @return 城市列表
// */
// public static List<String> getCitiesByProvince(String provinceName) {
// List<String> cities = new ArrayList<>();
//
// if (cityInfoJson == null || provinceName == null || provinceName.trim().isEmpty()) {
// return cities;
// }
//
// try {
// if (cityInfoJson.has(provinceName)) {
// JSONArray cityList = cityInfoJson.getJSONArray(provinceName);
// if (cityList != null) {
// for (int i = 0; i < cityList.length(); i++) {
// cities.add(cityList.getString(i));
// }
// }
// }
// } catch (JSONException e) {
// Log.e(TAG, "获取城市列表失败: " + e.getMessage());
// }
//
// return cities;
// }
//}

View File

@@ -82,4 +82,39 @@ public class ActivityManager {
}
}
}
/**
* 关闭指定tag的所有Activity
*
* @param tag 比如 add_device_flag
*/
public static void removeActivityByTag(String tag)
{
if(activitys == null || activitys.isEmpty()){
return;
}
//避免遍历时ConcurrentModificationException
Map<String, Activity> tempMap =
new HashMap<>(activitys);
for (Map.Entry<String, Activity> entry : tempMap.entrySet()) {
String key = entry.getKey();
Activity activity = entry.getValue();
if (key != null && key.contains(tag)) {
if (activity != null &&
!activity.isFinishing() &&
!activity.isDestroyed()) {
activity.finish();
}
activitys.remove(key);
}
}
}
}

View File

@@ -4,6 +4,7 @@ import android.content.Context;
import com.ckkj.water.AppConfig;
import com.ckkj.water.ConstantUtil;
import com.ckkj.water.base.entity.MineUserInfoBean;
import com.ckkj.water.base.entity.UserInfoEntity;
import com.ckkj.water.login.entity.LoginEntity;
import com.ckkj.water.utils.dataUtil.SharePreUtil;
@@ -15,20 +16,20 @@ import com.ckkj.water.utils.dataUtil.SharePreUtil;
* @Date 04-07-2025 周一 12:51
*/
public class MingDengUserInfoManager {
private static MingDengUserInfoManager instance;
public class WaterUserInfoManager {
private static WaterUserInfoManager instance;
private LoginEntity entity;
private UserInfoEntity userInfo;
private MineUserInfoBean userInfo;
private MingDengUserInfoManager() {
private WaterUserInfoManager() {
// 私有构造方法防止外部直接创建实例
}
public static MingDengUserInfoManager getInstance() {
public static WaterUserInfoManager getInstance() {
if (instance == null) {
synchronized (MingDengUserInfoManager.class) {
synchronized (WaterUserInfoManager.class) {
if (instance == null) {
instance = new MingDengUserInfoManager();
instance = new WaterUserInfoManager();
}
}
}
@@ -43,11 +44,11 @@ public class MingDengUserInfoManager {
this.entity = entity;
}
public UserInfoEntity getUserInfo() {
public MineUserInfoBean getUserInfo() {
return userInfo;
}
public void setUserInfo(UserInfoEntity userInfo) {
public void setUserInfo(MineUserInfoBean userInfo) {
this.userInfo = userInfo;
}

View File

@@ -10,9 +10,9 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginHorizontal="@dimen/dp_5"
android:layout_marginVertical="@dimen/dp_5"
android:layout_marginVertical="@dimen/dp_6"
app:cardCornerRadius="16dp"
app:cardElevation="4dp">
app:cardElevation="@dimen/dp_5">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"

View File

@@ -80,18 +80,47 @@
android:textStyle="bold" />
<!-- 设备列表区域 -->
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/rv_devices"
<com.scwang.smart.refresh.layout.SmartRefreshLayout
android:id="@+id/refresh"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:clipToPadding="false"
android:paddingHorizontal="@dimen/dp_15"
android:paddingTop="@dimen/dp_15"
android:paddingBottom="@dimen/dp_20"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
tools:listitem="@layout/index_device_list_item" />
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<!-- 设备列表区域 -->
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/rv_devices"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:clipToPadding="false"
android:paddingHorizontal="@dimen/dp_15"
android:paddingBottom="@dimen/dp_20"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
tools:listitem="@layout/index_device_list_item" />
<RelativeLayout
android:id="@+id/rel_no_more"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:visibility="gone" >
<include
android:id="@+id/lay_no_more"
layout="@layout/layout_no_more"/>
</RelativeLayout>
</LinearLayout>
</com.scwang.smart.refresh.layout.SmartRefreshLayout>
<RelativeLayout
android:id="@+id/rel_noresult"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:visibility="gone">
<include
android:id="@+id/included_noresult"
layout="@layout/include_no_result_layout"/>
</RelativeLayout>
</LinearLayout>

View File

@@ -25,7 +25,6 @@
android:id="@+id/tab_code"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="vertical">
<TextView
@@ -50,7 +49,6 @@
android:id="@+id/tab_psd"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="vertical"
android:layout_marginLeft="40dp">
@@ -90,7 +88,7 @@
<EditText
android:id="@+id/et_account"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_marginLeft="5dp"
android:background="@null"
android:textSize="14sp"
@@ -113,8 +111,9 @@
android:layout_height="24dp"
android:src="@mipmap/icon_phone_code"/>
<EditText
android:id="@+id/ed_code_input"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_weight="2"
android:layout_marginLeft="5dp"
android:background="@null"
@@ -150,6 +149,7 @@
android:layout_height="24dp"
android:src="@mipmap/icon_psd"/>
<EditText
android:id="@+id/et_input_psd"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="5dp"
@@ -203,5 +203,40 @@
android:text="@string/reset_psd"
android:visibility="invisible"/>
</RelativeLayout>
</LinearLayout>
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="@dimen/dp_100">
<RelativeLayout
android:id="@+id/realtive_read_finish"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_alignParentBottom="true"
android:layout_marginHorizontal="@dimen/dp_15"
android:layout_marginBottom="@dimen/dp_30">
<RadioButton
android:id="@+id/checkbox_read"
android:layout_width="@dimen/dp_14"
android:layout_height="@dimen/dp_14"
android:background="@drawable/select_radio"
android:layout_centerVertical="true"
android:button="@null"
android:clickable="false"
android:visibility="visible" />
<TextView
android:id="@+id/tv_agreement_full"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="@dimen/dp_12"
android:layout_marginRight="@dimen/dp_12"
android:layout_toRightOf="@+id/checkbox_read"
android:autoLink="none"
android:lineSpacingExtra="4dp"
android:textColor="@color/color_gray_tab"
android:textSize="11sp" />
</RelativeLayout>
</RelativeLayout>
</LinearLayout>

View File

@@ -40,7 +40,7 @@
<EditText
android:id="@+id/et_account"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_marginLeft="@dimen/dp_5"
android:background="@null"
android:textSize="14sp"
@@ -65,7 +65,7 @@
<EditText
android:id="@+id/et_verfi_code"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_weight="2"
android:layout_marginLeft="@dimen/dp_5"
android:background="@null"
@@ -102,7 +102,7 @@
<EditText
android:id="@+id/et_input_psd"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_marginLeft="@dimen/dp_5"
android:background="@null"
android:textSize="14sp"
@@ -127,7 +127,7 @@
<EditText
android:id="@+id/et_input_psd_agin"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_height="match_parent"
android:layout_marginLeft="@dimen/dp_5"
android:background="@null"
android:textSize="14sp"

View File

@@ -7,5 +7,5 @@
android:id="@+id/ivRefresh"
android:layout_width="30dp"
android:layout_height="30dp"
android:src="@mipmap/icon_refresh_logo" />
android:src="@mipmap/ic_launcher" />
</RelativeLayout>

View File

@@ -18,6 +18,8 @@
<string name="login_error_phone_empty">手机号不能为空</string>
<string name="hint_input_psd_not_match">两次输入的密码不一致</string>
<string name="login_error_phone_invalid">请输入正确的手机号或邮箱</string>
<string name="login_error_psd_empty">手机号或邮箱不能为空</string>
<string name="login_error_psd_agin_empty">请再次输入密码</string>
<string name="register_title">注册用户</string>
<string name="register_title_bar">注册</string>
<string name="register_success_title">注册成功</string>

View File

@@ -16,7 +16,9 @@
<string name="hint_input_new_psd">请输入新密码</string>
<string name="hint_input_new_psd_agin">请再次输入新密码</string>
<string name="hint_input_psd_not_match">两次输入的密码不一致</string>
<string name="login_error_phone_empty">手机号不能为空</string>
<string name="login_error_phone_empty">手机号或邮箱不能为空</string>
<string name="login_error_psd_empty">密码不能为空</string>
<string name="login_error_psd_agin_empty">请再次输入密码</string>
<string name="login_error_phone_invalid">请输入正确的手机号或邮箱</string>
<string name="register_title">注册用户</string>
<string name="register_title_bar">注册</string>
@@ -177,7 +179,7 @@
</string>
<string name="app_name">星语明灯</string>
<string name="app_name">智能浇水</string>
<!-- ==================== 登录页 ==================== -->
<string name="login_app_name">星语明灯</string>