1:修改系统和官方公告展示html出现标签展示的问题

2:添加群全员禁言和单个禁言的功能
3:将道具商城做成原生的
4:添加应用更新的时候,添加版本判断和重新刷新手机文本,预防出现安装缓存(自己测试十几次,未在出现问题,还需要大量测试)
This commit is contained in:
2026-01-04 08:58:09 +08:00
parent aa96aa4a3b
commit f77b5ba4d7
45 changed files with 2008 additions and 39 deletions

View File

@@ -137,7 +137,7 @@ public class CommonAppContext extends MultiDexApplication implements Application
@Getter @Getter
public UnreadCountEvent unreadCountEvent; public UnreadCountEvent unreadCountEvent;
public static int selectRelease = 1; public static int selectRelease = -1;
public int is_open = 0;//主题的开关 public int is_open = 0;//主题的开关

View File

@@ -0,0 +1,53 @@
package com.xscm.moduleutil.bean
/**
* 项目名称:羽声语音
* 时间2026/1/3 10:13
* 用途:群聊实体类
*/
class GroupBean {
var guild_id: String = ""
var guild_cover: String = ""
var is_deacon: Int = 0 //是否是群主 1是 ,其他的不是
var user_list: List<GroupUserBean> = ArrayList()
var name: String = ""
var notification: String = ""
var mute_all_member : Int = 0 //是否全体禁言 1是 0不是
class GroupUserBean {
var is_online: Int = 0 //是否在线 1在线 0不在线
var market_value: Int = 0 //身价
var nickname: String = ""
var avatar: String = ""
var user_code: String = ""
var user_id: Int = 0
var createtime: String = ""
var is_self: Int = 0 //是否是本人 1是 0不是
var role: String = ""
var role_str: String = ""
var in_room_id: Int = 0 //是否在房间内 1在 0不在
var is_mute: Int = 0 //是否被禁言 1是 0不是
}
/*"guild_id": "f627",
"guild_cover": "https://yusheng-1369267578.cos.ap-guangzhou.myqcloud.com/images/android_images/325ee1f528343bb09ddc086b2b83b190.jpg",
"is_deacon": 1,
"user_list": [
{
"is_online": 1,
"market_value": 28,
"nickname": "🥭芒的很",
"avatar": "https://yusheng-1369267578.cos.ap-guangzhou.myqcloud.com/images/ios_images/1764941796523.jpeg",
"user_code": "10001",
"user_id": 21211,
"createtime": "2025-12-31 13:20:28",
"is_self": 0,
"role": "Member",
"role_str": "普通群成员",
"in_room_id": 0
}
],
"name": "美丽的眼神的家族",
"notification": ""*/
}

View File

@@ -0,0 +1,13 @@
package com.xscm.moduleutil.bean
/**
* 项目名称:羽声语音
* 时间2026/1/3 14:07
* 用途:群成员列表
*/
class GroupUserListBean {
var page : String=""
var limit : String=""
var count : String=""
var list : List<GroupBean.GroupUserBean>?= ArrayList()
}

View File

@@ -0,0 +1,57 @@
package com.xscm.moduleutil.bean
/**
* 项目名称:羽声语音
* 时间2026/1/3 18:44
* 用途:装扮列表
*/
class PersonaltyListBean {
var did: Int =0 // 装扮id
var title: String = "" // 装扮名称
var type: Int = 0 // 1头像框 2坐骑 3资料展示特效 4光圈 5气泡 6个人靓号 7房间靓号 8工会靓号 100热门
var base_image: String = "" // 展示图片
var play_image: String = "" // 播放图像
var price: Int = 0 // 实际价格(金币)
var special_num: Int = 0 // 靓号
var original_price: Int = 0 // 原价
var discount: Int = 0 // 折扣
var discount_str: String = "" // 折扣字段
/* title
装扮名称
type
类型1头像框 2坐骑 3资料展示特效 4光圈 5气泡 6个人靓号 7房间靓号 8工会靓号 100热门
base_image
展示图片
play_image
播放图像
price
实际价格(金币)
special_num
靓号
original_price
原价
discount
折扣
discount_str
折扣字段*/
}

View File

@@ -43,6 +43,9 @@ public interface ApiServer {
@GET(Constants.GET_FESTIVAL_THEME) @GET(Constants.GET_FESTIVAL_THEME)
Call<BaseModel<FestivalThemeBean>> getFestivalThemeBean(); Call<BaseModel<FestivalThemeBean>> getFestivalThemeBean();
@GET(Constants.GET_PERSONALTY_LIST_BEAN)
Call<BaseModel<List<PersonaltyListBean>>> getPersonaltyListBean(@Query("type") String type);
@GET(Constants.GET_EMOTION) @GET(Constants.GET_EMOTION)
Call<BaseModel<List<Emotion>>> upEmotion(); Call<BaseModel<List<Emotion>>> upEmotion();
@@ -132,6 +135,16 @@ public interface ApiServer {
@FormUrlEncoded @FormUrlEncoded
@POST(Constants.POST_INVITE) @POST(Constants.POST_INVITE)
Call<BaseModel<String>> postInvite(@Field("apply_id") String apply_id, @Field("type") String type); Call<BaseModel<String>> postInvite(@Field("apply_id") String apply_id, @Field("type") String type);
@GET(Constants.GET_GROUP_INFO)
Call<BaseModel<GroupBean>> getGuildInfo(@Query("guild_id")String guild_id);
@FormUrlEncoded
@POST(Constants.POST_GROUP_INFO)
Call<BaseModel<String>> setGuildInfo(@Field("guild_id") String guild_id, @Field("name") String guild_name, @Field("notice") String guild_notice,@Field("avatar") String guild_avatar);
@GET(Constants.GET_MEMBER_LIST)
Call<BaseModel<GroupUserListBean>> memberList(@Query("page")String page, @Query("page_limit") String page_limit, @Query("guild_id") String guild_id,@Query("search") String search);
@GET(Constants.GET_TEMP_KEY) @GET(Constants.GET_TEMP_KEY)
Call<BaseModel<TempKeyBean>> getTempKey(); Call<BaseModel<TempKeyBean>> getTempKey();

View File

@@ -251,6 +251,35 @@ public class RetrofitClient {
}); });
} }
public void getPersonaltyListBean(String type, BaseObserver<List<PersonaltyListBean>> observer) {
sApiServer.getPersonaltyListBean(type).enqueue(new Callback<BaseModel<List<PersonaltyListBean>>>() {
@Override
public void onResponse(Call<BaseModel<List<PersonaltyListBean>>> call, Response<BaseModel<List<PersonaltyListBean>>> response) {
if (response.code() == 200) {
BaseModel<List<PersonaltyListBean>> body = response.body();
if (body.getCode() == 1) {
observer.onNext(body.getData());
} else if (body.getCode() == 0) {
ToastUtils.showLong(body.getMsg());
observer.onNext(new ArrayList<>());
} else if (body.getCode() == 301) {
setCode301(body.getMsg());
}
} else {
ToastUtils.showLong("装扮请求错误", response.code());
LogUtils.e("getPersonaltyList", response.message());
}
}
@Override
public void onFailure(Call<BaseModel<List<PersonaltyListBean>>> call, Throwable t) {
LogUtils.e("getPersonaltyList", t.getMessage());
}
});
}
public void getFestivalTheme(BaseObserver<FestivalThemeBean> observer) { public void getFestivalTheme(BaseObserver<FestivalThemeBean> observer) {
sApiServer.getFestivalThemeBean().enqueue(new Callback<BaseModel<FestivalThemeBean>>() { sApiServer.getFestivalThemeBean().enqueue(new Callback<BaseModel<FestivalThemeBean>>() {
@@ -646,6 +675,77 @@ public class RetrofitClient {
}); });
} }
public void getGuildInfo(String guildId, BaseObserver<GroupBean> observer) {
sApiServer.getGuildInfo(guildId).enqueue(new Callback<BaseModel<GroupBean>>() {
@Override
public void onResponse(Call<BaseModel<GroupBean>> call, Response<BaseModel<GroupBean>> response) {
if (response.code() == 200) {
BaseModel<GroupBean> baseModel = response.body();
if (baseModel.getCode() == 1)
observer.onNext(baseModel.getData());
else if (baseModel.getCode() == 301) {
setCode301(baseModel.getMsg());
} else {
ToastUtils.showLong(baseModel.getMsg());
observer.onNext(new GroupBean());
}
} else {
observer.onNext(new GroupBean());
ToastUtils.showLong("群聊设置错误,请重试", response.code());
LogUtils.e("getGuildInfo", response.message());
}
}
@Override
public void onFailure(Call<BaseModel<GroupBean>> call, Throwable t) {
LogUtils.e("getGuildInfo", t.fillInStackTrace());
}
});
}
public void setGuildInfo(String guildId, String name, String notice, String avatar, BaseObserver<String> observer) {
sApiServer.setGuildInfo(guildId, name, notice, avatar).enqueue(new Callback<BaseModel<String>>() {
@Override
public void onResponse(Call<BaseModel<String>> call, Response<BaseModel<String>> response) {
onNextRetu(response, observer);
}
@Override
public void onFailure(Call<BaseModel<String>> call, Throwable t) {
LogUtils.e("setGuildInfo", t.fillInStackTrace());
}
});
}
public void memberList(String page, String pageLimit, String guildId, String search, BaseObserver<GroupUserListBean> observer) {
sApiServer.memberList(page, pageLimit, guildId, search).enqueue(new Callback<BaseModel<GroupUserListBean>>() {
@Override
public void onResponse(Call<BaseModel<GroupUserListBean>> call, Response<BaseModel<GroupUserListBean>> response) {
if (response.code() == 200) {
BaseModel<GroupUserListBean> baseModel = response.body();
if (baseModel.getCode() == 1)
observer.onNext(baseModel.getData());
else if (baseModel.getCode() == 301)
setCode301(baseModel.getMsg());
else {
ToastUtils.showLong(baseModel.getMsg());
}
} else {
ToastUtils.showLong("群成员请求错误", response.code());
LogUtils.e("memberList", response.message());
}
}
@Override
public void onFailure(Call<BaseModel<GroupUserListBean>> call, Throwable t) {
LogUtils.e("memberList", t.fillInStackTrace());
}
});
}
public void singerAuth(String url, BaseObserver<String> observer) { public void singerAuth(String url, BaseObserver<String> observer) {
sApiServer.singerAuth(url).enqueue(new Callback<BaseModel<String>>() { sApiServer.singerAuth(url).enqueue(new Callback<BaseModel<String>>() {
@@ -2034,7 +2134,7 @@ public class RetrofitClient {
} }
} else { } else {
observer.onError(new Throwable(response.message())); observer.onError(new Throwable(response.message()));
ToastUtils.showLong("首页房间列表异常",response.code()); ToastUtils.showLong("首页房间列表异常", response.code());
LogUtils.e("getTopRooms", response.message()); LogUtils.e("getTopRooms", response.message());
} }
} }
@@ -2382,7 +2482,7 @@ public class RetrofitClient {
setCode301(listBaseModel.getMsg()); setCode301(listBaseModel.getMsg());
} }
} else { } else {
ToastUtils.showLong("进入用户主页错误",response.code()); ToastUtils.showLong("进入用户主页错误", response.code());
LogUtils.e("getUserHome", response.message()); LogUtils.e("getUserHome", response.message());
} }
} }
@@ -2445,15 +2545,15 @@ public class RetrofitClient {
}); });
} }
public void delSong(String roomId,String did,BaseObserver<String> observer){ public void delSong(String roomId, String did, BaseObserver<String> observer) {
sApiServer.delSong(roomId,did).enqueue(new Callback<BaseModel<String>>() { sApiServer.delSong(roomId, did).enqueue(new Callback<BaseModel<String>>() {
@Override @Override
public void onResponse(Call<BaseModel<String>> call, Response<BaseModel<String>> response) { public void onResponse(Call<BaseModel<String>> call, Response<BaseModel<String>> response) {
if (response.code() == 200) { if (response.code() == 200) {
onNextRetu(response, observer); onNextRetu(response, observer);
}else { } else {
ToastUtils.showLong("删除歌曲失败",response.code()); ToastUtils.showLong("删除歌曲失败", response.code());
LogUtils.e("delSong", response.message()); LogUtils.e("delSong", response.message());
} }
} }
@@ -2480,7 +2580,7 @@ public class RetrofitClient {
ToastUtils.showShort(listBaseModel.getMsg()); ToastUtils.showShort(listBaseModel.getMsg());
} }
} else { } else {
ToastUtils.showLong("获取用户数据错误",response.code()); ToastUtils.showLong("获取用户数据错误", response.code());
LogUtils.e("getMyInfo", response.message()); LogUtils.e("getMyInfo", response.message());
} }
} }
@@ -2673,8 +2773,8 @@ public class RetrofitClient {
} else { } else {
MessageListenerSingleton.getInstance().quitGroup(roomId); MessageListenerSingleton.getInstance().quitGroup(roomId);
} }
}else { } else {
ToastUtils.showLong("进入房间错误",response.code()); ToastUtils.showLong("进入房间错误", response.code());
if (joinRoomLoadListener != null) { if (joinRoomLoadListener != null) {
joinRoomLoadListener.onJoinRoomLoad("网络异常"); joinRoomLoadListener.onJoinRoomLoad("网络异常");
} }
@@ -3013,7 +3113,7 @@ public class RetrofitClient {
} }
public void getRedpacketConfig(BaseObserver<RedPacketConfig> observer) { public void getRedpacketConfig(BaseObserver<RedPacketConfig> observer) {
sApiServer.getRedpacketConfig().enqueue(new Callback<BaseModel<RedPacketConfig>>(){ sApiServer.getRedpacketConfig().enqueue(new Callback<BaseModel<RedPacketConfig>>() {
@Override @Override
public void onResponse(Call<BaseModel<RedPacketConfig>> call, Response<BaseModel<RedPacketConfig>> response) { public void onResponse(Call<BaseModel<RedPacketConfig>> call, Response<BaseModel<RedPacketConfig>> response) {

View File

@@ -380,6 +380,9 @@ public class Constants {
public static final String POST_CLEAR_USER_CHARM = "/api/Room/clear_user_charm";//清除魅力值 public static final String POST_CLEAR_USER_CHARM = "/api/Room/clear_user_charm";//清除魅力值
public static final String POST_MESSAGE_LIST = "/api/UserMessage/get_user_message_list";//消息列表 public static final String POST_MESSAGE_LIST = "/api/UserMessage/get_user_message_list";//消息列表
public static final String POST_INVITE = "/api/Guild/invite_apply_handle";//【新】受邀申请处理 public static final String POST_INVITE = "/api/Guild/invite_apply_handle";//【新】受邀申请处理
public static final String GET_GROUP_INFO = "/api/Guild/get_guild_info";//群聊设置详情
public static final String POST_GROUP_INFO = "/api/Guild/set_guild_info";//设置群聊信息
public static final String GET_MEMBER_LIST = "/api/Guild/member_list";//群聊成员
public static final String POST_BIND_DETAIL = "/api/Bind/bind_detail";//绑定详情 public static final String POST_BIND_DETAIL = "/api/Bind/bind_detail";//绑定详情
public static final String POST_USER_WALL = "/api/User/user_gift_wall";//礼物墙 public static final String POST_USER_WALL = "/api/User/user_gift_wall";//礼物墙
public static final String POST_USER_OLINE_STATUS = "/api/Room/user_online_status";//用户在线状态 public static final String POST_USER_OLINE_STATUS = "/api/Room/user_online_status";//用户在线状态
@@ -452,6 +455,7 @@ public class Constants {
public static final String MODIFY_MOBILE = "/api/UserData/modify_mobiles";//手机换绑 public static final String MODIFY_MOBILE = "/api/UserData/modify_mobiles";//手机换绑
public static final String BIND_MOBILE = "/api/UserData/bind_mobile";//手机绑定 public static final String BIND_MOBILE = "/api/UserData/bind_mobile";//手机绑定
public static final String GET_FESTIVAL_THEME = "/api/Theme/get_festival_theme";//节日主题接口 public static final String GET_FESTIVAL_THEME = "/api/Theme/get_festival_theme";//节日主题接口
public static final String GET_PERSONALTY_LIST_BEAN = "/api/Decorate/get_decorate_list";//装饰列表
public static final String POST_SIGN_START = "/api/Sign/start_sign";//签约开始 public static final String POST_SIGN_START = "/api/Sign/start_sign";//签约开始

View File

@@ -77,7 +77,7 @@
android:layout_gravity="center_horizontal" android:layout_gravity="center_horizontal"
android:background="@mipmap/text_bj" android:background="@mipmap/text_bj"
android:gravity="center" android:gravity="center"
android:text="x30" tools:text="x30"
android:textColor="@color/color_FF333333" android:textColor="@color/color_FF333333"
android:textSize="@dimen/sp_10" android:textSize="@dimen/sp_10"
android:visibility="gone" android:visibility="gone"

View File

@@ -7,6 +7,27 @@
<uses-permission android:name="android.permission.VIBRATE" /> <uses-permission android:name="android.permission.VIBRATE" />
<application android:theme="@style/AppTheme"> <application android:theme="@style/AppTheme">
<activity
android:name=".activity.user.activity.PropMallActivity"
android:exported="false"
android:label="@string/title_activity_prop_mall"
android:theme="@style/AppTheme.NoActionBar" />
<activity
android:name=".activity.GroupUserListActivity"
android:exported="false" />
<activity
android:name=".activity.GroupChatSettingsActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<!-- 自定义action -->
<action android:name="com.example.mainmodule.action.GROUP_CHAT_SETTINGS" />
<!-- 自定义category可选 -->
<category android:name="com.example.mainmodule.category.DETAIL" />
</intent-filter>
</activity>
<activity <activity
android:name=".activity.user.activity.MobilePhoneActivity" android:name=".activity.user.activity.MobilePhoneActivity"
android:exported="false" /> android:exported="false" />
@@ -56,10 +77,10 @@
android:configChanges="orientation|screenSize|keyboardHidden" android:configChanges="orientation|screenSize|keyboardHidden"
android:enableOnBackInvokedCallback="false" android:enableOnBackInvokedCallback="false"
android:exported="false" android:exported="false"
android:persistableMode="persistAcrossReboots"
android:screenOrientation="portrait" android:screenOrientation="portrait"
android:theme="@style/AppTheme" android:theme="@style/AppTheme"
android:windowSoftInputMode="adjustPan" android:windowSoftInputMode="adjustPan" /> <!-- 防止系统回收 View 层级Android 11+ -->
android:persistableMode="persistAcrossReboots"/><!-- 防止系统回收 View 层级Android 11+ -->
<activity <activity
android:name=".activity.room.activity.RedResultActivity" android:name=".activity.room.activity.RedResultActivity"
android:exported="true" /> android:exported="true" />

View File

@@ -0,0 +1,146 @@
package com.xscm.modulemain.activity
import android.content.Intent
import android.view.View
import android.widget.CompoundButton
import androidx.recyclerview.widget.LinearLayoutManager
import com.blankj.utilcode.util.ToastUtils
import com.tencent.imsdk.v2.V2TIMCallback
import com.tencent.imsdk.v2.V2TIMGroupManager
import com.tencent.imsdk.v2.V2TIMManager
import com.xscm.modulemain.BaseMvpActivity
import com.xscm.modulemain.R
import com.xscm.modulemain.activity.msg.NewsContacts
import com.xscm.modulemain.activity.msg.NewsPresenter
import com.xscm.modulemain.adapter.GroupAdapter
import com.xscm.modulemain.databinding.ActivityGroupChatSettingsBinding
import com.xscm.moduleutil.bean.GroupBean
import com.xscm.moduleutil.bean.GroupUserListBean
import com.xscm.moduleutil.bean.NewsMessageList
import com.xscm.moduleutil.utils.ImageUtils
/**
* @Author
* @Time 2026/1/2 14:57
* @Description 群聊设置
*/
class GroupChatSettingsActivity :
BaseMvpActivity<NewsPresenter, ActivityGroupChatSettingsBinding>(),
NewsContacts.View {
var groupAdapter: GroupAdapter? = GroupAdapter()
val v2TIMGroupManager: V2TIMGroupManager?= V2TIMManager.getGroupManager()
var groupId: String = ""
var isOwner : Boolean = false
var groupBean : GroupBean= GroupBean()
override fun bindPresenter(): NewsPresenter {
return NewsPresenter(this, this)
}
override fun initData() {
mBinding?.topBar?.tvTitle?.text = "群聊设置"
MvpPre?.getGuildInfo(groupId)
// 设置布局管理器
mBinding?.rvGroupMember?.apply {
layoutManager = LinearLayoutManager(context, LinearLayoutManager.HORIZONTAL, false)
// 可选:设置是否固定大小
setHasFixedSize(true)
// 设置适配器
adapter = groupAdapter
}
mBinding?.tvGroupCount?.setOnClickListener {
val intent = Intent(this, GroupUserListActivity::class.java).apply {
putExtra("groupId", groupId)
putExtra("isOwner", isOwner)
}
startActivity(intent)
}
mBinding?.tvConfirm?.setOnClickListener {
if(mBinding?.evGroupName?.text.toString().equals(groupBean.name) && mBinding?.etG?.text.toString().equals(groupBean.notification)){
finish()
}else if (mBinding?.evGroupName?.text.toString().equals(groupBean.name) && !mBinding?.etG?.text.toString().equals(groupBean.notification)){
MvpPre?.setGuildInfo(groupId, "", mBinding?.etG?.text.toString(), "")
}else if (!mBinding?.evGroupName?.text.toString().equals(groupBean.name) && mBinding?.etG?.text.toString().equals(groupBean.notification)){
MvpPre?.setGuildInfo(groupId, mBinding?.evGroupName?.text.toString(), "", "")
}else {
MvpPre?.setGuildInfo(
groupId,
mBinding?.evGroupName?.text.toString(),
mBinding?.etG?.text.toString(),
""
)
}
}
mBinding?.switJy?.setOnCheckedChangeListener { compoundButton, b ->
v2TIMGroupManager?.muteAllGroupMembers(groupId, b, object : V2TIMCallback {
override fun onSuccess() {
}
override fun onError(code: Int, desc: String?) {
mBinding?.switJy?.isChecked = !b
}
})
}
}
override fun getLayoutId(): Int {
return R.layout.activity_group_chat_settings
}
override fun showNews(newsList: List<NewsMessageList?>?) {
}
override fun finishRefresh() {
}
override fun postInvite() {
}
override fun getGuildInfo(groupBean: GroupBean?) {
if (groupBean == null) {
finish()
return
}
this.groupBean=groupBean
mBinding?.groupName?.text = groupBean.name
ImageUtils.loadHead(groupBean.guild_cover, mBinding?.imGroup)
if (groupBean.is_deacon == 1) {
isOwner=true
mBinding?.llGroup?.visibility = View.VISIBLE
mBinding?.switJy?.isChecked = groupBean.mute_all_member == 1
mBinding?.etG?.isEnabled = true
mBinding?.evGroupName?.isEnabled = true
} else {
isOwner=false
mBinding?.llGroup?.visibility = View.GONE
mBinding?.etG?.isEnabled = false
mBinding?.evGroupName?.isEnabled = false
}
mBinding?.etG?.text?.append(groupBean.notification)
mBinding?.evGroupName?.text?.append(groupBean.name)
groupAdapter?.setNewData(groupBean.user_list)
}
override fun setGuildInfo(s: String?) {
ToastUtils.showLong(s)
finish()
}
override fun memberList(groupUserListBean: GroupUserListBean?) {
}
override fun doDone() {
super.doDone()
groupId = intent.getStringExtra("groupId").toString()
}
}

View File

@@ -0,0 +1,261 @@
package com.xscm.modulemain.activity
import android.view.View
import android.view.ViewGroup
import android.widget.LinearLayout
import android.widget.TextView
import androidx.core.content.ContextCompat
import com.blankj.utilcode.util.ToastUtils
import com.google.android.material.bottomsheet.BottomSheetDialog
import com.scwang.smartrefresh.layout.api.RefreshLayout
import com.scwang.smartrefresh.layout.listener.OnRefreshLoadMoreListener
import com.tencent.imsdk.v2.V2TIMCallback
import com.tencent.imsdk.v2.V2TIMGroupManager
import com.tencent.imsdk.v2.V2TIMManager
import com.xscm.modulemain.BaseMvpActivity
import com.xscm.modulemain.R
import com.xscm.modulemain.activity.msg.NewsContacts
import com.xscm.modulemain.activity.msg.NewsPresenter
import com.xscm.modulemain.adapter.GroupUserListAdapter
import com.xscm.modulemain.databinding.ActivityGroupUserListBinding
import com.xscm.moduleutil.bean.CommentBean.CommentDetailsBean
import com.xscm.moduleutil.bean.CommentBean.CommentDetailsBean.Replies
import com.xscm.moduleutil.bean.GroupBean
import com.xscm.moduleutil.bean.GroupUserListBean
import com.xscm.moduleutil.bean.NewsMessageList
import com.xscm.moduleutil.utils.SpUtil
/**
* @Author qx
* @Time 2026/1/3 11:44
* @Description 群成员列表
*/
class GroupUserListActivity : BaseMvpActivity<NewsPresenter, ActivityGroupUserListBinding>(),
NewsContacts.View {
val groupUserListAdapter: GroupUserListAdapter by lazy { GroupUserListAdapter() }
val v2TIMGroupManager: V2TIMGroupManager? = V2TIMManager.getGroupManager()
var groupId: String? = null
var isOwner: Boolean = false
var page: Int = 1
var search: String = ""
var groupUserBean: List<GroupBean.GroupUserBean> = ArrayList()
override fun bindPresenter(): NewsPresenter {
return NewsPresenter(this, this)
}
override fun doDone() {
super.doDone()
groupId = intent.getStringExtra("groupId").toString()
isOwner = intent.getBooleanExtra("isOwner", false)
}
override fun initData() {
mBinding?.topBar?.tvTitle?.text = "群聊成员"
mBinding?.recycleView?.layoutManager =
androidx.recyclerview.widget.LinearLayoutManager(this)
mBinding?.recycleView?.adapter = groupUserListAdapter
groupUserListAdapter.setOnItemClickListener(object :
GroupUserListAdapter.OnItemClickListener {
override fun onItemClick(ismute: Int, item: GroupBean.GroupUserBean?) {
if (ismute == 1) {
v2TIMGroupManager?.muteGroupMember(
groupId,
"u" + item?.user_id.toString(),
0,
object :
V2TIMCallback {
override fun onSuccess() {
if (item?.is_mute == 1) {
item.is_mute = 0
} else {
item?.is_mute = 1
}
groupUserListAdapter.notifyDataSetChanged()
}
override fun onError(code: Int, desc: String?) {
ToastUtils.showLong(desc)
}
})
} else {
onCommentLongClick(item)
}
}
})
mBinding.tvCancel.setOnClickListener { view ->
search = mBinding.editQuery.text.toString()
MvpPre?.memberList(page.toString(), "10", groupId, search)
}
mBinding.smartRefreshLayout.setOnRefreshLoadMoreListener(object :
OnRefreshLoadMoreListener {
override fun onLoadMore(refreshLayout: RefreshLayout) {
page++
MvpPre?.memberList(page.toString(), "10", groupId, "")
}
override fun onRefresh(refreshLayout: RefreshLayout) {
page = 1
MvpPre?.memberList(page.toString(), "10", groupId, "")
}
})
if (isOwner) {
mBinding.llSearch.visibility = View.VISIBLE
} else {
mBinding.llSearch.visibility = View.GONE
}
MvpPre?.memberList(page.toString(), "10", groupId, "")
}
override fun getLayoutId(): Int {
return R.layout.activity_group_user_list
}
fun onCommentLongClick(item: GroupBean.GroupUserBean?) {
val options: Array<String?>? =
arrayOf<String>(
"禁言一天",
"禁言五天",
"禁言十天",
"禁言三十天",
"取消"
) as Array<String?>?
// 创建底部对话框
val bottomSheetDialog = BottomSheetDialog(this)
val dialogView = getLayoutInflater().inflate(
com.xscm.moduleutil.R.layout.dialog_bottom_sheet_actions,
null
)
// 初始化视图
val container =
dialogView.findViewById<LinearLayout?>(com.xscm.moduleutil.R.id.ll_options_container)
// 动态添加选项
for (i in options!!.indices) {
val textView = TextView(this)
textView.setText(options[i])
textView.setTextSize(16f)
textView.setPadding(
getResources().getDimensionPixelSize(com.xscm.moduleutil.R.dimen.dp_16),
getResources().getDimensionPixelSize(com.xscm.moduleutil.R.dimen.dp_14),
getResources().getDimensionPixelSize(com.xscm.moduleutil.R.dimen.dp_16),
getResources().getDimensionPixelSize(com.xscm.moduleutil.R.dimen.dp_14)
)
// 设置点击效果
textView.setBackgroundResource(com.xscm.moduleutil.R.drawable.bg_bottom_sheet_item)
val optionIndex = i
textView.setOnClickListener(View.OnClickListener { v: View? ->
handleOptionClick(optionIndex, item)
bottomSheetDialog.dismiss()
})
container.addView(textView)
// 添加分割线(除了最后一个)
if (i < options.size - 1) {
val divider = View(this)
divider.setBackgroundColor(
ContextCompat.getColor(
this,
com.xscm.moduleutil.R.color.color_FFEEEEEE
)
)
val params = LinearLayout.LayoutParams(
ViewGroup.LayoutParams.MATCH_PARENT,
getResources().getDimensionPixelSize(com.xscm.moduleutil.R.dimen.dp_1)
)
divider.setLayoutParams(params)
container.addView(divider)
}
}
bottomSheetDialog.setContentView(dialogView)
bottomSheetDialog.show()
}
private fun handleOptionClick(
optionIndex: Int,
item: GroupBean.GroupUserBean?,
) {
var seconds: Int = 0
when (optionIndex) {
0 ->
seconds = 86400
1 ->
seconds = 432000
2 ->
seconds = 864000
3 ->
seconds = 2592000
4 ->
seconds = 0
}
v2TIMGroupManager?.muteGroupMember(
groupId,
"u" + item?.user_id.toString(),
seconds,
object :
V2TIMCallback {
override fun onSuccess() {
if (item?.is_mute == 1) {
item?.is_mute = 0
} else {
item?.is_mute = 1
}
groupUserListAdapter.notifyDataSetChanged()
}
override fun onError(code: Int, desc: String?) {
ToastUtils.showLong(desc)
}
})
}
override fun showNews(newsList: List<NewsMessageList?>?) {
}
override fun finishRefresh() {
}
override fun postInvite() {
}
override fun getGuildInfo(groupBean: GroupBean?) {
}
override fun setGuildInfo(s: String?) {
}
override fun memberList(groupUserListBean: GroupUserListBean?) {
mBinding.smartRefreshLayout.finishRefresh()
mBinding.smartRefreshLayout.finishLoadMore()
if (groupUserListBean == null) {
return
}
groupUserBean = groupUserListBean.list!!
groupUserListAdapter.updateOwnerStatus(isOwner)
if (page == 1) {
groupUserListAdapter.setNewData(groupUserBean)
} else {
groupUserListAdapter.addData(groupUserBean)
}
}
}

View File

@@ -726,12 +726,13 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
@Override @Override
public void appUpdate(AppUpdateModel appUpdateModel) { public void appUpdate(AppUpdateModel appUpdateModel) {
if (appUpdateModel.getCode() > getCurrentVersionCode(this)) { if (appUpdateModel.getCode() > getCurrentVersionCode(this)) {
String apkName="yusheng"+appUpdateModel.getCode()+".apk";
// 1. 禁止屏幕自动息屏(核心逻辑) // 1. 禁止屏幕自动息屏(核心逻辑)
keepScreenOn(true); keepScreenOn(true);
// 初始化DownloadManager注意需确保DownloadManager类的包名正确 // 初始化DownloadManager注意需确保DownloadManager类的包名正确
manager = new DownloadManager.Builder(this) manager = new DownloadManager.Builder(this)
.apkUrl(appUpdateModel.getUrl()) .apkUrl(appUpdateModel.getUrl())
.apkName("yusheng.apk") .apkName(apkName)
.smallIcon(R.mipmap.ic_launcher_foreground) .smallIcon(R.mipmap.ic_launcher_foreground)
.showNewerToast(false) .showNewerToast(false)
.apkVersionCode(appUpdateModel.getCode()) .apkVersionCode(appUpdateModel.getCode())

View File

@@ -4,6 +4,8 @@ import android.app.Activity;
import com.xscm.moduleutil.activity.IPresenter; import com.xscm.moduleutil.activity.IPresenter;
import com.xscm.moduleutil.activity.IView; import com.xscm.moduleutil.activity.IView;
import com.xscm.moduleutil.bean.GroupBean;
import com.xscm.moduleutil.bean.GroupUserListBean;
import com.xscm.moduleutil.bean.NewsMessageList; import com.xscm.moduleutil.bean.NewsMessageList;
import java.util.List; import java.util.List;
@@ -14,12 +16,23 @@ public class NewsContacts {
void finishRefresh(); void finishRefresh();
void postInvite(); void postInvite();
void getGuildInfo(GroupBean groupBean);
void setGuildInfo(String s);
void memberList(GroupUserListBean groupUserListBean);
} }
public interface IHomePre extends IPresenter { public interface IHomePre extends IPresenter {
void getMessagetitle(String type,String page,String pageLimit); void getMessagetitle(String type,String page,String pageLimit);
void postInvite(String apply_id, String type); void postInvite(String apply_id, String type);
void getGuildInfo(String guild_id);
void setGuildInfo(String groupId,String name,String notice,String avatar);
void memberList(String page,String pageLimit, String guild_id,String search);
} }
} }

View File

@@ -2,6 +2,8 @@ package com.xscm.modulemain.activity.msg;
import android.content.Context; import android.content.Context;
import com.xscm.moduleutil.bean.GroupBean;
import com.xscm.moduleutil.bean.GroupUserListBean;
import com.xscm.moduleutil.bean.NewsMessageList; import com.xscm.moduleutil.bean.NewsMessageList;
import com.xscm.moduleutil.http.BaseObserver; import com.xscm.moduleutil.http.BaseObserver;
import com.xscm.moduleutil.http.RetrofitClient; import com.xscm.moduleutil.http.RetrofitClient;
@@ -58,4 +60,61 @@ public class NewsPresenter extends BasePresenter<NewsContacts.View> implements N
} }
}); });
} }
@Override
public void getGuildInfo(String guild_id) {
api.getGuildInfo(guild_id, new BaseObserver<GroupBean>() {
@Override
public void onSubscribe(Disposable d) {
addDisposable(d);
}
@Override
public void onNext(GroupBean groupBean) {
if (MvpRef==null){
MvpRef=new WeakReference<>(mView);
}
MvpRef.get().getGuildInfo(groupBean);
}
});
}
@Override
public void setGuildInfo(String groupId, String name, String notice, String avatar) {
api.setGuildInfo(groupId, name, notice, avatar, new BaseObserver<String>() {
@Override
public void onSubscribe(Disposable d) {
addDisposable(d);
}
@Override
public void onNext(String s) {
if (MvpRef==null){
MvpRef=new WeakReference<>(mView);
}
MvpRef.get().setGuildInfo(s);
}
});
}
@Override
public void memberList(String page, String pageLimit, String guild_id, String search) {
api.memberList(page, pageLimit, guild_id, search, new BaseObserver<GroupUserListBean>() {
@Override
public void onSubscribe(Disposable d) {
addDisposable(d);
}
@Override
public void onNext(GroupUserListBean groupUserListBean) {
if (MvpRef==null){
MvpRef=new WeakReference<>(mView);
}
MvpRef.get().memberList(groupUserListBean);
}
});
}
} }

View File

@@ -19,6 +19,8 @@ import com.xscm.modulemain.R;
import com.xscm.modulemain.databinding.ActivityOfficialNoticeBinding; import com.xscm.modulemain.databinding.ActivityOfficialNoticeBinding;
import com.xscm.modulemain.manager.RoomManager; import com.xscm.modulemain.manager.RoomManager;
import com.xscm.modulemain.activity.WebViewActivity; import com.xscm.modulemain.activity.WebViewActivity;
import com.xscm.moduleutil.bean.GroupBean;
import com.xscm.moduleutil.bean.GroupUserListBean;
import com.xscm.moduleutil.bean.NewsMessageList; import com.xscm.moduleutil.bean.NewsMessageList;
import com.xscm.moduleutil.utils.ImageUtils; import com.xscm.moduleutil.utils.ImageUtils;
import com.xscm.moduleutil.utils.TimeUtils; import com.xscm.moduleutil.utils.TimeUtils;
@@ -66,7 +68,7 @@ public class OfficialNoticeActivity extends BaseMvpActivity<NewsPresenter, Activ
helper.getView(R.id.ll_system).setVisibility(GONE); helper.getView(R.id.ll_system).setVisibility(GONE);
helper.getView(R.id.ll_gh).setVisibility(VISIBLE); helper.getView(R.id.ll_gh).setVisibility(VISIBLE);
helper.setText(R.id.tv_sys_cons, item.getContent()); helper.setText(R.id.tv_sys_cons, Html.fromHtml(item.getContent()));
if (item.getGuild_invited_status() == 0) { if (item.getGuild_invited_status() == 0) {
helper.getView(R.id.ll_but).setVisibility(VISIBLE); helper.getView(R.id.ll_but).setVisibility(VISIBLE);
helper.getView(R.id.tv_cancel2).setVisibility(GONE); helper.getView(R.id.tv_cancel2).setVisibility(GONE);
@@ -108,7 +110,7 @@ public class OfficialNoticeActivity extends BaseMvpActivity<NewsPresenter, Activ
helper.getView(R.id.ll_gh).setVisibility(GONE); helper.getView(R.id.ll_gh).setVisibility(GONE);
if (item.getImage() == null || item.getImage().isEmpty()) { if (item.getImage() == null || item.getImage().isEmpty()) {
helper.getView(R.id.tv_sys_con).setVisibility(VISIBLE); helper.getView(R.id.tv_sys_con).setVisibility(VISIBLE);
helper.setText(R.id.tv_sys_con, item.getContent()); helper.setText(R.id.tv_sys_con, Html.fromHtml(item.getContent()));
helper.getView(R.id.ll_system_official).setVisibility(GONE); helper.getView(R.id.ll_system_official).setVisibility(GONE);
} else { } else {
helper.getView(R.id.tv_sys_con).setVisibility(GONE); helper.getView(R.id.tv_sys_con).setVisibility(GONE);
@@ -176,4 +178,19 @@ public class OfficialNoticeActivity extends BaseMvpActivity<NewsPresenter, Activ
public void postInvite() { public void postInvite() {
MvpPre.getMessagetitle(type, "1", "10"); MvpPre.getMessagetitle(type, "1", "10");
} }
@Override
public void getGuildInfo(GroupBean groupBean) {
}
@Override
public void setGuildInfo(String s) {
}
@Override
public void memberList(GroupUserListBean groupUserListBean) {
}
} }

View File

@@ -2,6 +2,7 @@ package com.xscm.modulemain.activity.msg.fragment;
import android.content.Intent; import android.content.Intent;
import android.text.Html;
import android.view.View; import android.view.View;
import androidx.fragment.app.Fragment; import androidx.fragment.app.Fragment;
@@ -131,12 +132,14 @@ public class NewsFragment extends BaseMvpFragment<NewsPresenter, FragmentNewsBin
@Override @Override
public void getOfficialNoticeList(NewsDataBean newsDataBeans) { public void getOfficialNoticeList(NewsDataBean newsDataBeans) {
if (newsDataBeans.getAnnouncement_last_message()!=null){ if (newsDataBeans.getAnnouncement_last_message()!=null){
mBinding.tvNr.setText(newsDataBeans.getAnnouncement_last_message().getContent()!=null?newsDataBeans.getAnnouncement_last_message().getContent():""); mBinding.tvNr.setText(Html.fromHtml(newsDataBeans.getAnnouncement_last_message().getContent()!=null?newsDataBeans.getAnnouncement_last_message().getContent():""));
// mBinding.tvNr.setText(newsDataBeans.getAnnouncement_last_message().getContent()!=null?newsDataBeans.getAnnouncement_last_message().getContent():"");
}else { }else {
mBinding.tvNr.setText(""); mBinding.tvNr.setText("");
} }
if (newsDataBeans.getSystem_last_message()!=null){ if (newsDataBeans.getSystem_last_message()!=null){
mBinding.tvXtNr.setText(newsDataBeans.getSystem_last_message().getContent()!=null?newsDataBeans.getSystem_last_message().getContent():""); mBinding.tvXtNr.setText(Html.fromHtml(newsDataBeans.getSystem_last_message().getContent()!=null?newsDataBeans.getSystem_last_message().getContent():""));
// mBinding.tvXtNr.setText(newsDataBeans.getSystem_last_message().getContent()!=null?newsDataBeans.getSystem_last_message().getContent():"");
}else { }else {
mBinding.tvXtNr.setText(""); mBinding.tvXtNr.setText("");
} }

View File

@@ -18,7 +18,9 @@ import com.xscm.modulemain.BaseMvpActivity;
import com.xscm.modulemain.activity.WebViewActivity; import com.xscm.modulemain.activity.WebViewActivity;
import com.xscm.moduleutil.adapter.MyPagerAdapter; import com.xscm.moduleutil.adapter.MyPagerAdapter;
import com.xscm.moduleutil.base.WebUrlConstants; import com.xscm.moduleutil.base.WebUrlConstants;
import com.xscm.moduleutil.bean.BannerModel;
import com.xscm.moduleutil.bean.PersonaltyBean; import com.xscm.moduleutil.bean.PersonaltyBean;
import com.xscm.moduleutil.bean.PersonaltyListBean;
import com.xscm.moduleutil.utils.ColorManager; import com.xscm.moduleutil.utils.ColorManager;
import com.xscm.moduleutil.utils.SpUtil; import com.xscm.moduleutil.utils.SpUtil;
@@ -100,6 +102,17 @@ public class PersonalityActivity extends BaseMvpActivity<PersonalityPresenter, A
} }
}); });
} }
@Override
public void setBanners(List<BannerModel> bannerModels) {
}
@Override
public void getPersonaltyListBean(List<PersonaltyListBean> personaltyListBeans) {
}
private void refreshCurrentGiftFragment(String id,int position) { private void refreshCurrentGiftFragment(String id,int position) {
if (getCurrentGiftFragment()!=null){ if (getCurrentGiftFragment()!=null){
getCurrentGiftFragment().loadDataIfNeeded(Integer.parseInt(id), position); getCurrentGiftFragment().loadDataIfNeeded(Integer.parseInt(id), position);

View File

@@ -0,0 +1,179 @@
package com.xscm.modulemain.activity.user.activity
import android.content.Intent
import android.graphics.Color
import android.util.TypedValue
import android.view.LayoutInflater
import android.view.View
import android.widget.ImageView
import android.widget.TextView
import com.google.android.material.tabs.TabLayout
import com.google.android.material.tabs.TabLayoutMediator
import com.stx.xhb.xbanner.XBanner
import com.stx.xhb.xbanner.XBanner.XBannerAdapter
import com.xscm.modulemain.BaseMvpActivity
import com.xscm.modulemain.R
import com.xscm.modulemain.activity.WebViewActivity
import com.xscm.modulemain.activity.user.activity.ui.main.PlaceholderFragment
import com.xscm.modulemain.activity.user.activity.ui.main.SectionsPagerAdapter
import com.xscm.modulemain.activity.user.conacts.PersonalityConacts
import com.xscm.modulemain.activity.user.presenter.PersonalityPresenter
import com.xscm.modulemain.databinding.ActivityPropMallBinding
import com.xscm.moduleutil.bean.BannerModel
import com.xscm.moduleutil.bean.PersonaltyBean
import com.xscm.moduleutil.bean.PersonaltyListBean
import com.xscm.moduleutil.utils.ColorManager
import com.xscm.moduleutil.utils.ImageUtils
/**
* @Author qx
* @Time 2026/1/3 17:08
* @Description 道具商城
*/
class PropMallActivity : BaseMvpActivity<PersonalityPresenter, ActivityPropMallBinding>(), PersonalityConacts.View {
private lateinit var sectionsPagerAdapter: SectionsPagerAdapter
override fun bindPresenter(): PersonalityPresenter {
return PersonalityPresenter(this,this)
}
override fun initData() {
// 加载道具商城数据
mBinding.topBar.tvTitle.text="道具商城"
MvpPre.getBanners("7")
MvpPre.getPersonaltyList()
mBinding.banner.loadImage(object : XBannerAdapter {
override fun loadBanner(banner: XBanner?, model: Any?, view: View?, position: Int) {
val bannerModel = model as BannerModel
ImageUtils.loadCenterCrop(
bannerModel.getXBannerUrl() as String?,
view as ImageView?
)
}
})
mBinding.banner.setOnItemClickListener(object : XBanner.OnItemClickListener {
override fun onItemClick(banner: XBanner?, model: Any?, view: View?, position: Int) {
/**
* type=1时该值表示房间idtype=2时表示文章id
*/
val bannerModel = model as BannerModel
val intent = Intent(this@PropMallActivity, WebViewActivity::class.java)
intent.putExtra("url", bannerModel.getUrl())
intent.putExtra("title", "商城横幅")
startActivity(intent)
}
})
}
override fun getLayoutId(): Int {
return R.layout.activity_prop_mall
}
override fun getPersonaltyList(personaltyBean: List<PersonaltyBean?>?) {
sectionsPagerAdapter = SectionsPagerAdapter( this,
personaltyBean as List<PersonaltyBean>
)
mBinding.viewPager.adapter = sectionsPagerAdapter
// 创建适配器
mBinding.slidingTabLayout.setSelectedTabIndicatorColor(
ColorManager.getInstance().getPrimaryColorInt()
)
if (!personaltyBean.isEmpty()) mBinding.viewPager.setOffscreenPageLimit(personaltyBean.size - 1)
// 设置 TabLayout 与 ViewPager2 的关联
TabLayoutMediator(
mBinding.slidingTabLayout, mBinding.viewPager,
TabLayoutMediator.TabConfigurationStrategy { tab: TabLayout.Tab?, position: Int ->
// 边界检查
if (position >= 0 && position < personaltyBean.size && personaltyBean.get(position) != null) {
// 创建自定义布局
val customView = LayoutInflater.from(this)
.inflate(R.layout.custom_tab_layout, null)
val textView = customView.findViewById<TextView?>(R.id.tab_text)
textView.setText(personaltyBean.get(position).name)
// 设置初始状态
if (position == 0) {
textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16f)
textView.setTextColor(getResources().getColor(android.R.color.black))
} else {
textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 12f)
textView.setTextColor(Color.parseColor("#999999"))
}
tab!!.setCustomView(customView)
}
}
).attach()
mBinding.slidingTabLayout.addOnTabSelectedListener(object :
TabLayout.OnTabSelectedListener {
override fun onTabSelected(tab: TabLayout.Tab) {
val position = tab.getPosition()
// 边界检查
if (position >= 0 && position < personaltyBean.size) {
val customView = tab.getCustomView()
if (customView != null) {
val textView = customView.findViewById<TextView?>(R.id.tab_text)
if (textView != null) {
textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16f)
textView.setTextColor(getResources().getColor(android.R.color.black))
}
}
}
}
override fun onTabUnselected(tab: TabLayout.Tab) {
// 直接通过 TabLayout 设置未选中状态的文字大小
val customView = tab.getCustomView()
if (customView != null) {
val textView = customView.findViewById<TextView?>(R.id.tab_text)
if (textView != null) {
textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 12f)
textView.setTextColor(Color.parseColor("#999999"))
}
customView.setBackgroundResource(com.xscm.moduleutil.R.drawable.tab_unselected_background)
}
}
override fun onTabReselected(tab: TabLayout.Tab?) {
}
})
// 初始加载第一个tab的数据
mBinding.viewPager.post {
val firstFragment = sectionsPagerAdapter.getFragment(0)
if (firstFragment is PlaceholderFragment) {
firstFragment.loadDataIfNeeded()
}
}
// 添加ViewPager2页面切换监听实现按需加载数据
mBinding.viewPager.registerOnPageChangeCallback(object : androidx.viewpager2.widget.ViewPager2.OnPageChangeCallback() {
override fun onPageSelected(position: Int) {
super.onPageSelected(position)
// 通知当前选中的Fragment加载数据
val fragment = sectionsPagerAdapter.getFragment(position)
if (fragment is PlaceholderFragment) {
fragment.loadDataIfNeeded()
}
}
})
}
override fun setBanners(bannerModels: List<BannerModel?>?) {
mBinding.banner.setBannerData(R.layout.index_image_banner, bannerModels!!)
}
override fun getPersonaltyListBean(personaltyListBeans: List<PersonaltyListBean?>?) {
TODO("Not yet implemented")
}
}

View File

@@ -0,0 +1,54 @@
package com.xscm.modulemain.activity.user.activity.ui.main
import android.graphics.Paint
import android.text.TextUtils
import android.widget.TextView
import com.chad.library.adapter.base.BaseQuickAdapter
import com.chad.library.adapter.base.BaseViewHolder
import com.xscm.modulemain.R
import com.xscm.modulemain.adapter.GroupUserListAdapter
import com.xscm.moduleutil.bean.GroupBean
import com.xscm.moduleutil.bean.PersonaltyListBean
import com.xscm.moduleutil.utils.ImageUtils
/**
* @Author qx
* @Time 2026/1/3 19:17
* @Description 商城展示适配器
*/
class PersonaltyAdapter :
BaseQuickAdapter<PersonaltyListBean, BaseViewHolder>(R.layout.item_personalty) {
interface OnItemClickListener {
fun onItemClick( item: PersonaltyListBean?)
}
private var onItemClickListener: OnItemClickListener? = null
fun setOnItemClickListener(listener: OnItemClickListener?) {
this.onItemClickListener = listener
}
override fun convert(
helper: BaseViewHolder,
item: PersonaltyListBean?
) {
helper.setText(R.id.tv_name_period, item?.title)
helper.setText(R.id.discount,item?.price.toString())
helper.setText(R.id.original_price, item?.original_price.toString())
helper.getView<TextView>(R.id.original_price).paintFlags= Paint.STRIKE_THRU_TEXT_FLAG
ImageUtils.loadHead(item?.base_image,helper.getView(R.id.iv_img))
if (TextUtils.isEmpty(item?.discount_str)){
helper.getView<TextView>(R.id.discount_str).visibility=TextView.GONE
}else{
helper.getView<TextView>(R.id.discount_str).visibility=TextView.VISIBLE
}
helper.setText(R.id.discount_str,item?.discount_str)
helper.itemView.setOnClickListener {
if (onItemClickListener != null) {
onItemClickListener?.onItemClick( item)
}
}
}
}

View File

@@ -0,0 +1,112 @@
package com.xscm.modulemain.activity.user.activity.ui.main
import android.content.Context
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.TextView
import androidx.lifecycle.Observer
import androidx.lifecycle.ViewModelProvider
import androidx.recyclerview.widget.GridLayoutManager
import androidx.recyclerview.widget.LinearLayoutManager
import com.stx.xhb.xbanner.XBanner
import com.xscm.modulemain.R
import com.xscm.modulemain.activity.user.conacts.PersonalityConacts
import com.xscm.modulemain.activity.user.presenter.PersonalityPresenter
import com.xscm.modulemain.databinding.FragmentPropMallBinding
import com.xscm.moduleutil.base.BaseMvpFragment
import com.xscm.moduleutil.bean.BannerModel
import com.xscm.moduleutil.bean.PersonaltyBean
import com.xscm.moduleutil.bean.PersonaltyListBean
/**
* @Author qx
* @Time 2026/1/3 17:57
* @Description 道具商城的fragemnt
*/
class PlaceholderFragment : BaseMvpFragment<PersonalityPresenter,FragmentPropMallBinding>(),
PersonalityConacts.View {
private lateinit var personaltyAdapter: PersonaltyAdapter
var type: String =""
// 标记数据是否已加载
private var isDataLoaded = false
override fun bindPresenter(): PersonalityPresenter? {
return PersonalityPresenter(this,activity)
}
companion object {
/**
* The fragment argument representing the section number for this
* fragment.
*/
private const val ARG_SECTION_NUMBER = "0"
/**
* Returns a new instance of this fragment for the given section
* number.
*/
@JvmStatic
fun newInstance(sectionNumber: Int): PlaceholderFragment {
return PlaceholderFragment().apply {
arguments = Bundle().apply {
putInt(ARG_SECTION_NUMBER, sectionNumber)
}
}
}
}
override fun onAttach(context: Context) {
super.onAttach(context)
type= arguments?.getInt(ARG_SECTION_NUMBER).toString()
}
override fun initData() {
// 不再自动加载数据,改为按需加载
// MvpPre.getPersonaltyListBean(type)
}
/**
* 按需加载数据
* 只有在需要时且数据未加载时才加载
*/
fun loadDataIfNeeded() {
if (!isDataLoaded ) {
MvpPre.getPersonaltyListBean(type)
isDataLoaded = true
}
}
override fun initView() {
mBinding.recyclerView.layoutManager = GridLayoutManager(context, 3)
personaltyAdapter = PersonaltyAdapter()
mBinding.recyclerView.adapter = personaltyAdapter
personaltyAdapter.setOnItemClickListener(object : PersonaltyAdapter.OnItemClickListener{
override fun onItemClick(item: PersonaltyListBean?) {
}
});
}
override fun getLayoutId(): Int {
return R.layout.fragment_prop_mall
}
override fun getPersonaltyList(personaltyBean: List<PersonaltyBean?>?) {
// 隐藏加载进度
}
override fun setBanners(bannerModels: List<BannerModel?>?) {
}
override fun getPersonaltyListBean(personaltyListBeans: List<PersonaltyListBean?>?) {
personaltyAdapter.setNewData(personaltyListBeans)
}
}

View File

@@ -0,0 +1,67 @@
package com.xscm.modulemain.activity.user.activity.ui.main
import androidx.fragment.app.Fragment
import androidx.fragment.app.FragmentActivity
import androidx.viewpager2.adapter.FragmentStateAdapter
import com.blankj.utilcode.util.ActivityUtils
import com.xscm.modulemain.activity.user.activity.PropMallActivity
import com.xscm.moduleutil.bean.PersonaltyBean
/**
* 道具商城的FragmentStateAdapter
* 用于ViewPager2展示不同类型的道具商城页面
*/
class SectionsPagerAdapter(
fragmentActivity: FragmentActivity,
private val personalityList: List<PersonaltyBean>,
) : FragmentStateAdapter(fragmentActivity) {
/**
* 获取页面总数
* @return 页面数量
*/
override fun getItemCount(): Int = personalityList.size
/**
* 创建指定位置的Fragment
* @param position Fragment位置
* @return 对应的Fragment实例
*/
override fun createFragment(position: Int): Fragment {
val personality = personalityList[position]
return PlaceholderFragment.newInstance(
sectionNumber =personality.id.toInt(),
)
}
/**
* 获取指定位置的标题
* @param position 位置索引
* @return 标题文本
*/
fun getPageTitle(position: Int): String? {
return if (position >= 0 && position < personalityList.size) {
personalityList[position].name
} else {
null
}
}
/**
* 获取指定位置的Fragment
* @param position Fragment位置
* @return 对应的Fragment实例
*/
fun getFragment(position: Int): Fragment? {
try {
// 通过反射获取Fragment实例
val fragmentManager = (ActivityUtils.getTopActivity() as PropMallActivity).supportFragmentManager
val fragment = fragmentManager.findFragmentByTag("f" + getItemId(position))
return fragment
} catch (e: Exception) {
e.printStackTrace()
}
return null
}
}

View File

@@ -4,16 +4,23 @@ import android.app.Activity;
import com.xscm.moduleutil.activity.IPresenter; import com.xscm.moduleutil.activity.IPresenter;
import com.xscm.moduleutil.activity.IView; import com.xscm.moduleutil.activity.IView;
import com.xscm.moduleutil.bean.BannerModel;
import com.xscm.moduleutil.bean.PersonaltyBean; import com.xscm.moduleutil.bean.PersonaltyBean;
import com.xscm.moduleutil.bean.PersonaltyListBean;
import java.util.List; import java.util.List;
public class PersonalityConacts { public class PersonalityConacts {
public interface View extends IView<Activity> { public interface View extends IView<Activity> {
void getPersonaltyList(List<PersonaltyBean> personaltyBean); void getPersonaltyList(List<PersonaltyBean> personaltyBean);
void setBanners(List<BannerModel> bannerModels);
void getPersonaltyListBean(List<PersonaltyListBean> personaltyListBeans);
} }
public interface IMePre extends IPresenter { public interface IMePre extends IPresenter {
void getPersonaltyList(); void getPersonaltyList();
void getPersonaltyListBean(String type);
} }
} }

View File

@@ -28,6 +28,7 @@ import com.xscm.modulemain.R;
import com.xscm.modulemain.activity.user.activity.BosomFriendActivity; import com.xscm.modulemain.activity.user.activity.BosomFriendActivity;
import com.xscm.modulemain.activity.user.activity.GiftWallActivity; import com.xscm.modulemain.activity.user.activity.GiftWallActivity;
import com.xscm.modulemain.activity.user.activity.NobleTitleActivity; import com.xscm.modulemain.activity.user.activity.NobleTitleActivity;
import com.xscm.modulemain.activity.user.activity.PropMallActivity;
import com.xscm.modulemain.activity.user.activity.RechargeActivity; import com.xscm.modulemain.activity.user.activity.RechargeActivity;
import com.xscm.modulemain.activity.user.activity.SingerVerificationActivity; import com.xscm.modulemain.activity.user.activity.SingerVerificationActivity;
import com.xscm.modulemain.activity.user.activity.UserFamilyActivity; import com.xscm.modulemain.activity.user.activity.UserFamilyActivity;
@@ -232,11 +233,13 @@ public class VocalRangeFragment extends BaseMvpFragment<MePresenter, FragmentVoc
intent.putExtra("url", String.format(WebUrlConstants.INSTANCE.getWEB_GUILD_URL(),SpUtil.getToken(),"")); intent.putExtra("url", String.format(WebUrlConstants.INSTANCE.getWEB_GUILD_URL(),SpUtil.getToken(),""));
intent.putExtra("title", "公会"); intent.putExtra("title", "公会");
startActivity(intent); startActivity(intent);
}else if (id==R.id.ll_my_shopping){ }else if (id==R.id.ll_my_shopping){//道具商城
Intent intent=new Intent(getContext(), WebViewActivity.class); startActivity(new Intent(getContext(), PropMallActivity.class));
intent.putExtra("url", String.format(WebUrlConstants.INSTANCE.getWEB_PROP_MALL_URL(),SpUtil.getToken()));
intent.putExtra("title", "道具商城"); // Intent intent=new Intent(getContext(), WebViewActivity.class);
startActivity(intent); // intent.putExtra("url", String.format(WebUrlConstants.INSTANCE.getWEB_PROP_MALL_URL(),SpUtil.getToken()));
// intent.putExtra("title", "道具商城");
// startActivity(intent);
} else if (id == R.id.ll_fans) {//粉丝 } else if (id == R.id.ll_fans) {//粉丝
Intent intent = new Intent(getContext(), BlacklistActivity.class); Intent intent = new Intent(getContext(), BlacklistActivity.class);
intent.putExtra("type", 2); intent.putExtra("type", 2);

View File

@@ -2,18 +2,26 @@ package com.xscm.modulemain.activity.user.presenter;
import android.content.Context; import android.content.Context;
import com.xscm.modulemain.activity.user.conacts.MeConacts;
import com.xscm.modulemain.activity.user.conacts.PersonalityConacts; import com.xscm.modulemain.activity.user.conacts.PersonalityConacts;
import com.xscm.moduleutil.bean.BannerModel;
import com.xscm.moduleutil.bean.PersonaltyBean; import com.xscm.moduleutil.bean.PersonaltyBean;
import com.xscm.moduleutil.bean.PersonaltyListBean;
import com.xscm.moduleutil.http.BaseObserver; import com.xscm.moduleutil.http.BaseObserver;
import com.xscm.moduleutil.http.RetrofitClient;
import com.xscm.moduleutil.presenter.BasePresenter; import com.xscm.moduleutil.presenter.BasePresenter;
import java.lang.ref.WeakReference;
import java.util.List; import java.util.List;
import io.reactivex.disposables.Disposable; import io.reactivex.disposables.Disposable;
public class PersonalityPresenter extends BasePresenter<PersonalityConacts.View> implements PersonalityConacts.IMePre{ public class PersonalityPresenter extends BasePresenter<PersonalityConacts.View> implements PersonalityConacts.IMePre {
PersonalityConacts.View mView;
public PersonalityPresenter(PersonalityConacts.View view, Context context) { public PersonalityPresenter(PersonalityConacts.View view, Context context) {
super(view, context); super(view, context);
mView = view;
} }
@Override @Override
@@ -30,4 +38,44 @@ public class PersonalityPresenter extends BasePresenter<PersonalityConacts.View>
} }
}); });
} }
@Override
public void getPersonaltyListBean(String type) {
api.getPersonaltyListBean(type, new BaseObserver<List<PersonaltyListBean>>() {
@Override
public void onSubscribe(Disposable d) {
addDisposable(d);
}
@Override
public void onNext(List<PersonaltyListBean> personaltyListBeans) {
if (MvpRef == null) {
MvpRef = new WeakReference<>(mView);
}
MvpRef.get().getPersonaltyListBean(personaltyListBeans);
}
});
}
public void getBanners(String s) {
// Type listType = new TypeToken<List<BannerModel>>() {}.getType();
// List<BannerModel> restoredRoomModels = GsonUtils.getGSON().fromJson(SpUtils.getHomeBanner(), listType);
// MvpRef.get().setBanners(restoredRoomModels);
RetrofitClient.getInstance().getBanners(s, new BaseObserver<List<BannerModel>>() {
@Override
public void onSubscribe(Disposable d) {
addDisposable(d);
}
@Override
public void onNext(List<BannerModel> bannerModels) {
if (MvpRef == null) {
MvpRef = new WeakReference<>(mView);
}
MvpRef.get().setBanners(bannerModels);
}
});
}
} }

View File

@@ -0,0 +1,23 @@
package com.xscm.modulemain.adapter
import com.chad.library.adapter.base.BaseQuickAdapter
import com.chad.library.adapter.base.BaseViewHolder
import com.xscm.modulemain.R
import com.xscm.moduleutil.bean.GroupBean
import com.xscm.moduleutil.utils.ImageUtils
/**
* 项目名称:羽声语音
* 时间2026/1/3 10:58
* 用途:群聊设置中的用户展示
*/
class GroupAdapter : BaseQuickAdapter<GroupBean.GroupUserBean, BaseViewHolder>(R.layout.item_group_member) {
override fun convert(
helper: BaseViewHolder,
item: GroupBean.GroupUserBean?
) {
helper.setText(R.id.tv_group_name, item?.nickname)
ImageUtils.loadHead(item?.avatar, helper.getView(R.id.im_group))
}
}

View File

@@ -0,0 +1,71 @@
package com.xscm.modulemain.adapter
import android.graphics.Color
import android.widget.TextView
import com.chad.library.adapter.base.BaseQuickAdapter
import com.chad.library.adapter.base.BaseViewHolder
import com.xscm.modulemain.R
import com.xscm.moduleutil.bean.BlackUserBean
import com.xscm.moduleutil.bean.GroupBean
import com.xscm.moduleutil.color.ThemeableDrawableUtils
import com.xscm.moduleutil.utils.MeHeadView
/**
* 项目名称:羽声语音
* 时间2026/1/3 14:17
* 用途:
*/
class GroupUserListAdapter : BaseQuickAdapter<GroupBean.GroupUserBean, BaseViewHolder>(R.layout.item_group_user) {
interface OnItemClickListener {
fun onItemClick(ismute: Int, item: GroupBean.GroupUserBean?)
}
private var onItemClickListener: OnItemClickListener? = null
fun setOnItemClickListener(listener: OnItemClickListener?) {
this.onItemClickListener = listener
}
var isOwner = false
var ismute: Int = 0
// 在适配器中添加设置方法
fun updateOwnerStatus(isOwner: Boolean) {
this.isOwner = isOwner
notifyDataSetChanged() // 如果需要刷新视图
}
override fun convert(
helper: BaseViewHolder,
item: GroupBean.GroupUserBean?
) {
helper.getView<MeHeadView>(R.id.im_user).setData(item?.avatar, "","")
helper.setText(R.id.tv_nick_name, item?.nickname)
if (isOwner){
helper.setVisible(R.id.im_g, true)
ThemeableDrawableUtils.setThemeableRoundedBackground(
helper.getView<TextView>(R.id.im_g),
Color.parseColor("#333333"),
34
)
helper.getView<TextView>(R.id.im_g).setTextColor(Color.WHITE)
if (item?.is_mute==1){
helper.getView<TextView>(R.id.im_g).text = "解禁"
ismute=1
}else{
helper.getView<TextView>(R.id.im_g).text = "禁言"
ismute=0
}
helper.getView<TextView>(R.id.im_g).setOnClickListener {
if (onItemClickListener != null) {
onItemClickListener?.onItemClick(ismute,item)
}
}
}else{
helper.setVisible(R.id.im_g, false)
}
}
}

View File

@@ -0,0 +1,176 @@
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/main"
tools:context="GroupChatSettingsActivity">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingHorizontal="@dimen/dp_20">
<com.xscm.moduleutil.widget.CustomTopBar
android:id="@+id/top_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintTop_toTopOf="parent" />
<com.xscm.moduleutil.widget.CircularImage
android:id="@+id/im_group"
android:layout_width="@dimen/dp_60"
android:layout_height="@dimen/dp_60"
android:layout_gravity="center"
android:layout_marginTop="@dimen/dp_20"
android:src="@mipmap/ic_launcher_app"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/top_bar"
app:riv_oval="true" />
<TextView
android:id="@+id/group_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="@dimen/dp_15"
android:textSize="@dimen/sp_15"
app:layout_constraintBottom_toBottomOf="@+id/im_group"
app:layout_constraintStart_toEndOf="@+id/im_group"
app:layout_constraintTop_toTopOf="@+id/im_group"
tools:text="群聊名称" />
<TextView
android:id="@+id/tv_group_member"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/dp_15"
android:text="群聊成员"
android:textColor="@color/black"
android:textSize="@dimen/sp_15"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="@id/im_group"
app:layout_constraintTop_toBottomOf="@id/im_group" />
<TextView
android:id="@+id/tv_group_count"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="查看成员 >"
android:textColor="@color/color_999999"
android:textSize="@dimen/sp_15"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="@id/tv_group_member" />
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/rv_group_member"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/dp_5"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/tv_group_member"
tools:itemCount="1"
tools:listitem="@layout/item_group_member" />
<EditText
android:id="@+id/ev_group_name"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_45"
android:layout_marginTop="@dimen/dp_5"
android:background="@drawable/bg_r100_hui"
android:gravity="center|start"
android:paddingStart="@dimen/dp_20"
tools:text="群聊名称"
android:textColor="@color/color_999999"
android:textSize="@dimen/sp_15"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="@id/im_group"
app:layout_constraintTop_toBottomOf="@id/rv_group_member" />
<TextView
android:id="@+id/tv_group_announcement"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/dp_15"
android:text="群聊公告"
android:textColor="@color/black"
android:textSize="@dimen/sp_15"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="@id/tv_group_member"
app:layout_constraintTop_toBottomOf="@id/ev_group_name" />
<RelativeLayout
android:id="@+id/rl_group_announcement"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_150"
android:layout_marginTop="@dimen/dp_10"
android:background="@drawable/bg_r100_hui"
app:layout_constraintTop_toBottomOf="@+id/tv_group_announcement">
<EditText
android:id="@+id/et_g"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_140"
android:layout_marginStart="@dimen/dp_16"
android:layout_marginTop="@dimen/dp_10"
android:layout_marginEnd="@dimen/dp_16"
android:layout_marginBottom="@dimen/dp_10"
android:background="@android:color/transparent"
android:gravity="left|top"
android:hint="设置房间公告"
android:textColor="#333333"
android:textColorHint="@color/color_FF666666"
android:textSize="@dimen/sp_15" />
</RelativeLayout>
<LinearLayout
android:id="@+id/ll_group"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/dp_15"
android:orientation="vertical"
app:layout_constraintTop_toBottomOf="@+id/rl_group_announcement">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="@+id/tv_group_ban"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_centerVertical="true"
android:layout_marginTop="@dimen/dp_15"
android:text="全员禁言"
android:textColor="@color/black"
android:textSize="@dimen/sp_15"
android:textStyle="bold" />
<Switch
android:id="@+id/swit_jy"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentEnd="true"
android:layout_centerVertical="true"
tools:ignore="UseSwitchCompatOrMaterialXml" />
</RelativeLayout>
<TextView
android:id="@+id/tv_confirm"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_40"
android:layout_below="@+id/tv_group_ban"
android:layout_marginTop="@dimen/dp_10"
android:background="@drawable/cs"
android:gravity="center"
android:text="确认保存"
android:textColor="@color/white"
android:textSize="@dimen/sp_14" />
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View File

@@ -0,0 +1,101 @@
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/main"
tools:context=".activity.GroupUserListActivity">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<com.xscm.moduleutil.widget.CustomTopBar
android:id="@+id/top_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintTop_toTopOf="parent" />
<LinearLayout
android:id="@+id/ll_search"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_44"
android:layout_marginTop="@dimen/dp_10"
android:gravity="center_vertical"
android:orientation="horizontal"
app:layout_constraintTop_toBottomOf="@+id/top_bar">
<LinearLayout
android:layout_width="@dimen/dp_0"
android:layout_height="@dimen/dp_32"
android:layout_marginLeft="@dimen/dp_20"
android:layout_marginTop="@dimen/dp_6"
android:layout_marginRight="@dimen/dp_20"
android:layout_marginBottom="@dimen/dp_6"
android:layout_weight="1"
android:background="@drawable/shape_search_in"
android:gravity="center_vertical"
android:orientation="horizontal">
<ImageView
android:id="@+id/iv_close"
android:layout_width="@dimen/dp_18"
android:layout_height="@dimen/dp_18"
android:layout_marginLeft="@dimen/dp_11"
android:layout_marginRight="@dimen/dp_7"
android:src="@drawable/index_level_search" />
<EditText
android:id="@+id/edit_query"
android:layout_width="@dimen/dp_0"
android:layout_height="match_parent"
android:layout_weight="1"
android:background="@android:color/transparent"
android:hint="请输入ID/用户搜索"
android:maxLength="10"
android:singleLine="true"
android:textColor="#333333"
android:textColorHint="@color/color_FF999999"
android:textSize="@dimen/sp_12" />
</LinearLayout>
<TextView
android:id="@+id/tv_cancel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingRight="@dimen/dp_20"
android:text="搜索"
android:textColor="@color/color_FF333333"
android:textSize="@dimen/sp_14" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
app:layout_constraintTop_toBottomOf="@id/ll_search">
<com.scwang.smartrefresh.layout.SmartRefreshLayout
android:id="@+id/smart_refresh_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:srlEnableLoadMore="true"
app:srlEnableRefresh="true">
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recycle_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/dp_40"
android:clipToPadding="false"/>
</com.scwang.smartrefresh.layout.SmartRefreshLayout>
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View File

@@ -0,0 +1,74 @@
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
tools:context=".activity.user.activity.PropMallActivity">
<androidx.coordinatorlayout.widget.CoordinatorLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.google.android.material.appbar.AppBarLayout
android:id="@+id/app_bar_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/color_transparent"
app:elevation="0dp">
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/constraint_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingLeft="16dp"
android:paddingTop="@dimen/dp_10"
android:paddingRight="16dp"
app:layout_scrollFlags="scroll|enterAlways">
<com.xscm.moduleutil.widget.CustomTopBar
android:id="@+id/top_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintTop_toTopOf="parent" />
<com.stx.xhb.xbanner.XBanner
android:id="@+id/banner"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_64"
android:layout_marginTop="@dimen/dp_12"
app:AutoPlayTime="3000"
app:isAutoPlay="true"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/top_bar"
app:pointsVisibility="false" />
</androidx.constraintlayout.widget.ConstraintLayout>
<com.google.android.material.tabs.TabLayout
android:id="@+id/sliding_tab_layout"
android:layout_width="wrap_content"
android:layout_height="@dimen/dp_34"
android:layout_marginLeft="@dimen/dp_16"
android:layout_marginTop="@dimen/dp_12"
android:layout_marginRight="@dimen/dp_16"
app:tabIndicatorFullWidth="false"
app:tabIndicatorHeight="@dimen/dp_2"
app:tabIndicatorGravity="bottom"
app:tabMode="scrollable"
app:tabMinWidth="@dimen/dp_30"
app:tabIndicatorColor="@color/colorPrimary"
app:tabTextAppearance="@style/CustomTabTextAppearance"
app:tabTextColor="#F1ECFF" />
</com.google.android.material.appbar.AppBarLayout>
<androidx.viewpager2.widget.ViewPager2
android:id="@+id/view_pager"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginHorizontal="@dimen/dp_14"
app:layout_behavior="com.google.android.material.appbar.AppBarLayout$ScrollingViewBehavior" />
</androidx.coordinatorlayout.widget.CoordinatorLayout>
</layout>

View File

@@ -50,7 +50,7 @@
android:layout_marginStart="@dimen/dp_16" android:layout_marginStart="@dimen/dp_16"
android:layout_marginTop="@dimen/dp_12" android:layout_marginTop="@dimen/dp_12"
android:layout_marginEnd="@dimen/dp_16" android:layout_marginEnd="@dimen/dp_16"
android:visibility="gone"> >
<ImageView <ImageView
android:id="@+id/im_gg" android:id="@+id/im_gg"

View File

@@ -0,0 +1,25 @@
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/constraintLayout"
tools:context=".activity.user.activity.ui.main.PlaceholderFragment">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recyclerView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="10dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>

View File

@@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="@dimen/dp_90"
android:padding="@dimen/dp_5"
xmlns:app="http://schemas.android.com/apk/res-auto">
<com.xscm.moduleutil.widget.CircularImage
android:id="@+id/im_group"
android:layout_width="@dimen/dp_45"
android:layout_height="@dimen/dp_45"
android:layout_gravity="center"
android:src="@mipmap/ic_launcher_app"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:riv_oval="true" />
<TextView
android:id="@+id/tv_group_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="群聊"
android:textSize="@dimen/sp_12"
android:textColor="@color/color_999999"
app:layout_constraintStart_toStartOf="parent"
android:layout_marginTop="@dimen/dp_5"
app:layout_constraintTop_toBottomOf="@+id/im_group"
app:layout_constraintEnd_toEndOf="parent"/>
</androidx.constraintlayout.widget.ConstraintLayout>

View File

@@ -0,0 +1,74 @@
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
xmlns:tools="http://schemas.android.com/tools">
<LinearLayout
android:id="@+id/ll_szmm"
android:layout_width="match_parent"
android:layout_height="@dimen/dp_62"
android:layout_margin="15dp"
android:layout_gravity="center"
android:gravity="center"
>
<com.xscm.moduleutil.utils.MeHeadView
android:id="@+id/im_user"
android:layout_width="@dimen/dp_50"
android:layout_height="@dimen/dp_50"
android:layout_gravity="center"
android:layout_marginEnd="10dp"
android:src="@mipmap/default_avatar" />
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_gravity="center"
android:gravity="left"
android:orientation="vertical">
<TextView
android:id="@+id/tv_nick_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="16sp"
android:textColor="@color/color_FF333333"
tools:text="@string/set_password" />
<LinearLayout
android:id="@+id/ll_in"
android:layout_width="wrap_content"
android:layout_height="@dimen/dp_16"
android:layout_gravity="center_vertical"
android:gravity="center_vertical"
android:orientation="horizontal"
/>
</LinearLayout>
<TextView
android:id="@+id/tv_oline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="@dimen/dp_10"
android:layout_marginRight="@dimen/dp_10"
android:layout_gravity="center_vertical"
android:gravity="center_vertical"
android:text="[在线]"
android:textColor="@color/color_FF999999"
android:textSize="@dimen/sp_10"
android:visibility="gone"
/>
<TextView
android:id="@+id/im_g"
android:layout_width="@dimen/dp_79"
android:layout_height="@dimen/dp_31"
android:layout_marginEnd="@dimen/dp_16"
android:layout_gravity="center"
android:gravity="center"
/>
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>

View File

@@ -69,7 +69,7 @@
app:layout_constraintTop_toTopOf="parent" app:layout_constraintTop_toTopOf="parent"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
android:gravity="center" android:gravity="center"
android:text="x30" tools:text="x30"
android:textColor="@color/color_FF333333" android:textColor="@color/color_FF333333"
android:textSize="@dimen/sp_10" /> android:textSize="@dimen/sp_10" />
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

View File

@@ -0,0 +1,93 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/zb_bg_ll"
android:layout_width="@dimen/dp_87"
android:layout_height="@dimen/dp_142"
android:background="@mipmap/room_gift_bjx"
android:orientation="vertical"
>
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/zb_bg"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical">
<ImageView
android:id="@+id/iv_img"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_marginLeft="9dp"
android:layout_marginTop="15dp"
android:layout_marginRight="9dp"
android:src="@mipmap/default_image"
app:layout_constraintDimensionRatio="1:1.2"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/tv_name_period"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:layout_marginTop="5dp"
android:textColor="@color/color_FF333333"
android:textSize="13sp"
android:textStyle="bold"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/iv_img"
tools:text="梦幻之翼" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:layout_marginTop="@dimen/dp_1"
android:orientation="horizontal"
android:layout_marginBottom="@dimen/dp_5"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/tv_name_period">
<TextView
android:id="@+id/discount"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:drawableStart="@mipmap/jinb"
android:textColor="@color/color_FF333333"
android:textSize="13sp"
tools:text="28" />
<TextView
android:id="@+id/original_price"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginStart="@dimen/dp_3"
android:textColor="@color/color_999999"
android:textSize="13sp"
tools:text="30" />
</LinearLayout>
<TextView
android:id="@+id/discount_str"
android:layout_width="@dimen/dp_35"
android:layout_height="@dimen/dp_13"
android:background="@mipmap/text_bj"
android:gravity="center"
android:textColor="@color/white"
android:textSize="@dimen/sp_10"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="x30" />
</androidx.constraintlayout.widget.ConstraintLayout>
</LinearLayout>

View File

@@ -51,7 +51,7 @@
app:layout_constraintTop_toTopOf="parent" app:layout_constraintTop_toTopOf="parent"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
android:gravity="center" android:gravity="center"
android:text="x30" tools:text="x30"
android:textColor="@color/color_FF333333" android:textColor="@color/color_FF333333"
android:textSize="@dimen/sp_10" /> android:textSize="@dimen/sp_10" />
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

View File

@@ -5,4 +5,7 @@
<string name="main_tab4">我的</string> <string name="main_tab4">我的</string>
<!-- TODO: Remove or change this placeholder text --> <!-- TODO: Remove or change this placeholder text -->
<string name="hello_blank_fragment">Hello blank fragment</string> <string name="hello_blank_fragment">Hello blank fragment</string>
<string name="title_activity_prop_mall">PropMallActivity</string>
<string name="tab_text_1">Tab 1</string>
<string name="tab_text_2">Tab 2</string>
</resources> </resources>

View File

@@ -0,0 +1,11 @@
<resources>
<style name="AppTheme.NoActionBar">
<item name="windowActionBar">false</item>
<item name="windowNoTitle">true</item>
</style>
<style name="AppTheme.AppBarOverlay" parent="ThemeOverlay.AppCompat.Dark.ActionBar" />
<style name="AppTheme.PopupOverlay" parent="ThemeOverlay.AppCompat.Light" />
</resources>

View File

@@ -39,7 +39,7 @@ class DownloadManager private constructor(builder: Builder) : Serializable {
} }
private var application: Application = builder.application private var application: Application = builder.application
private var apkVersionCode: Int internal var apkVersionCode: Int
private var showNewerToast: Boolean private var showNewerToast: Boolean
internal var contextClsName: String = builder.contextClsName internal var contextClsName: String = builder.contextClsName
internal var apkUrl: String internal var apkUrl: String

View File

@@ -151,7 +151,15 @@ class DownloadService : Service(), OnDownloadListener {
) )
} }
if (manager.jumpInstallPage) { if (manager.jumpInstallPage) {
ApkUtil.installApk(this@DownloadService, Constant.AUTHORITIES!!, apk) if (apk.toPath().toString().contains(manager.apkVersionCode.toString())) {
ApkUtil.installApk(this@DownloadService, Constant.AUTHORITIES!!, apk)
} else {
Toast.makeText(
this@DownloadService,
"当前下载的版本不正确,重新下载或者联系管理员",
Toast.LENGTH_SHORT
)
}
} }
manager.onDownloadListeners.forEach { it.done(apk) } manager.onDownloadListeners.forEach { it.done(apk) }

View File

@@ -3,8 +3,11 @@ package com.azhon.appupdate.util
import android.content.Context import android.content.Context
import android.content.Intent import android.content.Intent
import android.content.pm.PackageManager import android.content.pm.PackageManager
import android.media.MediaScannerConnection
import android.net.Uri import android.net.Uri
import android.os.Build import android.os.Build
import android.os.Handler
import android.os.Looper
import android.os.PatternMatcher import android.os.PatternMatcher
import androidx.core.content.FileProvider import androidx.core.content.FileProvider
import java.io.File import java.io.File
@@ -23,7 +26,20 @@ class ApkUtil {
* install package form file * install package form file
*/ */
fun installApk(context: Context, authorities: String, apk: File) { fun installApk(context: Context, authorities: String, apk: File) {
context.startActivity(createInstallIntent(context, authorities, apk)) // context.startActivity(createInstallIntent(context, authorities, apk))
// 偏方:针对某些厂商安装器的缓存问题
// 1. 主动刷新媒体库即使我们用了FileProvider也扫描一下影响系统相册的数据库
MediaScannerConnection.scanFile(context,
arrayOf(apk.absolutePath),
arrayOf("application/vnd.android.package-archive"),
null)
// 2. 短暂延迟,给系统一点处理时间
Handler(Looper.getMainLooper()).postDelayed({
// 3. 再启动安装
val intent = createInstallIntent(context, authorities, apk)
context.startActivity(intent)
}, 500) // 延迟500毫秒
} }
fun createInstallIntent(context: Context, authorities: String, apk: File): Intent { fun createInstallIntent(context: Context, authorities: String, apk: File): Intent {

View File

@@ -16,6 +16,7 @@ import android.view.WindowManager
import android.widget.Button import android.widget.Button
import android.widget.ImageView import android.widget.ImageView
import android.widget.TextView import android.widget.TextView
import android.widget.Toast
import androidx.activity.OnBackPressedCallback import androidx.activity.OnBackPressedCallback
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import androidx.core.app.ActivityCompat import androidx.core.app.ActivityCompat
@@ -177,8 +178,14 @@ class UpdateDialogActivity : AppCompatActivity(), View.OnClickListener {
} }
R.id.btn_update -> { R.id.btn_update -> {
if (btnUpdate.tag == install) { if (btnUpdate.tag == install) {
ApkUtil.installApk(this, Constant.AUTHORITIES!!, apk) if (apk.toString().contains(manager?.apkVersionCode.toString())){
return ApkUtil.installApk(this, Constant.AUTHORITIES!!, apk)
return
}else{
Toast.makeText(this, "当前版本不对,请联系管理员", Toast.LENGTH_SHORT).show()
return
}
} }
if (!checkPermission()) { if (!checkPermission()) {
startUpdate() startUpdate()

View File

@@ -28,8 +28,8 @@ isBuildModule=false
#org.gradle.deamon=false #org.gradle.deamon=false
android.injected.testOnly=false android.injected.testOnly=false
APP_VERSION_NAME=1.0.9.3 APP_VERSION_NAME=1.0.9.6
APP_VERSION_CODE=83 APP_VERSION_CODE=86
org.gradle.jvm.toolchain.useLegacyAdapters=false org.gradle.jvm.toolchain.useLegacyAdapters=false
#org.gradle.java.home=C\:\\Users\\qx\\.jdks\\ms-17.0.15 #org.gradle.java.home=C\:\\Users\\qx\\.jdks\\ms-17.0.15

View File

@@ -6,6 +6,7 @@ import android.text.TextUtils;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import androidx.annotation.Nullable; import androidx.annotation.Nullable;
import com.alibaba.android.arouter.launcher.ARouter; import com.alibaba.android.arouter.launcher.ARouter;
@@ -83,11 +84,22 @@ public class TUIGroupChatFragment extends TUIBaseChatFragment {
titleBar.setOnRightClickListener(new View.OnClickListener() { titleBar.setOnRightClickListener(new View.OnClickListener() {
@Override @Override
public void onClick(View v) { public void onClick(View v) {
Intent intent = new Intent();
intent.setAction("com.example.mainmodule.action.GROUP_CHAT_SETTINGS");
// 可以传递参数
intent.putExtra("groupId", chatInfo.getId());
// 如果需要可以设置Category
intent.addCategory("com.example.mainmodule.category.DETAIL");
// 确保跳转的Activity是在当前任务栈中而不是启动一个新的任务栈
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
// ARouter.getInstance().build("/moduleUtil/WebViewActivity").withString("id", chatInfo.getId()).navigation();
// EventBus.getDefault().post(chatInfo); // EventBus.getDefault().post(chatInfo);
// String id = chatInfo.getId().replace("g", ""); // String id = chatInfo.getId().replace("g", "");
ARouter.getInstance().build("/moduleUtil/WebViewActivity").withString("id", chatInfo.getId()).navigation();
// Map<String, Object> param = new HashMap<>(); // Map<String, Object> param = new HashMap<>();
// if (TUIChatUtils.isTopicGroup(chatInfo.getId())) { // if (TUIChatUtils.isTopicGroup(chatInfo.getId())) {
// param.put(TUIConstants.TUIChat.Extension.ChatNavigationMoreItem.TOPIC_ID, chatInfo.getId()); // param.put(TUIConstants.TUIChat.Extension.ChatNavigationMoreItem.TOPIC_ID, chatInfo.getId());

View File

@@ -267,7 +267,7 @@ public class TUIConversationFragment extends Fragment {
mConversationPopWindow.setBackgroundDrawable(new ColorDrawable()); mConversationPopWindow.setBackgroundDrawable(new ColorDrawable());
mConversationPopWindow.setOutsideTouchable(true); mConversationPopWindow.setOutsideTouchable(true);
int width = ConversationUtils.getListUnspecifiedWidth(mConversationPopAdapter, mConversationPopList); int width = ConversationUtils.getListUnspecifiedWidth(mConversationPopAdapter, mConversationPopList);
mConversationPopWindow.setWidth(width); mConversationPopWindow.setWidth(width*2);
mConversationPopWindow.setOnDismissListener(new PopupWindow.OnDismissListener() { mConversationPopWindow.setOnDismissListener(new PopupWindow.OnDismissListener() {
@Override @Override
public void onDismiss() { public void onDismiss() {