feat: 扩展前端WebSocket与导航
- 优化WebSocketClient、WebSocketMessage - 更新AppNavigation、MainActivity Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -25,7 +25,6 @@ import androidx.compose.foundation.layout.size
|
|||||||
import androidx.compose.foundation.layout.statusBars
|
import androidx.compose.foundation.layout.statusBars
|
||||||
import androidx.compose.foundation.layout.windowInsetsPadding
|
import androidx.compose.foundation.layout.windowInsetsPadding
|
||||||
import androidx.compose.foundation.shape.RoundedCornerShape
|
import androidx.compose.foundation.shape.RoundedCornerShape
|
||||||
import androidx.compose.ui.draw.scale
|
|
||||||
import androidx.compose.material3.Icon
|
import androidx.compose.material3.Icon
|
||||||
import androidx.compose.material3.MaterialTheme
|
import androidx.compose.material3.MaterialTheme
|
||||||
import androidx.compose.material3.Scaffold
|
import androidx.compose.material3.Scaffold
|
||||||
@@ -39,18 +38,18 @@ import androidx.compose.runtime.saveable.rememberSaveable
|
|||||||
import androidx.compose.runtime.setValue
|
import androidx.compose.runtime.setValue
|
||||||
import androidx.compose.ui.Alignment
|
import androidx.compose.ui.Alignment
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
|
import androidx.compose.ui.draw.scale
|
||||||
import androidx.compose.ui.graphics.vector.ImageVector
|
import androidx.compose.ui.graphics.vector.ImageVector
|
||||||
|
import androidx.compose.ui.platform.LocalContext
|
||||||
import androidx.compose.ui.text.font.FontWeight
|
import androidx.compose.ui.text.font.FontWeight
|
||||||
import androidx.compose.ui.tooling.preview.Preview
|
|
||||||
import androidx.compose.ui.tooling.preview.PreviewScreenSizes
|
import androidx.compose.ui.tooling.preview.PreviewScreenSizes
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import androidx.compose.ui.unit.sp
|
import androidx.compose.ui.unit.sp
|
||||||
import androidx.core.view.WindowCompat
|
import androidx.core.view.WindowCompat
|
||||||
import androidx.core.view.WindowInsetsControllerCompat
|
|
||||||
import androidx.core.view.WindowInsetsCompat
|
import androidx.core.view.WindowInsetsCompat
|
||||||
|
import androidx.core.view.WindowInsetsControllerCompat
|
||||||
import androidx.navigation.compose.currentBackStackEntryAsState
|
import androidx.navigation.compose.currentBackStackEntryAsState
|
||||||
import androidx.navigation.compose.rememberNavController
|
import androidx.navigation.compose.rememberNavController
|
||||||
import androidx.compose.ui.platform.LocalContext
|
|
||||||
import com.huaga.life_echo.data.auth.TokenManager
|
import com.huaga.life_echo.data.auth.TokenManager
|
||||||
import com.huaga.life_echo.navigation.AppNavigation
|
import com.huaga.life_echo.navigation.AppNavigation
|
||||||
import com.huaga.life_echo.navigation.Screen
|
import com.huaga.life_echo.navigation.Screen
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ sealed class Screen(val route: String) {
|
|||||||
object MyOrders : Screen("my_orders")
|
object MyOrders : Screen("my_orders")
|
||||||
object ExportData : Screen("export_data")
|
object ExportData : Screen("export_data")
|
||||||
object PlanDetails : Screen("plan_details")
|
object PlanDetails : Screen("plan_details")
|
||||||
|
object PlanBalance : Screen("plan_balance") // 套餐余额
|
||||||
object FAQ : Screen("faq")
|
object FAQ : Screen("faq")
|
||||||
object Feedback : Screen("feedback")
|
object Feedback : Screen("feedback")
|
||||||
object About : Screen("about")
|
object About : Screen("about")
|
||||||
@@ -134,6 +135,15 @@ fun AppNavigation(
|
|||||||
) {
|
) {
|
||||||
PlanDetailsScreen(navController = navController)
|
PlanDetailsScreen(navController = navController)
|
||||||
}
|
}
|
||||||
|
composable(
|
||||||
|
route = Screen.PlanBalance.route,
|
||||||
|
enterTransition = { slideInHorizontally() },
|
||||||
|
exitTransition = { slideOutHorizontally() },
|
||||||
|
popEnterTransition = { slideInHorizontallyFromLeft() },
|
||||||
|
popExitTransition = { slideOutHorizontallyToRight() }
|
||||||
|
) {
|
||||||
|
PlanBalanceScreen(navController = navController)
|
||||||
|
}
|
||||||
composable(
|
composable(
|
||||||
route = Screen.FAQ.route,
|
route = Screen.FAQ.route,
|
||||||
enterTransition = { slideInHorizontally() },
|
enterTransition = { slideInHorizontally() },
|
||||||
|
|||||||
@@ -234,6 +234,20 @@ class WebSocketClient {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 仅转写:发送音频获取文字,不落库、不触发 Agent,用于「转文字」后客户端再发文本
|
||||||
|
*/
|
||||||
|
suspend fun sendTranscribeOnly(audioBytes: ByteArray, conversationId: String) {
|
||||||
|
Log.d(TAG, "发送仅转写请求,大小: ${audioBytes.size} 字节")
|
||||||
|
if (!isConnected) throw Exception("WebSocket未连接,请先建立连接")
|
||||||
|
val base64Audio = android.util.Base64.encodeToString(audioBytes, android.util.Base64.NO_WRAP)
|
||||||
|
sendMessage(WebSocketMessage(
|
||||||
|
type = MessageType.transcribe_only,
|
||||||
|
conversation_id = conversationId,
|
||||||
|
data = buildJsonObject { put("audio_base64", JsonPrimitive(base64Audio)) }
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
suspend fun sendTextMessage(text: String, conversationId: String) {
|
suspend fun sendTextMessage(text: String, conversationId: String) {
|
||||||
Log.d(TAG, "准备发送文本消息: $text")
|
Log.d(TAG, "准备发送文本消息: $text")
|
||||||
if (!isConnected) {
|
if (!isConnected) {
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ enum class MessageType {
|
|||||||
connect,
|
connect,
|
||||||
audio_chunk,
|
audio_chunk,
|
||||||
audio_message, // 完整音频消息(类似微信语音)
|
audio_message, // 完整音频消息(类似微信语音)
|
||||||
|
transcribe_only, // 仅转写,不落库不触发 Agent,用于「转文字」发送
|
||||||
text, // 文本消息
|
text, // 文本消息
|
||||||
transcript, // 语音转文字结果
|
transcript, // 语音转文字结果
|
||||||
agent_response,
|
agent_response,
|
||||||
|
|||||||
Reference in New Issue
Block a user