From 08a196e60ed714263d5283f3c0579bb2dcf56e02 Mon Sep 17 00:00:00 2001 From: lmw <125975490@qq.com> Date: 星期一, 03 三月 2025 17:44:26 +0800 Subject: [PATCH] save --- app/src/main/res/layout/item_banner.xml | 2 app/src/main/java/com/sinata/xqmuse/ThinkAudioService.kt | 89 ++++++++++++++++++++++ app/src/main/java/com/sinata/xqmuse/ui/home/VoiceDetailActivity.kt | 1 app/src/main/java/com/sinata/xqmuse/ui/home/adapter/CardBannerAdapter.kt | 2 app/src/main/res/layout/item_banner_card.xml | 6 app/src/main/res/layout/activity_guide.xml | 2 app/src/main/res/layout/fragment_home.xml | 4 app/src/main/java/com/sinata/xqmuse/MainActivity.kt | 78 ++++++++++--------- app/src/main/java/com/sinata/xqmuse/network/Apis.kt | 2 9 files changed, 140 insertions(+), 46 deletions(-) diff --git a/app/src/main/java/com/sinata/xqmuse/MainActivity.kt b/app/src/main/java/com/sinata/xqmuse/MainActivity.kt index 2890343..c2fb678 100644 --- a/app/src/main/java/com/sinata/xqmuse/MainActivity.kt +++ b/app/src/main/java/com/sinata/xqmuse/MainActivity.kt @@ -8,6 +8,7 @@ import android.provider.Settings import android.util.Log import android.view.View +import android.view.WindowManager import androidx.fragment.app.Fragment import androidx.fragment.app.FragmentPagerAdapter import cn.sinata.xldutils.gone @@ -57,7 +58,7 @@ private var thinkHandler:Handler? = null //冥想时间相关 private var inGuide = false //true 引导中... - private val isFirst by lazy { intent.getBooleanExtra("isFirst",false) } //首次安装,需要到导师引导页 + private val isFirst by lazy { intent.getBooleanExtra("isFirst", false) } //首次安装,需要到导师引导页 private val MSG_PROGRESS = 0//疗愈进度+1 private val MSG_TODAY = 1//今日疗愈更新计时 @@ -72,14 +73,14 @@ override fun initClick() { player_close.setOnClickListener { - TipDialog.show(supportFragmentManager,"是否关闭当前音频?",object :TipDialog.OnClickCallback{ + TipDialog.show(supportFragmentManager, "是否关闭当前音频?", object : TipDialog.OnClickCallback { override fun onOk() { EventBus.getDefault().post(EmptyEvent(Const.EventCode.FINISH_THINK)) } override fun onCancel() { } - },"确认","取消") + }, "确认", "取消") } cl_player.setOnClickListener { @@ -121,24 +122,24 @@ override fun handleMessage(msg: Message) { super.handleMessage(msg) when(msg.what){ - MSG_PROGRESS->{ - currentPosition = thinkBgPlayer?.currentPosition ?:0 + MSG_PROGRESS -> { + currentPosition = thinkBgPlayer?.currentPosition ?: 0 EventBus.getDefault().post(EmptyEvent(Const.EventCode.GOT_THINK_POSITION)) - sendEmptyMessageDelayed(MSG_PROGRESS,1000) + sendEmptyMessageDelayed(MSG_PROGRESS, 1000) } - MSG_COUNTDOWN->{ - if (System.currentTimeMillis()>= finishTime) + MSG_COUNTDOWN -> { + if (System.currentTimeMillis() >= finishTime) EventBus.getDefault().post(EmptyEvent(Const.EventCode.FINISH_THINK)) else - sendEmptyMessageDelayed(MSG_COUNTDOWN,1000) + sendEmptyMessageDelayed(MSG_COUNTDOWN, 1000) } - MSG_TODAY->{ + MSG_TODAY -> { if (System.currentTimeMillis() - lastTodayTime > 60000) { //距离上次刷新过去了1分钟 - Log.e(Const.Tag,"已经过1分钟,需要重新获取今日疗愈数据") + Log.e(Const.Tag, "已经过1分钟,需要重新获取今日疗愈数据") lastTodayTime = System.currentTimeMillis() (fragments[0] as HomeFragment).getToday() } - sendEmptyMessageDelayed(MSG_TODAY,5000) + sendEmptyMessageDelayed(MSG_TODAY, 5000) } } } @@ -151,29 +152,29 @@ if (guidePlayer == null) guidePlayer = AudioUtils() if (guideAudio.isNullOrEmpty()) - HttpManager.getPlan().request(this){_,data-> + HttpManager.getPlan().request(this){ _, data-> guideAudio = data if (inGuide){ guidePlayer?.setVolume(0.6f) - guidePlayer?.loopPlayMusic(this,data) + guidePlayer?.loopPlayMusic(this, data) } } else{ guidePlayer?.setVolume(0.6f) - guidePlayer?.loopPlayMusic(this,guideAudio) + guidePlayer?.loopPlayMusic(this, guideAudio) } } private fun startBgm() { - HttpManager.getHomeBackgroundMusicByUserId().request(this){_,data-> + HttpManager.getHomeBackgroundMusicByUserId().request(this){ _, data-> if (!data?.audioFile.isNullOrEmpty()){ if (bgPlayer == null) bgPlayer = AudioUtils() - val volume = SPUtils.instance().getInt(Const.User.VOLUME,50) - bgPlayer?.setVolume(volume.toFloat()/100) - bgPlayer?.loopPlayMusic(this,data?.audioFile) + val volume = SPUtils.instance().getInt(Const.User.VOLUME, 50) + bgPlayer?.setVolume(volume.toFloat() / 100) + bgPlayer?.loopPlayMusic(this, data?.audioFile) } - (fragments[0] as HomeFragment).changeBg(data?.imageUrl?:"",data?.backUrl?:"") + (fragments[0] as HomeFragment).changeBg(data?.imageUrl ?: "", data?.backUrl ?: "") } } @@ -188,8 +189,8 @@ thinkBgPlayer = AudioUtils() thinkBgPlayer!!.setOnAudioStatusUpdateListener(this) } - val volume = SPUtils.instance().getInt(Const.User.VOLUME_THINK,50) - thinkBgPlayer?.setVolume(volume.toFloat()/100) + val volume = SPUtils.instance().getInt(Const.User.VOLUME_THINK, 50) + thinkBgPlayer?.setVolume(volume.toFloat() / 100) thinkBgPlayer?.startPlayMusic(this, voice?.meditationMusicList?.get(index)) currentDuration = voice?.meditationSecondList?.get(index)?:0 EventBus.getDefault().post(EmptyEvent(Const.EventCode.GOT_THINK_DURATION)) @@ -233,10 +234,10 @@ return val time = ((System.currentTimeMillis() - startTime) / 1000).toInt() startTime = 0L - HttpManager.saveViewingHistory(voice?.id?:"", time).request(this,false,{ _, _-> - Log.e(Const.Tag,"冥想记录成功:$time 秒") - }){_,_-> - Log.e(Const.Tag,"冥想记录失败:$time 秒") + HttpManager.saveViewingHistory(voice?.id ?: "", time).request(this, false, { _, _ -> + Log.e(Const.Tag, "冥想记录成功:$time 秒") + }){ _, _-> + Log.e(Const.Tag, "冥想记录失败:$time 秒") } } @@ -248,7 +249,7 @@ } private fun initTab() { - val titles = arrayListOf("疗愈","课程","","疗愈馆","我的") + val titles = arrayListOf("疗愈", "课程", "", "疗愈馆", "我的") val iconChecked = arrayListOf( R.mipmap.home_selected, R.mipmap.play_selected, @@ -269,7 +270,7 @@ fragments.add(DiscoveryFragment()) fragments.add(MineFragment()) view_pager.offscreenPageLimit = fragments.size - view_pager.adapter = object : FragmentPagerAdapter(supportFragmentManager,0) { + view_pager.adapter = object : FragmentPagerAdapter(supportFragmentManager, 0) { override fun getItem(p0: Int): Fragment { return fragments[p0] } @@ -327,7 +328,7 @@ } @Subscribe - fun onEvent(e:EmptyEvent){ + fun onEvent(e: EmptyEvent){ if (e.code == Const.EventCode.CHANGE_USER){ tab_bar.currentTab = 0 onTabSelect(0) @@ -359,8 +360,8 @@ }else if(e.code == Const.EventCode.PAUSE_OR_RESUME_THINK){ player_play.callOnClick() }else if(e.code == Const.EventCode.CHANGE_THINK_VOLUME){ - val v = SPUtils.instance().getInt(Const.User.VOLUME_THINK,50) - thinkBgPlayer?.setVolume(v.toFloat()/100) + val v = SPUtils.instance().getInt(Const.User.VOLUME_THINK, 50) + thinkBgPlayer?.setVolume(v.toFloat() / 100) }else if(e.code == Const.EventCode.START_GUIDE_AUDIO){ inGuide = true startGuide() @@ -382,7 +383,7 @@ } @Subscribe - fun onIntEvent(e:IntEvent){ + fun onIntEvent(e: IntEvent){ if (e.code == Const.EventCode.THINK_SEEK_PROGRESS){ thinkBgPlayer?.seekTo(e.i) player_play.callOnClick() @@ -394,12 +395,15 @@ val answer = SPUtils.instance().getString(Const.User.ANSWER) if (!answer.isNullOrEmpty()){ //已登录并且有答案 val reqAnswer = Gson().fromJson(answer, ReqAnswer::class.java) - reqAnswer?.device = Settings.Secure.getString(contentResolver, Settings.Secure.ANDROID_ID) - HttpManager.saveUserAnswers(reqAnswer).request(this,false,success = { _, _-> - SPUtils.instance().put(Const.User.ANSWER,"").apply() - Log.e(Const.Tag,"私人定制已保存") + reqAnswer?.device = Settings.Secure.getString( + contentResolver, + Settings.Secure.ANDROID_ID + ) + HttpManager.saveUserAnswers(reqAnswer).request(this, false, success = { _, _ -> + SPUtils.instance().put(Const.User.ANSWER, "").apply() + Log.e(Const.Tag, "私人定制已保存") (fragments[0] as HomeFragment).getPrivacy() - }){_,_-> + }){ _, _-> } } } diff --git a/app/src/main/java/com/sinata/xqmuse/ThinkAudioService.kt b/app/src/main/java/com/sinata/xqmuse/ThinkAudioService.kt new file mode 100644 index 0000000..a6d8f87 --- /dev/null +++ b/app/src/main/java/com/sinata/xqmuse/ThinkAudioService.kt @@ -0,0 +1,89 @@ +package com.sinata.xqmuse + +import android.app.NotificationChannel +import android.app.NotificationManager +import android.app.Service +import android.content.Intent +import android.media.AudioManager +import android.media.MediaPlayer +import android.os.Build +import android.os.IBinder +import android.os.PowerManager +import androidx.core.app.NotificationCompat + +class ThinkAudioService:Service() { + private var mediaPlayer: MediaPlayer? = null + private var wakeLock: PowerManager.WakeLock? = null + + override fun onCreate() { + super.onCreate() + // 初始化 MediaPlayer +// mediaPlayer = MediaPlayer.create(this, R.raw.audio_sample) + mediaPlayer!!.isLooping = true + + // 初始化 WakeLock + val powerManager = getSystemService(POWER_SERVICE) as PowerManager + wakeLock = powerManager.newWakeLock( + PowerManager.PARTIAL_WAKE_LOCK, + "AudioService::WakeLock" + ) + } + + private val focusChangeListener = + AudioManager.OnAudioFocusChangeListener { focusChange -> + if (focusChange == AudioManager.AUDIOFOCUS_LOSS) { + mediaPlayer!!.pause() // 焦点丢失时暂停播放 + } + } + + private fun createNotificationChannel() { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { + val channel = NotificationChannel( + "audio_channel", + "音频播放", + NotificationManager.IMPORTANCE_LOW + ) + getSystemService(NotificationManager::class.java).createNotificationChannel(channel) + } + } + + override fun onBind(intent: Intent?): IBinder? { + return null + } + + override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int { + // 创建通知渠道(Android 8.0+ 必须) + createNotificationChannel() + + // 启动前台服务 + val notification = NotificationCompat.Builder(this, "audio_channel") + .setContentTitle("音频播放中") + .setSmallIcon(R.mipmap.ic_launcher) + .build() + startForeground(1, notification) + + // 请求音频焦点 + val audioManager = getSystemService(AUDIO_SERVICE) as AudioManager + val result = audioManager.requestAudioFocus( + focusChangeListener, + AudioManager.STREAM_MUSIC, + AudioManager.AUDIOFOCUS_GAIN + ) + if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) { + mediaPlayer?.start() + wakeLock?.acquire(30 * 60 * 1000L) // 申请 WakeLock + } + return START_STICKY + } + + override fun onDestroy() { + if (mediaPlayer != null) { + mediaPlayer!!.release() + mediaPlayer = null + } + if (wakeLock != null && wakeLock!!.isHeld) { + wakeLock!!.release() + } + super.onDestroy() + } +} \ No newline at end of file diff --git a/app/src/main/java/com/sinata/xqmuse/network/Apis.kt b/app/src/main/java/com/sinata/xqmuse/network/Apis.kt index 0f34416..961345f 100644 --- a/app/src/main/java/com/sinata/xqmuse/network/Apis.kt +++ b/app/src/main/java/com/sinata/xqmuse/network/Apis.kt @@ -5,7 +5,7 @@ // private const val TEST_URL = "http://192.168.110.64:9000/" //内网 private const val TEST_URL = "https://xq.xqzhihui.com/api/" //外网 - private const val LINE_URL = "https://jkcyl.cn/app/" //正式服 + private const val LINE_URL = "" //正式服 val BASE_URL = if (isTest) TEST_URL else LINE_URL /**公共接口*/ diff --git a/app/src/main/java/com/sinata/xqmuse/ui/home/VoiceDetailActivity.kt b/app/src/main/java/com/sinata/xqmuse/ui/home/VoiceDetailActivity.kt index 1b55c56..a08bc83 100644 --- a/app/src/main/java/com/sinata/xqmuse/ui/home/VoiceDetailActivity.kt +++ b/app/src/main/java/com/sinata/xqmuse/ui/home/VoiceDetailActivity.kt @@ -150,6 +150,7 @@ } } EventBus.getDefault().register(this) + iv_play.keepScreenOn = true } private fun startTimer(){ diff --git a/app/src/main/java/com/sinata/xqmuse/ui/home/adapter/CardBannerAdapter.kt b/app/src/main/java/com/sinata/xqmuse/ui/home/adapter/CardBannerAdapter.kt index ae4cb28..0a951fb 100644 --- a/app/src/main/java/com/sinata/xqmuse/ui/home/adapter/CardBannerAdapter.kt +++ b/app/src/main/java/com/sinata/xqmuse/ui/home/adapter/CardBannerAdapter.kt @@ -34,7 +34,7 @@ val bannerViewHolder = holder as BannerViewHolder bannerViewHolder.iv_bg.setImageURI(data?.coverUrl?.split(",")?.get(1)) bannerViewHolder.tv_title.text = data?.meditationTitle - bannerViewHolder.tv_subtitle.text = data?.coverDescription?.ellipsize(6) + bannerViewHolder.tv_subtitle.text = data?.coverDescription?.ellipsize(4) bannerViewHolder.tv_count.text = ((data?.realLearnedNum?:0)+(data?.virtualLearnedNum?:0)).toString() when(data?.chargeType){ //1=免费 2=会员免费 3=单独收费 2->{ diff --git a/app/src/main/res/layout/activity_guide.xml b/app/src/main/res/layout/activity_guide.xml index 8bcf343..324aef3 100644 --- a/app/src/main/res/layout/activity_guide.xml +++ b/app/src/main/res/layout/activity_guide.xml @@ -8,7 +8,7 @@ android:layout_width="match_parent" android:layout_height="match_parent" app:screenScaleType="type_center_crop" - app:playerBackgroundColor="@color/colorPrimary" + app:playerBackgroundColor="@color/white" android:id="@+id/player"/> <TextView diff --git a/app/src/main/res/layout/fragment_home.xml b/app/src/main/res/layout/fragment_home.xml index c00013c..a26cf61 100644 --- a/app/src/main/res/layout/fragment_home.xml +++ b/app/src/main/res/layout/fragment_home.xml @@ -126,7 +126,7 @@ android:layout_height="wrap_content" app:layout_constraintBottom_toBottomOf="@id/iv_today" android:paddingVertical="8dp" - android:textSize="11sp" + android:textSize="14sp" android:textColor="@color/white" android:gravity="end" android:id="@+id/tv_today_count" @@ -141,7 +141,7 @@ app:layout_constraintBaseline_toBaselineOf="@id/tv_today_count" app:layout_constraintStart_toStartOf="parent" android:layout_marginStart="18dp" - android:textSize="11sp" + android:textSize="14sp" android:textColor="@color/white" /> diff --git a/app/src/main/res/layout/item_banner.xml b/app/src/main/res/layout/item_banner.xml index fbfd655..ee31397 100644 --- a/app/src/main/res/layout/item_banner.xml +++ b/app/src/main/res/layout/item_banner.xml @@ -45,6 +45,6 @@ android:layout_marginBottom="16dp" app:layout_constraintStart_toStartOf="@id/tv_name" android:textColor="@color/white" - android:textSize="10sp" + android:textSize="14sp" android:textStyle="bold"/> </androidx.constraintlayout.widget.ConstraintLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/item_banner_card.xml b/app/src/main/res/layout/item_banner_card.xml index 043899c..33de3e3 100644 --- a/app/src/main/res/layout/item_banner_card.xml +++ b/app/src/main/res/layout/item_banner_card.xml @@ -34,7 +34,7 @@ android:text="缓解压力" android:singleLine="true" android:ellipsize="end" - android:textSize="14sp" + android:textSize="16sp" android:textColor="@color/white" android:id="@+id/tv_title"/> <TextView @@ -46,7 +46,7 @@ app:layout_constraintBottom_toBottomOf="parent" android:layout_marginBottom="11dp" android:text="缓解压力" - android:textSize="9sp" + android:textSize="11sp" android:textColor="@color/white" android:id="@+id/tv_subtitle"/> <ImageView @@ -63,7 +63,7 @@ android:layout_height="wrap_content" android:id="@+id/tv_count" android:textColor="@color/white" - android:textSize="9sp" + android:textSize="11sp" app:layout_constraintStart_toEndOf="@id/iv" app:layout_constraintBaseline_toBaselineOf="@id/tv_subtitle" android:layout_marginStart="2dp" -- Gitblit v1.7.1