如何在 Jetpack 组合文本视图中显示 Firestore 集合文档中的文档字段
How can show a document field from a Firestore collection document in a jetpack compose text view
如果我违反了一些规则,或者之前已经有人问过,我感到非常抱歉。我花了很多时间来 google 示例,以及有关堆栈溢出和其他资源的问题。但我根本无法理解如何从 firestore 集合中获取文档字段,并在 Jetpack 撰写文本函数中显示字符串值。
我是编程初学者,Android。所以我确实对我应该怎么做有一些根本性的误解,但这是我的尝试,但没有用,我不明白为什么。
在 Firestore 中,我有一个名为 users 的集合,其中包含一个名为 holidaySavings 的文档,其中有一个名为 name 的字符串类型的字段。
我想在可组合的文本函数中显示名称的值。
我有一个名为 storedData 的 class 来处理 Firestore。它具有创建和更新集合/文档/字段的方法。行得通。
但我似乎无法将文档中的字段值读取到 Jetpack 可组合文本中。
我可以从文档字段中读取值,然后登录 Android studio。
这是我在 class 中处理 Firestore 数据库的功能
fun readDataTestFinal(): String{
val docRef = db.collection("users").document("holidaySavings")
var returnTest = ""
docRef.get()
.addOnSuccessListener { document ->
if (document != null) {
Log.d("Rtest", "DocumentSnapshot data: ${document.data}")
// I want to return this so I can use it in a composable text view
returnTest = document.get("name").toString()
} else {
Log.d("Rtest", "No such document")
}
}
.addOnFailureListener { exception ->
Log.d("Rfail", "get failed with ", exception)
}
return returnTest
}
在这里,我尝试将值读入 jetpack compose Text 函数。
var newStringFromStoredData by remember {
mutableStateOf(storedData().readDataTestFinal())
}
Text(
modifier = Modifier.background(color = Color.Blue),
text = newStringFromStoredData
)
当我 运行 应用程序时。一切都编译得很好,我从文档字段中得到了很好的值,并且可以在 Android Studio 的登录中看到它。
但是 Compose 函数在调用 Text 时没有在屏幕上显示值 newStringFromStoredData?
谁能告诉我我不明白的是什么,以及如何才能使用 firestore 文档字段并在 Jetpack Compose Text 函数中显示值?
Firebase 调用是异步的,这意味着它不会立即 return 数据。这就是 API 使用回调的原因。因此,您的函数 readDataTestFinal
始终是 return 一个空字符串。
您可以使用的一种解决方案是将您的函数转换为 suspend
函数并使用协程作用域调用它。例如:
suspend fun readDataTestFinal(): String {
val docRef = firestore.collection("users")
.document("holidaySavings")
return suspendCoroutine { continuation ->
docRef.get()
.addOnSuccessListener { document ->
if (document != null) {
continuation.resume(document.get("name").toString())
} else {
continuation.resume("No such document")
}
}
.addOnFailureListener { exception ->
continuation.resumeWithException(exception)
}
}
}
在上面的代码中,我们正在转换一个 。
在您的可组合项中,您可以执行以下操作:
var newStringFromStoredData by remember {
mutableStateOf("")
}
Text(newStringFromStoredData)
LaunchedEffect(newStringFromStoredData) {
newStringFromStoredData =
try { readDataTestFinal() } catch(e: Exception) { "Error!" }
}
LaunchedEffect
将启动您的暂停功能并在加载后立即更新结果。
更好的选择是在视图模型中定义此调用并从中调用此函数。但我认为这回答了你的问题,你可以稍后改进你的架构。您可以从 here.
开始
最方便、最快且显然是 best-in-your-case 补丁是使用所谓的 valueEventListeners
。
Firebase 为您提供了这些有用的方法,以便您可以将应用程序的数据 up-to-date 保存在 Firebase 服务器上。
val docRef = db.collection("cities").document("SF")
docRef.addSnapshotListener { snapshot, e -> // e is for error
// If error occurs
if (e != null) {
Log.w(TAG, "Listen failed.", e)
return@addSnapshotListener
}
// If backend value not received, use this to get current local stored value
val source = if (snapshot != null && snapshot.metadata.hasPendingWrites())
"Local"
else
"Server"
// If request was successful,
if (snapshot != null && snapshot.exists()) {
Log.d(TAG, "$source data: ${snapshot.data}")
//Update your text variable here
newStringFromStoredData = snapshot.data // Might need type-conversion
} else {
Log.d(TAG, "$source data: null")
}
}
这不仅可以解决您在问题中描述的问题,而且还可以确保只要服务器上的值为 changed/updated,您的文本就会随之更新。使用这些侦听器通常是一个很好的最佳实践,并且这些侦听器通常会转换为 LiveData
对象以遵守 'separation-of-concerns' 原则,但是您可以使用这个简单的实现来描述简单的 use-case .
另一件事,这通常会出现在 viewModel 中,因此,您也应该在 viewmodel 中声明文本变量。
在 init
块中尝试。
calss MVVM: ViewModel() {
init {
/* Paste Code From Above Here */
}
var newStringFromStoredData by mutableStateOf("")
}
然后在 Composable 中阅读它
Text(viewModel.newStringFromStoredData)
如果我违反了一些规则,或者之前已经有人问过,我感到非常抱歉。我花了很多时间来 google 示例,以及有关堆栈溢出和其他资源的问题。但我根本无法理解如何从 firestore 集合中获取文档字段,并在 Jetpack 撰写文本函数中显示字符串值。
我是编程初学者,Android。所以我确实对我应该怎么做有一些根本性的误解,但这是我的尝试,但没有用,我不明白为什么。
在 Firestore 中,我有一个名为 users 的集合,其中包含一个名为 holidaySavings 的文档,其中有一个名为 name 的字符串类型的字段。
我想在可组合的文本函数中显示名称的值。
我有一个名为 storedData 的 class 来处理 Firestore。它具有创建和更新集合/文档/字段的方法。行得通。
但我似乎无法将文档中的字段值读取到 Jetpack 可组合文本中。
我可以从文档字段中读取值,然后登录 Android studio。
这是我在 class 中处理 Firestore 数据库的功能
fun readDataTestFinal(): String{
val docRef = db.collection("users").document("holidaySavings")
var returnTest = ""
docRef.get()
.addOnSuccessListener { document ->
if (document != null) {
Log.d("Rtest", "DocumentSnapshot data: ${document.data}")
// I want to return this so I can use it in a composable text view
returnTest = document.get("name").toString()
} else {
Log.d("Rtest", "No such document")
}
}
.addOnFailureListener { exception ->
Log.d("Rfail", "get failed with ", exception)
}
return returnTest
}
在这里,我尝试将值读入 jetpack compose Text 函数。
var newStringFromStoredData by remember {
mutableStateOf(storedData().readDataTestFinal())
}
Text(
modifier = Modifier.background(color = Color.Blue),
text = newStringFromStoredData
)
当我 运行 应用程序时。一切都编译得很好,我从文档字段中得到了很好的值,并且可以在 Android Studio 的登录中看到它。
但是 Compose 函数在调用 Text 时没有在屏幕上显示值 newStringFromStoredData?
谁能告诉我我不明白的是什么,以及如何才能使用 firestore 文档字段并在 Jetpack Compose Text 函数中显示值?
Firebase 调用是异步的,这意味着它不会立即 return 数据。这就是 API 使用回调的原因。因此,您的函数 readDataTestFinal
始终是 return 一个空字符串。
您可以使用的一种解决方案是将您的函数转换为 suspend
函数并使用协程作用域调用它。例如:
suspend fun readDataTestFinal(): String {
val docRef = firestore.collection("users")
.document("holidaySavings")
return suspendCoroutine { continuation ->
docRef.get()
.addOnSuccessListener { document ->
if (document != null) {
continuation.resume(document.get("name").toString())
} else {
continuation.resume("No such document")
}
}
.addOnFailureListener { exception ->
continuation.resumeWithException(exception)
}
}
}
在上面的代码中,我们正在转换一个
在您的可组合项中,您可以执行以下操作:
var newStringFromStoredData by remember {
mutableStateOf("")
}
Text(newStringFromStoredData)
LaunchedEffect(newStringFromStoredData) {
newStringFromStoredData =
try { readDataTestFinal() } catch(e: Exception) { "Error!" }
}
LaunchedEffect
将启动您的暂停功能并在加载后立即更新结果。
更好的选择是在视图模型中定义此调用并从中调用此函数。但我认为这回答了你的问题,你可以稍后改进你的架构。您可以从 here.
开始最方便、最快且显然是 best-in-your-case 补丁是使用所谓的 valueEventListeners
。
Firebase 为您提供了这些有用的方法,以便您可以将应用程序的数据 up-to-date 保存在 Firebase 服务器上。
val docRef = db.collection("cities").document("SF")
docRef.addSnapshotListener { snapshot, e -> // e is for error
// If error occurs
if (e != null) {
Log.w(TAG, "Listen failed.", e)
return@addSnapshotListener
}
// If backend value not received, use this to get current local stored value
val source = if (snapshot != null && snapshot.metadata.hasPendingWrites())
"Local"
else
"Server"
// If request was successful,
if (snapshot != null && snapshot.exists()) {
Log.d(TAG, "$source data: ${snapshot.data}")
//Update your text variable here
newStringFromStoredData = snapshot.data // Might need type-conversion
} else {
Log.d(TAG, "$source data: null")
}
}
这不仅可以解决您在问题中描述的问题,而且还可以确保只要服务器上的值为 changed/updated,您的文本就会随之更新。使用这些侦听器通常是一个很好的最佳实践,并且这些侦听器通常会转换为 LiveData
对象以遵守 'separation-of-concerns' 原则,但是您可以使用这个简单的实现来描述简单的 use-case .
另一件事,这通常会出现在 viewModel 中,因此,您也应该在 viewmodel 中声明文本变量。
在 init
块中尝试。
calss MVVM: ViewModel() {
init {
/* Paste Code From Above Here */
}
var newStringFromStoredData by mutableStateOf("")
}
然后在 Composable 中阅读它
Text(viewModel.newStringFromStoredData)