实现 Google 在 jetpack compose android 中放置 autoComplete 文本字段实现

Ali*_*waz 10 android google-places placeautocompletefragment android-jetpack-compose

有人在 jetpack 撰写项目中实现了谷歌自动完成建议文本字段或片段吗?如果是这样,请指导或分享代码片段,因为我在实现它时遇到困难。

更新

这是我触发打开全屏对话框的意图,但是当我开始在其中输入时,它会被关闭,而且我也无法弄清楚问题是什么,并且需要有关处理活动结果的线索以供阅读此 compose 函数内的预测结果。

    Places.initialize(context, "sa")

    val fields = listOf(Place.Field.ID, Place.Field.NAME)

    val intent = Autocomplete.IntentBuilder(
        AutocompleteActivityMode.FULLSCREEN,fields).build(context)

        startActivityForResult(context as MainActivity,intent, AUTOCOMPLETE_REQUEST_CODE, Bundle.EMPTY)
                            
Run Code Online (Sandbox Code Playgroud)

Tom*_*Tom 12

我正在使用 MVVM 架构,这就是我实现它的方式:

GooglePlaceAPI

我创建了一个用于访问名为 GooglePlacesApi 的 google api 的 api
interface GooglePlacesApi {
    @GET("maps/api/place/autocomplete/json")
    suspend fun getPredictions(
        @Query("key") key: String = <GOOGLE_API_KEY>,
        @Query("types") types: String = "address",
        @Query("input") input: String
    ): GooglePredictionsResponse

    companion object{
        const val BASE_URL = "https://maps.googleapis.com/"
    }
}
Run Code Online (Sandbox Code Playgroud)

@Query("types") 字段用于指定您在查询中查找什么,您可以查找机构等。可以在此处找到类型

楷模

所以我为此实现创建了 3 个模型:
谷歌预测响应
如果您使用邮递员执行 GET 请求,则响应的方式如下:

Google 预测响应

您可以看到我们有一个带有“预测”键的对象,因此这是我们的第一个模型。

data class GooglePredictionsResponse(
    val predictions: ArrayList<GooglePrediction>
)
Run Code Online (Sandbox Code Playgroud)
谷歌预测术语
data class GooglePredictionTerm(
    val offset: Int,
    val value: String
)
Run Code Online (Sandbox Code Playgroud)
谷歌预测
data class GooglePrediction(
    val description: String,
    val terms: List<GooglePredictionTerm>
)
Run Code Online (Sandbox Code Playgroud)

我只需要这些信息,如果您需要其他任何信息,请随意修改模型或创建您自己的模型。

Google地方信息库

最后我们创建存储库来获取信息(我使用 hilt 来注入我的依赖项,如果不使用它,您可以忽略这些注释)
@ActivityScoped
class GooglePlacesRepository @Inject constructor(
    private val api: GooglePlacesApi,
){
    suspend fun getPredictions(input: String): Resource<GooglePredictionsResponse>{
        val response = try {
            api.getPredictions(input = input)
        } catch (e: Exception) {
            Log.d("Rently", "Exception: ${e}")
            return Resource.Error("Failed prediction")
        }

        return Resource.Success(response)
    }
}
Run Code Online (Sandbox Code Playgroud)

在这里,我使用了一个我创建的额外类来处理响应,称为 Resource

sealed class Resource<T>(val data: T? = null, val message: String? = null){
    class Success<T>(data: T): Resource<T>(data)
    class Error<T>(message: String, data:T? = null): Resource<T>(data = data, message = message)
    class Loading<T>(data: T? = null): Resource<T>(data = data)
}
Run Code Online (Sandbox Code Playgroud)

查看模型

我再次使用剑柄,因此如果不使用它,请忽略注释。
@HiltViewModel
class AddApartmentViewModel @Inject constructor(private val googleRepository: GooglePlacesRepository): ViewModel(){

    val isLoading = mutableStateOf(false)
    val predictions = mutableStateOf(ArrayList<GooglePrediction>())
    
    fun getPredictions(address: String) {
        viewModelScope.launch {
            isLoading.value = true
            val response = googleRepository.getPredictions(input = address)
            when(response){
                is Resource.Success -> {
                    predictions.value = response.data?.predictions!!
                }
            }

            isLoading.value = false
        }
    }

    fun onSearchAddressChange(address: String){
        getPredictions(address)
    }
}
Run Code Online (Sandbox Code Playgroud)

如果您需要任何进一步的帮助,请告诉我

  • 我没有包含 UI 实现,因为我认为它是单独的,但这是更容易的部分;)