Get all pokemon from API
This commit is contained in:
		@@ -1,60 +1,68 @@
 | 
				
			|||||||
package com.ti.mobpo.ui
 | 
					package com.ti.mobpo.ui
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import androidx.lifecycle.ViewModel
 | 
					import androidx.lifecycle.ViewModel
 | 
				
			||||||
 | 
					import androidx.lifecycle.viewModelScope
 | 
				
			||||||
import com.google.gson.annotations.SerializedName
 | 
					import com.google.gson.annotations.SerializedName
 | 
				
			||||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
					import kotlinx.coroutines.flow.MutableStateFlow
 | 
				
			||||||
import kotlinx.coroutines.flow.StateFlow
 | 
					import kotlinx.coroutines.flow.StateFlow
 | 
				
			||||||
import kotlinx.coroutines.flow.asStateFlow
 | 
					import kotlinx.coroutines.flow.asStateFlow
 | 
				
			||||||
import retrofit2.Call
 | 
					import kotlinx.coroutines.launch
 | 
				
			||||||
import retrofit2.Retrofit
 | 
					import retrofit2.Retrofit
 | 
				
			||||||
import retrofit2.converter.gson.GsonConverterFactory
 | 
					import retrofit2.converter.gson.GsonConverterFactory
 | 
				
			||||||
import retrofit2.http.GET
 | 
					import retrofit2.http.GET
 | 
				
			||||||
 | 
					import java.io.IOException
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// Data class to hold Pokemon species information
 | 
					private const val BASE_URL = "https://pokeapi.co/api/v2/";
 | 
				
			||||||
data class PokemonSpecies(
 | 
					data class PokemonSpecies(
 | 
				
			||||||
    @SerializedName("name") val name: String,
 | 
					    @SerializedName("name") val name: String,
 | 
				
			||||||
    @SerializedName("url") val url: String
 | 
					    @SerializedName("url") val url: String
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// Data class to hold the response from the Pokemon species API
 | 
					 | 
				
			||||||
data class PokemonSpeciesResponse(
 | 
					data class PokemonSpeciesResponse(
 | 
				
			||||||
    @SerializedName("results") val results: List<PokemonSpecies>
 | 
					    @SerializedName("results") val results: List<PokemonSpecies>
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
interface PokeApiService {
 | 
					interface PokeApiService {
 | 
				
			||||||
    @GET("pokemon-species/?offset=0&limit=1025")
 | 
					    @GET("pokemon-species/?offset=0&limit=1025")
 | 
				
			||||||
    fun getPokemonSpecies(): Call<PokemonSpeciesResponse>
 | 
					    suspend fun getPokemonSpecies(): PokemonSpeciesResponse
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class PokeSearchViewModel : ViewModel() {
 | 
					class PokeSearchViewModel : ViewModel() {
 | 
				
			||||||
    private val retrofit = Retrofit.Builder()
 | 
					    private val retrofit = Retrofit.Builder()
 | 
				
			||||||
        .baseUrl("https://pokeapi.co/api/v2/")
 | 
					        .baseUrl(BASE_URL)
 | 
				
			||||||
        .addConverterFactory(GsonConverterFactory.create())
 | 
					        .addConverterFactory(GsonConverterFactory.create())
 | 
				
			||||||
        .build()
 | 
					        .build()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private val service = retrofit.create(PokeApiService::class.java)
 | 
					    private val service = retrofit.create(PokeApiService::class.java)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private val _uiState = MutableStateFlow(PokeSearchUiState())
 | 
					    private val _initialPokemonList = MutableStateFlow<List<PokemonSpecies>?>(null)
 | 
				
			||||||
    val uiState: StateFlow<PokeSearchUiState> = _uiState.asStateFlow()
 | 
					    private val _filteredPokemonList = MutableStateFlow<List<PokemonSpecies>?>(null)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private var pokemonList: List<PokemonSpecies>? = null
 | 
					    val pokemonList: StateFlow<List<PokemonSpecies>?> = _filteredPokemonList.asStateFlow()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    init {
 | 
					    init {
 | 
				
			||||||
        fetchPokemonSpecies()
 | 
					        fetchPokemonSpecies()
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private fun fetchPokemonSpecies() {
 | 
					    private fun fetchPokemonSpecies() {
 | 
				
			||||||
        service.getPokemonSpecies().enqueue(object : retrofit2.Callback<PokemonSpeciesResponse> {
 | 
					        viewModelScope.launch {
 | 
				
			||||||
            override fun onResponse(call: Call<PokemonSpeciesResponse>, response: retrofit2.Response<PokemonSpeciesResponse>) {
 | 
					            try {
 | 
				
			||||||
                if (response.isSuccessful) {
 | 
					                val response = service.getPokemonSpecies()
 | 
				
			||||||
                    val speciesResponse = response.body()
 | 
					                _initialPokemonList.value = response.results
 | 
				
			||||||
                    pokemonList = speciesResponse?.results
 | 
					                _filteredPokemonList.value = response.results
 | 
				
			||||||
                }
 | 
					            } catch (e: IOException) {
 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            override fun onFailure(call: Call<PokemonSpeciesResponse>, t: Throwable) {
 | 
					 | 
				
			||||||
                /*TODO*/
 | 
					                /*TODO*/
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
        })
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
}
 | 
					
 | 
				
			||||||
 | 
					    fun search(query: String) {
 | 
				
			||||||
 | 
					        val initialPokemonList = _initialPokemonList.value
 | 
				
			||||||
 | 
					        if (query.isNotBlank() && initialPokemonList != null) {
 | 
				
			||||||
 | 
					            val filteredList = initialPokemonList.filter { it.name.contains(query, ignoreCase = true) }
 | 
				
			||||||
 | 
					            _filteredPokemonList.value = filteredList
 | 
				
			||||||
 | 
					        } else {
 | 
				
			||||||
 | 
					            _filteredPokemonList.value = initialPokemonList
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@@ -1,9 +1,13 @@
 | 
				
			|||||||
package com.ti.mobpo.ui.screens
 | 
					package com.ti.mobpo.ui.screens
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import com.ti.mobpo.ui.PokeSearchViewModel
 | 
				
			||||||
import androidx.compose.foundation.layout.Arrangement
 | 
					import androidx.compose.foundation.layout.Arrangement
 | 
				
			||||||
import androidx.compose.foundation.layout.Column
 | 
					import androidx.compose.foundation.layout.Column
 | 
				
			||||||
 | 
					import androidx.compose.foundation.layout.Spacer
 | 
				
			||||||
import androidx.compose.foundation.layout.fillMaxSize
 | 
					import androidx.compose.foundation.layout.fillMaxSize
 | 
				
			||||||
 | 
					import androidx.compose.foundation.layout.height
 | 
				
			||||||
import androidx.compose.foundation.layout.padding
 | 
					import androidx.compose.foundation.layout.padding
 | 
				
			||||||
 | 
					import androidx.compose.material3.Text
 | 
				
			||||||
import androidx.compose.runtime.Composable
 | 
					import androidx.compose.runtime.Composable
 | 
				
			||||||
import androidx.compose.runtime.collectAsState
 | 
					import androidx.compose.runtime.collectAsState
 | 
				
			||||||
import androidx.compose.runtime.getValue
 | 
					import androidx.compose.runtime.getValue
 | 
				
			||||||
@@ -15,30 +19,41 @@ import androidx.compose.ui.unit.dp
 | 
				
			|||||||
import com.ti.mobpo.R
 | 
					import com.ti.mobpo.R
 | 
				
			||||||
import com.ti.mobpo.ui.SearchBar
 | 
					import com.ti.mobpo.ui.SearchBar
 | 
				
			||||||
import androidx.lifecycle.viewmodel.compose.viewModel
 | 
					import androidx.lifecycle.viewmodel.compose.viewModel
 | 
				
			||||||
import com.ti.mobpo.ui.PokeSearchViewModel
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
@Composable
 | 
					@Composable
 | 
				
			||||||
fun PokeSearchScreen(pokesearchViewModel: PokeSearchViewModel = viewModel()){
 | 
					fun PokeSearchScreen(pokeSearchViewModel: PokeSearchViewModel = viewModel()) {
 | 
				
			||||||
    val pokesearchUiState by pokesearchViewModel.uiState.collectAsState()
 | 
					    PokeSearch(pokeSearchViewModel)
 | 
				
			||||||
    PokeSearch()
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@Composable
 | 
					@Composable
 | 
				
			||||||
fun PokeSearch() {
 | 
					fun PokeSearch(pokeSearchViewModel: PokeSearchViewModel = viewModel()) {
 | 
				
			||||||
    Column (
 | 
					    val searchResults by pokeSearchViewModel.pokemonList.collectAsState()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    Column(
 | 
				
			||||||
        verticalArrangement = Arrangement.Top,
 | 
					        verticalArrangement = Arrangement.Top,
 | 
				
			||||||
        horizontalAlignment = Alignment.CenterHorizontally,
 | 
					        horizontalAlignment = Alignment.CenterHorizontally,
 | 
				
			||||||
        modifier = Modifier
 | 
					        modifier = Modifier
 | 
				
			||||||
            .fillMaxSize()
 | 
					            .fillMaxSize()
 | 
				
			||||||
            .padding(20.dp)
 | 
					            .padding(20.dp)
 | 
				
			||||||
    ) {
 | 
					    ) {
 | 
				
			||||||
        SearchBar(stringResource(R.string.input_field_label)){ value ->
 | 
					        SearchBar(stringResource(R.string.input_field_label)) { value ->
 | 
				
			||||||
            run {
 | 
					            pokeSearchViewModel.search(value)
 | 
				
			||||||
                println(value)
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        Spacer(modifier = Modifier.height(16.dp))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        searchResults?.let { results ->
 | 
				
			||||||
 | 
					            if (results.isNotEmpty()) {
 | 
				
			||||||
 | 
					                results.forEach { pokemon ->
 | 
				
			||||||
 | 
					                    Text(text = pokemon.name)
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
 | 
					            } else {
 | 
				
			||||||
 | 
					                Text("No results found")
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@Preview(showBackground = true)
 | 
					@Preview(showBackground = true)
 | 
				
			||||||
@Composable
 | 
					@Composable
 | 
				
			||||||
fun PokeSearchApp(){
 | 
					fun PokeSearchApp(){
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user