Compare commits

...

12 Commits

Author SHA1 Message Date
c96d41ccd7 1:修改测试H5的地址 2025-09-26 15:55:08 +08:00
3b6df9ec66 Merge remote-tracking branch 'origin/master' 2025-09-26 15:44:49 +08:00
77a1d910f0 1.定位的修改 2025-09-26 15:43:31 +08:00
393c59dd1b 1.定位的问题 2025-09-26 15:43:23 +08:00
a883aa86e5 1.定位的问题 2025-09-26 15:43:10 +08:00
7e14ba3fcb 添加ignore文件 2025-09-26 15:15:16 +08:00
43c431cc8f Remove .idea directory from version control 2025-09-26 15:09:18 +08:00
bd4a769347 Add .gitignore file to exclude Android Studio configs 2025-09-26 15:09:07 +08:00
2673835fc6 Merge branch 'dev_lxj' 2025-09-26 14:43:12 +08:00
7a084b6b2b 1.定位的修改 2025-09-26 14:22:48 +08:00
e55effea1a 1.定位的问题 2025-09-26 01:18:18 +08:00
bba729f5d0 1.定位的问题 2025-09-26 01:13:02 +08:00
35 changed files with 986 additions and 425 deletions

25
.gitignore vendored
View File

@@ -1,20 +1,9 @@
.idea/
*.iml
.gradle
/local.properties
/.idea/caches
/.idea/libraries
/.idea/modules.xml
/.idea/workspace.xml
/.idea/navEditor.xml
/.idea/assetWizardSettings.xml
.DS_Store
/build
/captures
.externalNativeBuild
.cxx
build/
local.properties
# ProGuard files
/app/proguard/
/seeds.txt
/usage.txt
/mapping.txt
.gradle/
.externalNativeBuild/
.DS_Store
*.dm
*.log

3
.idea/.gitignore generated vendored
View File

@@ -1,3 +0,0 @@
# Default ignored files
/shelf/
/workspace.xml

1
.idea/.name generated
View File

@@ -1 +0,0 @@
秘地

View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="AppInsightsSettings">
<option name="selectedTabId" value="Android Vitals" />
</component>
</project>

View File

@@ -1,117 +0,0 @@
<component name="ProjectCodeStyleConfiguration">
<code_scheme name="Project" version="173">
<codeStyleSettings language="XML">
<option name="FORCE_REARRANGE_MODE" value="1" />
<indentOptions>
<option name="CONTINUATION_INDENT_SIZE" value="4" />
</indentOptions>
<arrangement>
<rules>
<section>
<rule>
<match>
<AND>
<NAME>xmlns:android</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>^$</XML_NAMESPACE>
</AND>
</match>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>xmlns:.*</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>^$</XML_NAMESPACE>
</AND>
</match>
<order>BY_NAME</order>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>.*:id</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>
</AND>
</match>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>.*:name</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>
</AND>
</match>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>name</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>^$</XML_NAMESPACE>
</AND>
</match>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>style</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>^$</XML_NAMESPACE>
</AND>
</match>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>.*</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>^$</XML_NAMESPACE>
</AND>
</match>
<order>BY_NAME</order>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>.*</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>
</AND>
</match>
<order>ANDROID_ATTRIBUTE_ORDER</order>
</rule>
</section>
<section>
<rule>
<match>
<AND>
<NAME>.*</NAME>
<XML_ATTRIBUTE />
<XML_NAMESPACE>.*</XML_NAMESPACE>
</AND>
</match>
<order>BY_NAME</order>
</rule>
</section>
</rules>
</arrangement>
</codeStyleSettings>
</code_scheme>
</component>

6
.idea/compiler.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<bytecodeTargetLevel target="17" />
</component>
</project>

View File

@@ -13,12 +13,6 @@
</DropdownSelection>
<DialogSelection />
</SelectionState>
<SelectionState runConfigName="moduleactivity">
<option name="selectionMode" value="DROPDOWN" />
</SelectionState>
<SelectionState runConfigName="muduleactivity">
<option name="selectionMode" value="DROPDOWN" />
</SelectionState>
</selectionStates>
</component>
</project>
</project>

6
.idea/encodings.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="Encoding" defaultCharsetForPropertiesFiles="UTF-8">
<file url="PROJECT" charset="UTF-8" />
</component>
</project>

33
.idea/gradle.xml generated
View File

@@ -1,33 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="GradleMigrationSettings" migrationVersion="1" />
<component name="GradleSettings">
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="testRunner" value="CHOOSE_PER_TEST" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="gradleJvm" value="jbr-17" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" />
<option value="$PROJECT_DIR$/moduleLogin" />
<option value="$PROJECT_DIR$/moduleUtil" />
<option value="$PROJECT_DIR$/modulecircle" />
<option value="$PROJECT_DIR$/modulemain" />
<option value="$PROJECT_DIR$/modulenews" />
<option value="$PROJECT_DIR$/moduleroom" />
<option value="$PROJECT_DIR$/moduletablayout" />
<option value="$PROJECT_DIR$/modulevocal" />
<option value="$PROJECT_DIR$/modulevoice" />
<option value="$PROJECT_DIR$/timcommon" />
<option value="$PROJECT_DIR$/tuichat" />
<option value="$PROJECT_DIR$/tuiconversation" />
<option value="$PROJECT_DIR$/tuicore" />
</set>
</option>
<option name="resolveExternalAnnotations" value="false" />
</GradleProjectSettings>
</option>
</component>
</project>

View File

@@ -1,63 +0,0 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="AutoCloseableResource" enabled="true" level="WARNING" enabled_by_default="true">
<option name="METHOD_MATCHER_CONFIG" value="java.util.Formatter,format,java.io.Writer,append,com.google.common.base.Preconditions,checkNotNull,org.hibernate.Session,close,java.io.PrintWriter,printf,java.io.PrintStream,printf,java.lang.foreign.Arena,ofAuto,java.lang.foreign.Arena,global,android.content.Context,obtainStyledAttributes" />
</inspection_tool>
<inspection_tool class="ComposePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="JavadocDeclaration" enabled="true" level="WARNING" enabled_by_default="true">
<option name="ADDITIONAL_TAGS" value="data,description:" />
</inspection_tool>
<inspection_tool class="PreviewAnnotationInFunctionWithParameters" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewApiLevelMustBeValid" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewDeviceShouldUseNewSpec" enabled="true" level="WEAK WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewFontScaleMustBeGreaterThanZero" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewMultipleParameterProviders" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewPickerAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
<option name="previewFile" value="true" />
</inspection_tool>
</profile>
</component>

6
.idea/kotlinc.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="KotlinJpsPluginSettings">
<option name="version" value="1.9.24" />
</component>
</project>

10
.idea/migrations.xml generated
View File

@@ -1,10 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectMigrations">
<option name="MigrateToGradleLocalJavaHome">
<set>
<option value="$PROJECT_DIR$" />
</set>
</option>
</component>
</project>

55
.idea/misc.xml generated
View File

@@ -1,55 +0,0 @@
<project version="4">
<component name="ExternalStorageConfigurationManager" enabled="true" />
<component name="NullableNotNullManager">
<option name="myDefaultNullable" value="androidx.annotation.Nullable" />
<option name="myDefaultNotNull" value="androidx.annotation.NonNull" />
<option name="myNullables">
<value>
<list size="15">
<item index="0" class="java.lang.String" itemvalue="org.jspecify.annotations.Nullable" />
<item index="1" class="java.lang.String" itemvalue="com.android.annotations.Nullable" />
<item index="2" class="java.lang.String" itemvalue="androidx.annotation.RecentlyNullable" />
<item index="3" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.compatqual.NullableDecl" />
<item index="4" class="java.lang.String" itemvalue="org.jetbrains.annotations.Nullable" />
<item index="5" class="java.lang.String" itemvalue="androidx.annotation.Nullable" />
<item index="6" class="java.lang.String" itemvalue="org.eclipse.jdt.annotation.Nullable" />
<item index="7" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.Nullable" />
<item index="8" class="java.lang.String" itemvalue="android.support.annotation.Nullable" />
<item index="9" class="java.lang.String" itemvalue="jakarta.annotation.Nullable" />
<item index="10" class="java.lang.String" itemvalue="javax.annotation.CheckForNull" />
<item index="11" class="java.lang.String" itemvalue="javax.annotation.Nullable" />
<item index="12" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.qual.Nullable" />
<item index="13" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.compatqual.NullableType" />
<item index="14" class="java.lang.String" itemvalue="android.annotation.Nullable" />
</list>
</value>
</option>
<option name="myNotNulls">
<value>
<list size="15">
<item index="0" class="java.lang.String" itemvalue="androidx.annotation.RecentlyNonNull" />
<item index="1" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.qual.NonNull" />
<item index="2" class="java.lang.String" itemvalue="org.jspecify.annotations.NonNull" />
<item index="3" class="java.lang.String" itemvalue="jakarta.annotation.Nonnull" />
<item index="4" class="java.lang.String" itemvalue="androidx.annotation.NonNull" />
<item index="5" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.compatqual.NonNullType" />
<item index="6" class="java.lang.String" itemvalue="android.support.annotation.NonNull" />
<item index="7" class="java.lang.String" itemvalue="com.android.annotations.NonNull" />
<item index="8" class="java.lang.String" itemvalue="edu.umd.cs.findbugs.annotations.NonNull" />
<item index="9" class="java.lang.String" itemvalue="org.checkerframework.checker.nullness.compatqual.NonNullDecl" />
<item index="10" class="java.lang.String" itemvalue="org.jetbrains.annotations.NotNull" />
<item index="11" class="java.lang.String" itemvalue="javax.annotation.Nonnull" />
<item index="12" class="java.lang.String" itemvalue="org.eclipse.jdt.annotation.NonNull" />
<item index="13" class="java.lang.String" itemvalue="android.annotation.NonNull" />
<item index="14" class="java.lang.String" itemvalue="lombok.NonNull" />
</list>
</value>
</option>
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="jbr-17" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
</project>

View File

@@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="RunConfigurationProducerService">
<option name="ignoredProducers">
<set>
<option value="com.intellij.execution.junit.AbstractAllInDirectoryConfigurationProducer" />
<option value="com.intellij.execution.junit.AllInPackageConfigurationProducer" />
<option value="com.intellij.execution.junit.PatternConfigurationProducer" />
<option value="com.intellij.execution.junit.TestInClassConfigurationProducer" />
<option value="com.intellij.execution.junit.UniqueIdConfigurationProducer" />
<option value="com.intellij.execution.junit.testDiscovery.JUnitTestDiscoveryConfigurationProducer" />
<option value="org.jetbrains.kotlin.idea.junit.KotlinJUnitRunConfigurationProducer" />
<option value="org.jetbrains.kotlin.idea.junit.KotlinPatternConfigurationProducer" />
</set>
</option>
</component>
</project>

6
.idea/vcs.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>

View File

@@ -47,6 +47,7 @@ logger = "2.2.0"
loggingInterceptorVersion = "3.10.0"
multidex = "2.0.1"
ossAndroidSdkVersion = "2.9.21"
permissionx = "1.7.1"
persistentcookiejar = "v1.0.1"
picture_libraryVersion = "v2.6.0"
reactivexRxjava = "2.2.21"
@@ -125,6 +126,7 @@ logger = { module = "com.orhanobut:logger", version.ref = "logger" }
multidex = { module = "androidx.multidex:multidex", version.ref = "multidex" }
#numberprogressbar-library = { module = "com.daimajia.numberprogressbar:library", version.ref = "libraryVersion" }
okhttp3-logging-interceptor = { module = "com.squareup.okhttp3:logging-interceptor", version.ref = "loggingInterceptorVersion" }
permissionx = { module = "com.guolindev.permissionx:permissionx", version.ref = "permissionx" }
persistentcookiejar = { module = "com.github.franmontiel:PersistentCookieJar", version.ref = "persistentcookiejar" }
#pictureselector-picture_library = { module = "com.github.LuckSiege.PictureSelector:picture_library", version.ref = "picture_libraryVersion" }
reactivex-rxjava = { module = "io.reactivex.rxjava2:rxjava", version.ref = "reactivexRxjava" }

View File

@@ -1,8 +1,6 @@
#Wed May 07 09:31:48 CST 2025
#Mon Sep 22 21:05:11 CST 2025
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
#distributionUrl=https\://mirrors.cloud.tencent.com/gradle/gradle-8.7-all.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.10.2-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
#distributionUrl=file:///D:/Greadle/gradle-8.10.2-all.zip
distributionUrl=file:///D:/Gradle/gradle-8.10.2-bin.zip
zipStorePath=wrapper/distsl.

View File

@@ -215,6 +215,8 @@ dependencies {
api 'org.eclipse.paho:org.eclipse.paho.client.mqttv3:1.2.5'
api 'io.github.mayzs:paho.mqtt.android:1.2.1'
// room数据库
// def room_version = "2.5.0"
// implementation "androidx.room:room-runtime:$room_version"

View File

@@ -43,13 +43,13 @@ import org.greenrobot.eventbus.Subscribe;
import org.greenrobot.eventbus.ThreadMode;
public abstract class BaseMvpActivity<P extends IPresenter, VDB extends ViewDataBinding> extends BaseAppCompatActivity<VDB> implements
IView<Activity>, LocationProvider.LocationCallback {
IView<Activity> {
protected P MvpPre;
protected abstract P bindPresenter();
private String city1;
@Override
protected void initView() {
@@ -120,7 +120,7 @@ public abstract class BaseMvpActivity<P extends IPresenter, VDB extends ViewData
// 错误处理
}
});
initLocation();
//initLocation();
}
});
V2TIMManager.getInstance().addIMSDKListener(imSdkListener);
@@ -184,51 +184,7 @@ public abstract class BaseMvpActivity<P extends IPresenter, VDB extends ViewData
}, false, 0).show();
}
private SystemLocationProvider locationProvider;
private void initLocation() {
if (ContextCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
// 请求定位权限
ActivityCompat.requestPermissions(
(Activity) this,
new String[]{
android.Manifest.permission.ACCESS_FINE_LOCATION,
Manifest.permission.ACCESS_COARSE_LOCATION
},
1001 // 自定义常量,比如 1001
);
}
locationProvider = new SystemLocationProvider();
// 请求一次性的位置信息
locationProvider.getLastKnownLocation(this, this);
}
@Override
public void onLocationReceived(double latitude, double longitude, String city) {
LogUtils.e("当前位置:" + city);
city1 = city;
EventBus.getDefault().post(city1);
}
@Override
public void onFailed(String errorMessage) {
LogUtils.e("定位失败");
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if (requestCode == 1001) {
if (locationProvider == null) {
locationProvider = new SystemLocationProvider();
}
locationProvider.getLastKnownLocation(this, this);
}
}
@Override
public Resources getResources() {

View File

@@ -26,7 +26,7 @@ public enum EnvironmentEnum {
1600106397,
"05b406b4541e413887d8d2bf9be8642c",
"tcp://1.13.181.248",
"https://chatvespa.qxmier.com");
"https://tmd.xscmmidi.site/h5");
private final String serverUrl;//服务器地址
private final String ALI_AUTH_KEY;//阿里云授权key

View File

@@ -0,0 +1,119 @@
package com.xscm.moduleutil.view;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import androidx.appcompat.widget.AppCompatImageView;
import com.xscm.moduleutil.R;
public class AvatarWithDecoration extends AppCompatImageView {
// 挂件图片
private Drawable decoration;
// 挂件位置偏移量
private int decorationOffsetX = 0;
private int decorationOffsetY = 0;
// 挂件大小比例(相对于头像)
private float decorationScale = 0.3f;
public AvatarWithDecoration(Context context) {
super(context);
init();
}
public AvatarWithDecoration(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
public AvatarWithDecoration(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init();
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.AvatarWithDecoration);
decoration = a.getDrawable(R.styleable.AvatarWithDecoration_decoration);
decorationScale = a.getFloat(R.styleable.AvatarWithDecoration_decorationScale, 0.3f);
decorationOffsetX = a.getInt(R.styleable.AvatarWithDecoration_decorationOffsetX, 0);
decorationOffsetY = a.getInt(R.styleable.AvatarWithDecoration_decorationOffsetY, 0);
a.recycle();
}
private void init() {
// 可以在这里设置默认的挂件
decoration = getResources().getDrawable(R.mipmap.xlh_image);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
// 如果有挂件,则绘制挂件
if (decoration != null) {
drawDecoration(canvas);
}
}
private void drawDecoration(Canvas canvas) {
// 获取头像的宽高
int avatarWidth = getWidth();
int avatarHeight = getHeight();
// 计算挂件的大小
int decorationWidth = (int) (avatarWidth * decorationScale);
int decorationHeight = (int) (avatarHeight * decorationScale);
// 计算挂件的位置(右下角)
int left = avatarWidth - decorationWidth + decorationOffsetX;
int top = avatarHeight - decorationHeight + decorationOffsetY;
int right = left + decorationWidth;
int bottom = top + decorationHeight;
// 设置挂件的绘制边界
decoration.setBounds(left, top, right, bottom);
// 绘制挂件
decoration.draw(canvas);
}
/**
* 设置挂件图片
*/
public void setDecoration(Drawable decoration) {
this.decoration = decoration;
invalidate();
}
/**
* 设置挂件图片通过Bitmap
*/
public void setDecoration(Bitmap bitmap) {
if (bitmap != null) {
this.decoration = new BitmapDrawable(getResources(), bitmap);
invalidate();
}
}
/**
* 设置挂件位置偏移量
*/
public void setDecorationOffset(int offsetX, int offsetY) {
this.decorationOffsetX = offsetX;
this.decorationOffsetY = offsetY;
invalidate();
}
/**
* 设置挂件大小比例
*/
public void setDecorationScale(float scale) {
if (scale > 0 && scale <= 1) {
this.decorationScale = scale;
invalidate();
}
}
}

View File

@@ -0,0 +1,373 @@
package com.xscm.moduleutil.view;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Bitmap;
import android.graphics.BitmapShader;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PointF;
import android.graphics.RectF;
import android.graphics.Shader;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.util.TypedValue;
import android.view.View;
import androidx.annotation.Nullable;
import com.bumptech.glide.Glide;
import com.bumptech.glide.request.target.SimpleTarget;
import com.bumptech.glide.request.transition.Transition;
import com.xscm.moduleutil.R;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
public class FashionAvatarView extends View {
// 头像相关属性
private Bitmap mAvatarBitmap;
private String mAvatarUrl;
private Drawable mPlaceholderAvatar;
private int mAvatarRadius;
private int mAvatarBorderWidth;
private int mAvatarBorderColor;
// 顶部标签属性
private String mTagText;
private int mTagTextColor;
private float mTagTextSize;
private int mTagBackgroundColor;
private float mTagCornerRadius;
private int mTagPadding;
private int mTagOffsetY; // 标签Y轴偏移量
// 底部文字属性
private String mBottomText;
private int mBottomTextColor;
private float mBottomTextSize;
private int mBottomTextOffsetY; // 底部文字Y轴偏移量
// 爱心装饰属性
private Drawable mHeartIcon;
private int mHeartCount;
private int mHeartSize;
private List<PointF> mHeartPositions = new ArrayList<>();
private Random mRandom = new Random();
// 画笔
private Paint mAvatarPaint;
private Paint mTextPaint;
private Paint mTagBgPaint;
public FashionAvatarView(Context context) {
this(context, null);
}
public FashionAvatarView(Context context, @Nullable AttributeSet attrs) {
this(context, attrs, 0);
}
public FashionAvatarView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
initAttrs(context, attrs);
initPaints();
}
private void initAttrs(Context context, AttributeSet attrs) {
TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.FashionAvatarView);
// 头像属性
mAvatarUrl = ta.getString(R.styleable.FashionAvatarView_avatarUrl);
mPlaceholderAvatar = ta.getDrawable(R.styleable.FashionAvatarView_placeholderAvatar);
mAvatarRadius = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_avatarRadius, dp2px(60));
mAvatarBorderWidth = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_avatarBorderWidth, dp2px(2));
mAvatarBorderColor = ta.getColor(R.styleable.FashionAvatarView_avatarBorderColor, Color.parseColor("#FFD700"));
// 顶部标签属性
mTagText = ta.getString(R.styleable.FashionAvatarView_tagText);
mTagTextColor = ta.getColor(R.styleable.FashionAvatarView_tagTextColor, Color.WHITE);
mTagTextSize = ta.getDimension(R.styleable.FashionAvatarView_tagTextSize, sp2px(12));
mTagBackgroundColor = ta.getColor(R.styleable.FashionAvatarView_tagBackgroundColor, Color.parseColor("#FFA500"));
mTagCornerRadius = ta.getDimension(R.styleable.FashionAvatarView_tagCornerRadius, dp2px(4));
mTagPadding = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_tagPadding, dp2px(4));
mTagOffsetY = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_tagOffsetY, 0);
// 底部文字属性
mBottomText = ta.getString(R.styleable.FashionAvatarView_bottomText);
mBottomTextColor = ta.getColor(R.styleable.FashionAvatarView_bottomTextColor, Color.WHITE);
mBottomTextSize = ta.getDimension(R.styleable.FashionAvatarView_bottomTextSize, sp2px(14));
mBottomTextOffsetY = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_bottomTextOffsetY, dp2px(10));
// 爱心装饰属性
mHeartIcon = ta.getDrawable(R.styleable.FashionAvatarView_heartIcon);
if (mHeartIcon == null) {
try {
mHeartIcon = context.getResources().getDrawable(R.mipmap.xlh_image);
} catch (Exception e) {
e.printStackTrace();
}
}
mHeartCount = ta.getInt(R.styleable.FashionAvatarView_heartCount, 6);
mHeartSize = ta.getDimensionPixelSize(R.styleable.FashionAvatarView_heartSize, dp2px(16));
ta.recycle();
// 加载头像
if (mAvatarUrl != null && !mAvatarUrl.isEmpty()) {
loadAvatarFromNetwork();
} else if (mPlaceholderAvatar != null) {
mAvatarBitmap = drawableToBitmap(mPlaceholderAvatar);
}
}
private void initPaints() {
// 头像画笔
mAvatarPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mAvatarPaint.setDither(true);
// 文字画笔
mTextPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mTextPaint.setTextAlign(Paint.Align.CENTER);
// 标签背景画笔
mTagBgPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mTagBgPaint.setColor(mTagBackgroundColor);
}
private void loadAvatarFromNetwork() {
Glide.with(this)
.asBitmap()
.load(mAvatarUrl)
.into(new SimpleTarget<Bitmap>() {
@Override
public void onResourceReady(Bitmap resource, Transition<? super Bitmap> transition) {
mAvatarBitmap = resource;
invalidate();
}
@Override
public void onLoadFailed(@Nullable Drawable errorDrawable) {
super.onLoadFailed(errorDrawable);
if (mPlaceholderAvatar != null) {
mAvatarBitmap = drawableToBitmap(mPlaceholderAvatar);
}
invalidate();
}
});
}
private Bitmap drawableToBitmap(Drawable drawable) {
if (drawable instanceof BitmapDrawable) {
return ((BitmapDrawable) drawable).getBitmap();
}
if (drawable == null) {
return null;
}
int width = drawable.getIntrinsicWidth();
int height = drawable.getIntrinsicHeight();
if (width <= 0) width = mAvatarRadius * 2;
if (height <= 0) height = mAvatarRadius * 2;
Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
drawable.draw(canvas);
return bitmap;
}
private void initHeartPositions() {
mHeartPositions.clear();
if (mHeartIcon == null || mHeartCount <= 0 || mHeartSize <= 0) {
return;
}
int centerX = getWidth() / 2;
int centerY = getAvatarCenterY();
// 爱心围绕的半径,比头像大一些
int radius = mAvatarRadius + mAvatarBorderWidth + mHeartSize / 2;
for (int i = 0; i < mHeartCount; i++) {
// 随机分布在头像周围
double angle = 2 * Math.PI * mRandom.nextDouble();
// 稍微随机调整距离,让分布更自然
float distanceFactor = 0.8f + mRandom.nextFloat() * 0.4f;
float x = (float) (centerX + radius * distanceFactor * Math.cos(angle));
float y = (float) (centerY + radius * distanceFactor * Math.sin(angle));
mHeartPositions.add(new PointF(x, y));
}
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// 计算宽度:直径 + 左右可能的爱心空间
int width = 2 * (mAvatarRadius + mAvatarBorderWidth + mHeartSize / 2);
// 计算高度:头像直径 + 标签高度 + 底部文字高度 + 间距
int tagHeight = (int) (mTagTextSize + mTagPadding * 2);
int bottomTextHeight = (int) mBottomTextSize;
int height = 2 * (mAvatarRadius + mAvatarBorderWidth)
+ tagHeight / 2 // 标签一半在头像内
+ bottomTextHeight + mBottomTextOffsetY
+ dp2px(10);
setMeasuredDimension(resolveSize(width, widthMeasureSpec),
resolveSize(height, heightMeasureSpec));
}
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
// 视图大小确定后计算爱心位置
initHeartPositions();
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
if (getWidth() == 0 || getHeight() == 0) {
return;
}
int centerX = getWidth() / 2;
int avatarCenterY = getAvatarCenterY();
// 1. 绘制爱心装饰
drawHearts(canvas);
// 2. 绘制头像边框
mAvatarPaint.setColor(mAvatarBorderColor);
mAvatarPaint.setStyle(Paint.Style.FILL);
canvas.drawCircle(centerX, avatarCenterY, mAvatarRadius + mAvatarBorderWidth, mAvatarPaint);
// 3. 绘制头像
if (mAvatarBitmap != null) {
mAvatarPaint.setShader(new BitmapShader(mAvatarBitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP));
canvas.drawCircle(centerX, avatarCenterY, mAvatarRadius, mAvatarPaint);
mAvatarPaint.setShader(null);
}
// 4. 绘制顶部标签
drawTag(canvas, centerX, avatarCenterY);
// 5. 绘制底部文字
drawBottomText(canvas, centerX);
}
private int getAvatarCenterY() {
// 计算头像中心Y坐标考虑标签的高度
int tagHeight = (int) (mTagTextSize + mTagPadding * 2);
return mAvatarRadius + mAvatarBorderWidth + tagHeight / 2 + mTagOffsetY;
}
private void drawHearts(Canvas canvas) {
if (mHeartIcon == null || mHeartPositions.isEmpty()) {
return;
}
canvas.save();
for (PointF point : mHeartPositions) {
int left = (int) (point.x - mHeartSize / 2);
int top = (int) (point.y - mHeartSize / 2);
int right = left + mHeartSize;
int bottom = top + mHeartSize;
// 只绘制在视图范围内的爱心
if (right > 0 && bottom > 0 && left < getWidth() && top < getHeight()) {
mHeartIcon.setBounds(left, top, right, bottom);
mHeartIcon.draw(canvas);
}
}
canvas.restore();
}
private void drawTag(Canvas canvas, int centerX, int avatarCenterY) {
if (mTagText == null || mTagText.isEmpty()) {
return;
}
// 计算标签文字宽度
mTextPaint.setTextSize(mTagTextSize);
float textWidth = mTextPaint.measureText(mTagText);
// 计算标签背景矩形
float tagLeft = centerX - textWidth / 2 - mTagPadding;
float tagRight = centerX + textWidth / 2 + mTagPadding;
// 标签底部与头像顶部对齐
float tagBottom = avatarCenterY - mAvatarRadius - mAvatarBorderWidth;
float tagTop = tagBottom - mTagTextSize - mTagPadding * 2;
RectF tagRect = new RectF(tagLeft, tagTop, tagRight, tagBottom);
// 绘制标签背景
canvas.drawRoundRect(tagRect, mTagCornerRadius, mTagCornerRadius, mTagBgPaint);
// 绘制标签文字
mTextPaint.setColor(mTagTextColor);
Paint.FontMetrics fontMetrics = mTextPaint.getFontMetrics();
float baseLineY = tagBottom - mTagPadding - fontMetrics.bottom;
canvas.drawText(mTagText, centerX, baseLineY, mTextPaint);
}
private void drawBottomText(Canvas canvas, int centerX) {
if (mBottomText == null || mBottomText.isEmpty()) {
return;
}
// 计算文字位置:头像底部下方
int textY = getAvatarCenterY() + mAvatarRadius + mAvatarBorderWidth + mBottomTextOffsetY;
mTextPaint.setColor(mBottomTextColor);
mTextPaint.setTextSize(mBottomTextSize);
Paint.FontMetrics fontMetrics = mTextPaint.getFontMetrics();
float baseLineY = textY - fontMetrics.top;
canvas.drawText(mBottomText, centerX, baseLineY, mTextPaint);
}
// dp转px
private int dp2px(float dp) {
return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp,
getResources().getDisplayMetrics());
}
// sp转px
private float sp2px(float sp) {
return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, sp,
getResources().getDisplayMetrics());
}
// 设置器方法
public void setAvatarUrl(String url) {
this.mAvatarUrl = url;
loadAvatarFromNetwork();
}
public void setTagText(String text) {
this.mTagText = text;
invalidate();
}
public void setBottomText(String text) {
this.mBottomText = text;
invalidate();
}
public void setHeartIcon(Drawable heartIcon) {
this.mHeartIcon = heartIcon;
initHeartPositions();
invalidate();
}
}

View File

@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<!-- 背景颜色,与原代码中的#8D6F28保持一致 -->
<solid android:color="#8D6F28" />
<!-- 圆角半径,可以根据需要调整大小 -->
<corners android:radius="@dimen/dp_5" />
<!-- 可选:添加内边距,让文字与边框有一定距离 -->
<padding
android:left="@dimen/dp_2"
android:right="@dimen/dp_2"
android:top="@dimen/dp_2"
android:bottom="@dimen/dp_2" />
</shape>

View File

@@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<!-- 背景颜色,与原代码中的#8D6F28保持一致 -->
<solid android:color="#906C49E4" />
<!-- 圆角半径,可以根据需要调整大小 -->
<corners android:radius="@dimen/dp_5" />
<!-- 可选:添加内边距,让文字与边框有一定距离 -->
<padding
android:left="@dimen/dp_2"
android:right="@dimen/dp_2"
android:top="@dimen/dp_2"
android:bottom="@dimen/dp_2" />
</shape>

View File

@@ -313,6 +313,7 @@
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="@+id/exchange_layout"
app:layout_constraintBottom_toBottomOf="@+id/exchange_layout"
android:visibility="gone"
/>
<View
@@ -325,6 +326,7 @@
app:layout_constraintEnd_toStartOf="@+id/tv_option"
app:layout_constraintTop_toTopOf="@+id/exchange_layout"
app:layout_constraintBottom_toBottomOf="@+id/exchange_layout"
android:visibility="gone"
/>
<LinearLayout
android:id="@+id/exchange_layout"

Binary file not shown.

Before

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 171 KiB

View File

@@ -0,0 +1,38 @@
<resources>
<declare-styleable name="FashionAvatarView">
<!-- 头像相关属性 -->
<attr name="avatarUrl" format="string" />
<attr name="placeholderAvatar" format="reference" />
<attr name="avatarRadius" format="dimension" />
<attr name="avatarBorderWidth" format="dimension" />
<attr name="avatarBorderColor" format="color" />
<!-- 顶部标签相关属性 -->
<attr name="tagText" format="string" />
<attr name="tagTextColor" format="color" />
<attr name="tagTextSize" format="dimension" />
<attr name="tagBackgroundColor" format="color" />
<attr name="tagCornerRadius" format="dimension" />
<attr name="tagPadding" format="dimension" />
<attr name="tagOffsetY" format="dimension" />
<!-- 底部文字相关属性 -->
<attr name="bottomText" format="string" />
<attr name="bottomTextColor" format="color" />
<attr name="bottomTextSize" format="dimension" />
<attr name="bottomTextOffsetY" format="dimension" />
<!-- 爱心装饰相关属性 -->
<attr name="heartIcon" format="reference" />
<attr name="heartCount" format="integer" />
<attr name="heartSize" format="dimension" />
</declare-styleable>
<declare-styleable name="AvatarWithDecoration">
<attr name="decoration" format="reference" />
<attr name="decorationScale" format="float" />
<attr name="decorationOffsetX" format="integer" />
<attr name="decorationOffsetY" format="integer" />
</declare-styleable>
</resources>

View File

@@ -60,5 +60,7 @@ dependencies {
implementation (libs.arouter.api.v150)
//annotationProcessor
annotationProcessor libs.arouter.compiler
implementation libs.permissionx
}
apply plugin: 'com.alibaba.arouter' //

View File

@@ -1,6 +1,9 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- 前台定位权限 -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<!-- 后台定位权限Android 10+ -->
<uses-permission android:name="android.permission.ACCESS_BACKGROUND_LOCATION" />
<application
>

View File

@@ -1,5 +1,7 @@
package com.xscm.modulemain.activity;
import android.Manifest;
import android.app.Activity;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
@@ -16,9 +18,12 @@ import android.view.KeyEvent;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
import androidx.fragment.app.Fragment;
import com.alibaba.android.arouter.facade.annotation.Route;
@@ -32,6 +37,12 @@ import com.example.modulenews.fragment.NewsFragment;
import com.example.moduleroom.activity.RoomActivity;
import com.example.modulevocal.fragment.VocalRangeFragment;
import com.example.modulevoice.fragment.VoiceFragment;
import com.permissionx.guolindev.PermissionX;
import com.permissionx.guolindev.callback.ExplainReasonCallback;
import com.permissionx.guolindev.callback.ForwardToSettingsCallback;
import com.permissionx.guolindev.callback.RequestCallback;
import com.permissionx.guolindev.request.ExplainScope;
import com.permissionx.guolindev.request.ForwardScope;
import com.xscm.modulemain.R;
import com.xscm.modulemain.contacts.HomeContacts;
import com.xscm.modulemain.databinding.ActivityMainBinding;
@@ -56,6 +67,8 @@ import com.xscm.moduleutil.utils.BackgroundManager;
import com.xscm.moduleutil.utils.ColorManager;
import com.xscm.moduleutil.utils.ImageLoader;
import com.xscm.moduleutil.utils.SpUtil;
import com.xscm.moduleutil.utils.location.LocationProvider;
import com.xscm.moduleutil.utils.location.SystemLocationProvider;
import com.xscm.moduleutil.utils.logger.Logger;
import com.tencent.imsdk.v2.V2TIMManager;
import com.tencent.imsdk.v2.V2TIMValueCallback;
@@ -69,7 +82,8 @@ import java.util.List;
import java.util.Map;
@Route(path = ARouteConstants.ME)
public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBinding> implements HomeContacts.View, View.OnClickListener {
public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBinding>
implements HomeContacts.View, View.OnClickListener, LocationProvider.LocationCallback {
private static int index = -1;
public static boolean isShortsShowing() {
@@ -178,6 +192,7 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
});
}
@@ -262,6 +277,7 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
return super.onKeyDown(keyCode, event);
}
// 最推荐的方法
private void clearAllOtherTasksAndRestart() {
// Intent intent = new Intent(this, MainActivity.class);
@@ -278,6 +294,7 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
// 可选:如果上面的方法不够彻底,可以配合使用
Runtime.getRuntime().gc(); // 建议垃圾回收
}
/**
* 优雅地退出应用,避免闪屏
*/
@@ -366,7 +383,7 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
} else if (id == R.id.riv) {
String roomId = CommonAppContext.getInstance().playId;
if (!TextUtils.isEmpty(roomId)) {
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId,"");
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId, "");
// MvpPre.getRoomOnline(roomId, "1", "100");
// AppStateManager stateManager = AppStateManager.getInstance();
@@ -540,24 +557,63 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
MvpPre.getMyInfo(SpUtil.getUserId() + "");//获取首充是否需要展示
// mBinding.ivShouchl.setVisibility(View.VISIBLE);
// 请求GPS相关权限精确位置+可选的后台权限)
requestGpsPermissions();
}
private void requestGpsPermissions() {
PermissionX.init(this)
// 请求精确位置权限包含GPS定位能力
.permissions(
Manifest.permission.ACCESS_FINE_LOCATION,
// 如需后台使用GPS添加此权限Android 10+
Manifest.permission.ACCESS_BACKGROUND_LOCATION
).explainReasonBeforeRequest()
.onExplainRequestReason(new ExplainReasonCallback() {
@Override
public void onExplainReason(ExplainScope scope, List<String> deniedList) {
String message = "需要GPS权限以获取您的精确位置用于导航/定位功能";
// 若包含后台权限,补充说明
scope.showRequestReasonDialog(deniedList, message, "确定", "取消");
}
})
// 权限被永久拒绝时,引导至设置页面
.onForwardToSettings(new ForwardToSettingsCallback() {
@Override
public void onForwardToSettings(ForwardScope scope, List<String> deniedList) {
scope.showForwardToSettingsDialog(deniedList, "GPS权限被拒绝无法使用定位功能请去设置开启", "去设置", "取消");
}
})
// 权限请求结果回调
.request(new RequestCallback() {
@Override
public void onResult(boolean allGranted, List<String> grantedList, List<String> deniedList) {
if (allGranted) {
// Toast.makeText(MainActivity.this, "GPS权限已授予可开始定位", Toast.LENGTH_SHORT).show();
initLocation(); // 启动GPS定位逻辑
} else {
Toast.makeText(MainActivity.this, "GPS权限被拒绝无法使用定位功能", Toast.LENGTH_SHORT).show();
}
}
});
}
@Subscribe(threadMode = ThreadMode.MAIN)
public void onEvent(UnreadCountEvent event) {
long aLong = event.getALong();
long bLong = event.getBLong();
if (aLong==0 && bLong==0){
if (aLong == 0 && bLong == 0) {
mBinding.tvMessage.setVisibility(View.GONE);
}else {
} else {
mBinding.tvMessage.setVisibility(View.VISIBLE);
mBinding.tvMessage.setText(String.valueOf(event.getALong()+event.getBLong()));
mBinding.tvMessage.setText(String.valueOf(event.getALong() + event.getBLong()));
}
// if (event.getALong() == 0) {
@@ -619,6 +675,25 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
}
private String city1;
@Override
public void onLocationReceived(double latitude, double longitude, String city) {
LogUtils.e("当前位置:" + city);
city1 = city;
EventBus.getDefault().post(city1);
LogUtils.e("@@@1", "开始定位", "描述:", "当前位置" + city);
}
@Override
public void onFailed(String errorMessage) {
LogUtils.e("@@@1", "开始定位", "描述:", "失败");
}
public static int getCurrentVersionCode(Context context) {
try {
PackageInfo packageInfo = context.getPackageManager().getPackageInfo(context.getPackageName(), 0);
@@ -737,13 +812,13 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
}
if (!isPlaying){
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId,"");
if (!isPlaying) {
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId, "");
// ARouter.getInstance().build(ARouteConstants.ROOM_DETAILS).addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP).withString("form", "首页").withString("roomId", CommonAppContext.getInstance().playId).navigation();
}else {
} else {
// ARouter.getInstance().build(ARouteConstants.ROOM_DETAILS).withString("form", "首页").withString("roomId", CommonAppContext.getInstance().playId).navigation();
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId,"");
RoomManager.getInstance().fetchRoomDataAndEnter(this, CommonAppContext.getInstance().playId, "");
}
}
@@ -840,9 +915,35 @@ public class MainActivity extends BaseMvpActivity<HomePresenter, ActivityMainBin
}
// @Override
// @Override
// protected void onPause() {
// super.onPause();
// moveTaskToBack(true);
// }
private SystemLocationProvider locationProvider;
private void initLocation() {
// 在Activity或Fragment中调用
locationProvider = new SystemLocationProvider();
// 请求一次性的位置信息
locationProvider.getLastKnownLocation(this, this);
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if (requestCode == 1001) {
if (locationProvider == null) {
locationProvider = new SystemLocationProvider();
}
locationProvider.getLastKnownLocation(this, this);
}
}
}

View File

@@ -0,0 +1,258 @@
//package com.example.moduleroom.view;
//import android.content.Context;
//import android.graphics.drawable.Drawable;
//import android.util.AttributeSet;
//import android.view.View;
//import android.view.animation.Animation;
//import android.view.animation.RotateAnimation;
//import android.widget.Button;
//import android.widget.ImageView;
//import android.widget.LinearLayout;
//import android.widget.RelativeLayout;
//import android.widget.TextView;
//
//import androidx.annotation.Nullable;
//
//import com.example.moduleroom.R;
//
//public class QXMeetGiftView extends RelativeLayout {
//
// private TextView giftNameLabel;
// private ImageView giftPriceBgView;
// private Button giftCoin;
// private ImageView bgImageView;
// private ImageView giftBgImageView;
// private ImageView giftImageView;
//
// private boolean isLockGift;
// private Object model; // 这里用 Object 代替 QXDrawGiftModel
//
// public QXMeetGiftView(Context context) {
// super(context);
// initSubviews(context);
// }
//
// public QXMeetGiftView(Context context, @Nullable AttributeSet attrs) {
// super(context, attrs);
// initSubviews(context);
// }
//
// public QXMeetGiftView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
// super(context, attrs, defStyleAttr);
// initSubviews(context);
// }
//
// private void initSubviews(Context context) {
// // 创建背景图片视图
// bgImageView = new ImageView(context);
// bgImageView.setScaleType(ImageView.ScaleType.FIT_XY);
// bgImageView.setImageResource(R.drawable.ac_left_gift_bg);
// LayoutParams bgParams = new LayoutParams(
// LayoutParams.MATCH_PARENT,
// LayoutParams.MATCH_PARENT
// );
// bgParams.addRule(ALIGN_PARENT_TOP);
// bgParams.addRule(ALIGN_PARENT_LEFT);
// bgParams.addRule(ALIGN_PARENT_RIGHT);
// bgParams.bottomMargin = dpToPx(19); // 底部偏移-19
// addView(bgImageView, bgParams);
//
// // 创建礼物背景光效视图
// giftBgImageView = new ImageView(context);
// giftBgImageView.setScaleType(ImageView.ScaleType.FIT_XY);
// giftBgImageView.setImageResource(R.drawable.ac_lock_gift_light_bg);
// giftBgImageView.setVisibility(View.GONE); // 初始隐藏
// LayoutParams giftBgParams = new LayoutParams(
// LayoutParams.MATCH_PARENT,
// LayoutParams.MATCH_PARENT
// );
// giftBgParams.addRule(ALIGN_PARENT_TOP);
// giftBgParams.addRule(ALIGN_PARENT_LEFT);
// giftBgParams.addRule(ALIGN_PARENT_RIGHT);
// giftBgParams.bottomMargin = dpToPx(19);
// addView(giftBgImageView, giftBgParams);
//
// // 创建礼物图片视图
// giftImageView = new ImageView(context);
// giftImageView.setScaleType(ImageView.ScaleType.FIT_CENTER);
// LayoutParams giftImageParams = new LayoutParams(
// LayoutParams.MATCH_PARENT,
// LayoutParams.WRAP_CONTENT
// );
// giftImageParams.addRule(CENTER_IN_PARENT);
// giftImageParams.setMargins(dpToPx(6), dpToPx(6), dpToPx(6), 0);
// addView(giftImageView, giftImageParams);
//
// // 创建价格背景视图
// giftPriceBgView = new ImageView(context);
// giftPriceBgView.setImageResource(R.drawable.ac_meet_gift_name_bg);
// LayoutParams priceBgParams = new LayoutParams(
// LayoutParams.MATCH_PARENT,
// dpToPx(15)
// );
// priceBgParams.addRule(ALIGN_PARENT_BOTTOM);
// priceBgParams.bottomMargin = dpToPx(15); // 在名称标签上方
// addView(giftPriceBgView, priceBgParams);
//
// // 创建金币按钮
// giftCoin = new Button(context);
// giftCoin.setTextColor(0xFFC7BF62);
// // 设置按钮图标
// Drawable coinDrawable = getResources().getDrawable(R.drawable.sky_item_coin);
// coinDrawable.setBounds(0, 0, dpToPx(12), dpToPx(12));
// giftCoin.setCompoundDrawables(coinDrawable, null, null, null);
// giftCoin.setTextSize(10);
// giftCoin.setBackgroundColor(0x00000000); // 透明背景
// LayoutParams coinParams = new LayoutParams(
// LayoutParams.WRAP_CONTENT,
// LayoutParams.WRAP_CONTENT
// );
// coinParams.addRule(CENTER_IN_PARENT, TRUE);
// addView(giftCoin, coinParams);
//
// // 创建礼物名称标签
// giftNameLabel = new TextView(context);
// giftNameLabel.setTextColor(0xFFFFFFFF);
// giftNameLabel.setTextSize(12);
// giftNameLabel.setGravity(android.view.Gravity.CENTER);
// LayoutParams nameParams = new LayoutParams(
// LayoutParams.MATCH_PARENT,
// dpToPx(15)
// );
// nameParams.addRule(ALIGN_PARENT_BOTTOM);
// addView(giftNameLabel, nameParams);
//
// // 调整视图层级
// bringChildToFront(giftPriceBgView);
// bringChildToFront(giftCoin);
// }
//
// public void setIsLockGift(boolean isLockGift) {
// this.isLockGift = isLockGift;
//
// // 设置背景图片
// int bgResource = isLockGift ?
// R.drawable.ac_lock_gift_bg : R.drawable.ac_meet_gift_name_bg;
// bgImageView.setImageResource(bgResource);
//
// // 显示/隐藏光效背景
// giftBgImageView.setVisibility(isLockGift ? View.VISIBLE : View.GONE);
//
// if (isLockGift) {
// // 重新设置礼物图片的约束
// LayoutParams params = (LayoutParams) giftImageView.getLayoutParams();
// params.width = scaleWidth(62);
// params.height = scaleWidth(62);
// params.addRule(CENTER_IN_PARENT);
// params.setMargins(0, 0, 0, 0);
// giftImageView.setLayoutParams(params);
// } else {
// // 恢复原始约束
// LayoutParams params = (LayoutParams) giftImageView.getLayoutParams();
// params.width = LayoutParams.MATCH_PARENT;
// params.height = LayoutParams.WRAP_CONTENT;
// params.addRule(CENTER_IN_PARENT);
// params.setMargins(dpToPx(6), dpToPx(6), dpToPx(6), 0);
// giftImageView.setLayoutParams(params);
// }
// }
//
// public void setModel(Object model) {
// this.model = model;
// // 这里需要根据您的 QXDrawGiftModel 类来实现具体逻辑
// /*
// if (model instanceof QXDrawGiftModel) {
// QXDrawGiftModel giftModel = (QXDrawGiftModel) model;
//
// // 使用图片加载库加载图片
// // Glide.with(getContext()).load(giftModel.getBaseImage()).into(giftImageView);
//
// giftNameLabel.setText(giftModel.getGiftName());
// giftCoin.setText(giftModel.getGiftPrice());
// }
// */
// }
//
// public void startAnimation() {
// // 礼物图片顺时针旋转动画
// RotateAnimation rotateAnimation = new RotateAnimation(
// 0, 360, // 从 0 度旋转到 360 度
// Animation.RELATIVE_TO_SELF, 0.5f,
// Animation.RELATIVE_TO_SELF, 0.5f
// );
// rotateAnimation.setDuration(3000); // 3 秒
// rotateAnimation.setRepeatCount(Animation.INFINITE);
// rotateAnimation.setRepeatMode(Animation.RESTART);
// rotateAnimation.setInterpolator(getContext(), android.R.anim.linear_interpolator);
// giftImageView.startAnimation(rotateAnimation);
//
// // 光效背景逆时针旋转动画
// RotateAnimation rotateAnimation1 = new RotateAnimation(
// 0, -360, // 从 0 度旋转到 -360 度
// Animation.RELATIVE_TO_SELF, 0.5f,
// Animation.RELATIVE_TO_SELF, 0.5f
// );
// rotateAnimation1.setDuration(3000); // 3 秒
// rotateAnimation1.setRepeatCount(Animation.INFINITE);
// rotateAnimation1.setRepeatMode(Animation.RESTART);
// rotateAnimation1.setInterpolator(getContext(), android.R.anim.linear_interpolator);
// giftBgImageView.startAnimation(rotateAnimation1);
// }
//
// public void resetAnimation() {
// giftImageView.clearAnimation();
// giftBgImageView.clearAnimation();
// }
//
// public void stopAnimation() {
// giftImageView.clearAnimation();
// giftBgImageView.clearAnimation();
// }
//
// // 辅助方法dp 转 px
// private int dpToPx(int dp) {
// float density = getResources().getDisplayMetrics().density;
// return Math.round(dp * density);
// }
//
// // 缩放宽度方法(对应 ScaleWidth
// private int scaleWidth(int value) {
// // 这里需要根据您的缩放逻辑实现
// // 通常可以根据屏幕密度进行缩放
// float scale = getResources().getDisplayMetrics().density;
// return (int) (value * scale);
// }
//
// // Getter 方法
// public TextView getGiftNameLabel() {
// return giftNameLabel;
// }
//
// public ImageView getGiftPriceBgView() {
// return giftPriceBgView;
// }
//
// public Button getGiftCoin() {
// return giftCoin;
// }
//
// public ImageView getBgImageView() {
// return bgImageView;
// }
//
// public ImageView getGiftBgImageView() {
// return giftBgImageView;
// }
//
// public ImageView getGiftImageView() {
// return giftImageView;
// }
//
// public boolean isLockGift() {
// return isLockGift;
// }
//
// public Object getModel() {
// return model;
// }
//}

View File

@@ -482,7 +482,7 @@
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
tools:visibility="visible" />
<!--https://tmd.xscmmidi.site/data/avatar/head_pic.png-->
<com.xscm.moduleutil.widget.DropViewRoom
android:id="@+id/xlh_rk"
android:layout_width="wrap_content"
@@ -520,7 +520,6 @@
</com.xscm.moduleutil.widget.DropViewRoom>
<com.xscm.moduleutil.widget.floatingView.Floa
android:id="@+id/flaoat"
android:layout_width="@dimen/dp_240"

View File

@@ -0,0 +1,25 @@
package com.example.modulevoice.view;
import android.content.Context;
import android.util.AttributeSet;
import android.widget.TextView;
public class MarqueeTextView extends androidx.appcompat.widget.AppCompatTextView {
public MarqueeTextView(Context context) {
super(context);
}
public MarqueeTextView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public MarqueeTextView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
// 始终返回true确保能获取焦点
@Override
public boolean isFocused() {
return true;
}
}

View File

@@ -58,7 +58,6 @@
android:marqueeRepeatLimit="marquee_forever"
android:scrollHorizontally="true"
android:singleLine="true"
app:layout_constraintBottom_toBottomOf="@+id/view_num_bg"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/view_num_bg"