RecyclerView to fetch a list of cars from a json array |
Following is the json array example that we are about to parse >> https://navneet7k.github.io/sample_array.json.
sample_array.json
[ { "id": "1", "name": "Mercedes Benz", "desc": "Mercedes Benz is a global automobile marque and a division of the German company Daimler AG. The brand is known for luxury vehicles, buses, coaches, and lorries. The headquarters is in Stuttgart, Baden-Württemberg. The name first appeared in 1926 under Daimler-Benz." }, { "id": "2", "name": "BMW", "desc": "BMW AG, originally an initialism for Bayerische Motoren Werke in German, or Bavarian Motor Works in English) is a German multinational company which currently produces luxury automobiles and motorcycles, and also produced aircraft engines until 1945." }, { "id": "3", "name": "Bentley", "desc": "Bentley Motors Limited is a British manufacturer and marketer of luxury cars and SUVs—and a subsidiary of the Volkswagen Group since 1998." }, { "id": "4", "name": "Mustang", "desc": "The Ford Mustang is an American car manufactured by Ford. It was originally based on the platform of the second generation North American Ford Falcon, a compact car." }, { "id": "5", "name": "Aston Martin", "desc": "Aston Martin Lagonda Global Holdings plc is a British independent manufacturer of luxury sports cars and grand tourers. It was founded in 1913 by Lionel Martin and Robert Bamford." }, { "id": "6", "name": "Lamborghini", "desc": "Automobili Lamborghini is an Italian brand and manufacturer of luxury sports cars and SUVs based in Sant'Agata Bolognese and tractors Lamborghini Trattori in Pieve di Cento, Italy. The company is owned by the Volkswagen Group through its subsidiary Audi." }, { "id": "7", "name": "BMW", "desc": "BMW AG, originally an initialism for Bayerische Motoren Werke in German, or Bavarian Motor Works in English) is a German multinational company which currently produces luxury automobiles and motorcycles, and also produced aircraft engines until 1945." }, { "id": "8", "name": "Bentley", "desc": "Bentley Motors Limited is a British manufacturer and marketer of luxury cars and SUVs—and a subsidiary of the Volkswagen Group since 1998." }, { "id": "9", "name": "Mustang", "desc": "The Ford Mustang is an American car manufactured by Ford. It was originally based on the platform of the second generation North American Ford Falcon, a compact car." }, { "id": "10", "name": "Aston Martin", "desc": "Aston Martin Lagonda Global Holdings plc is a British independent manufacturer of luxury sports cars and grand tourers. It was founded in 1913 by Lionel Martin and Robert Bamford." }, { "id": "11", "name": "Lamborghini", "desc": "Automobili Lamborghini is an Italian brand and manufacturer of luxury sports cars and SUVs based in Sant'Agata Bolognese and tractors Lamborghini Trattori in Pieve di Cento, Italy. The company is owned by the Volkswagen Group through its subsidiary Audi." }, { "id": "12", "name": "BMW", "desc": "BMW AG, originally an initialism for Bayerische Motoren Werke in German, or Bavarian Motor Works in English) is a German multinational company which currently produces luxury automobiles and motorcycles, and also produced aircraft engines until 1945." }, { "id": "13", "name": "Bentley", "desc": "Bentley Motors Limited is a British manufacturer and marketer of luxury cars and SUVs—and a subsidiary of the Volkswagen Group since 1998." }, { "id": "14", "name": "Mustang", "desc": "The Ford Mustang is an American car manufactured by Ford. It was originally based on the platform of the second generation North American Ford Falcon, a compact car." }, { "id": "15", "name": "Aston Martin", "desc": "Aston Martin Lagonda Global Holdings plc is a British independent manufacturer of luxury sports cars and grand tourers. It was founded in 1913 by Lionel Martin and Robert Bamford." }, { "id": "16", "name": "Lamborghini", "desc": "Automobili Lamborghini is an Italian brand and manufacturer of luxury sports cars and SUVs based in Sant'Agata Bolognese and tractors Lamborghini Trattori in Pieve di Cento, Italy. The company is owned by the Volkswagen Group through its subsidiary Audi." } ]
Now let us jump into some code, go to your app level build.gradle file and add all the necessary dependencies like shown below
implementation 'com.android.support:cardview-v7:28.0.0'
implementation 'com.android.support:design:28.0.0'
implementation 'com.squareup.retrofit2:retrofit:2.0.0-beta4'
implementation 'com.squareup.retrofit2:converter-gson:2.3.0'
app level build.gradle file |
First of all, generate the model class like shown below(you may create it manually also).
1) Automatic model class/pojo class generation using http://www.jsonschema2pojo.org/
You can make use of jsonschema2pojo to covert json to java object online. This is a really effective tool which even supports various annotation types like jackson, gson, moshi etc.
- So, first of all, go to http://www.jsonschema2pojo.org/
- Paste the json https://navneet7k.github.io/sample_array.json in the box provided
Specify Target language as Java, Source Type as JSON and annotation style as Gson |
- Now click preview and copy the generated java files
Now copy the contents of the class and add it in android studio project |
CarModel.java
public class CarModel { @SerializedName("id") @Expose private String id; @SerializedName("name") @Expose private String name; @SerializedName("desc") @Expose private String desc; public String getId() { return id; } public void setId(String id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getDesc() { return desc; } public void setDesc(String desc) { this.desc = desc; } }
Now that you have generated the required model class, you will have to create an adapter for your recyclerview, which inflates the layout(item_layout.xml) for each recyclerview item. We will be passing the array fetched from the json into this adapter as an arraylist through its constructor.
DataAdapter.java
public class DataAdapter extends RecyclerView.Adapter<DataAdapter.ViewHolder> { private ArrayList<CarModel> articles=new ArrayList<>(); private Context context; public DataAdapter(ArrayList<CarModel> articles, Context context) { this.context=context; this.articles=articles; } @Override public DataAdapter.ViewHolder onCreateViewHolder(ViewGroup viewGroup, int i) { View view = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.item_layout, viewGroup, false); return new ViewHolder(view); } @Override public void onBindViewHolder(DataAdapter.ViewHolder viewHolder, final int i) { final String car_name=articles.get(i).getName(); final String car_desc=articles.get(i).getDesc(); viewHolder.car_name.setText(car_name); viewHolder.car_desc.setText(car_desc); } @Override public int getItemCount() { return articles.size(); } public class ViewHolder extends RecyclerView.ViewHolder{ private TextView car_name,car_desc; public ViewHolder(View view) { super(view); car_name = (TextView)view.findViewById(R.id.car_name); car_desc = (TextView)view.findViewById(R.id.car_desc); } } }
Since we are parsing a json array example, we can parse it as a list like this List<CarModel>. So our response type will be of type List<CarModel>. Now create your retrofit instance by passing it with GsonConverterFactory. We will need gson since it will help you convert our json response into java model easily. Below, in onResponse you can see that we have fetched the reponse as a list and then passed to an arraylist. Further we have passed this arraylist to the adapter using the constructor like this
dataAdapter=new DataAdapter(carModels,MainActivity.this);
MainActivity.java
public class MainActivity extends AppCompatActivity { private DataAdapter dataAdapter; private ArrayList<CarModel> carModels=new ArrayList<>(); private RecyclerView mRecyclerView; private ProgressBar mProgressBar; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); mProgressBar=(ProgressBar)findViewById(R.id.progress_bar); mProgressBar.setVisibility(View.VISIBLE); mRecyclerView=(RecyclerView)findViewById(R.id.cars_list); mRecyclerView.setLayoutManager(new LinearLayoutManager(this)); parseJson(); } private void parseJson() { Retrofit retrofit = new Retrofit.Builder() .baseUrl("https://navneet7k.github.io/") .addConverterFactory(GsonConverterFactory.create()) .build(); RequestInterface request = retrofit.create(RequestInterface.class); Call<List<CarModel>> call1=request.getJson(); call1.enqueue(new Callback<List<CarModel>>() { @Override public void onResponse(Call<List<CarModel>> call, Response<List<CarModel>> response) { mProgressBar.setVisibility(View.GONE); if (response.isSuccessful() && response.body()!=null) { carModels = new ArrayList<>(response.body()); dataAdapter=new DataAdapter(carModels,MainActivity.this); mRecyclerView.setAdapter(dataAdapter); } } @Override public void onFailure(Call<List<CarModel>> call, Throwable t) { mProgressBar.setVisibility(View.GONE); Toast.makeText(MainActivity.this,"Oops! Something went wrong!",Toast.LENGTH_SHORT).show(); } }); } }
As shown above, after initialising the adapter, we set the adapter( dataAdapter ) to our recyclerview(mRecyclerView) like shown below.
mRecyclerView.setAdapter(dataAdapter);
Below is the interface for our network call to the endpoint.
RequestInterface.java
interface RequestInterface { @GET("sample_array.json") Call<List<CarModel>> getJson(); }
Below in the MainActivity's layout file(activity_main.xml
), we are adding the recyclerview widget.
activity_main.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity"> <android.support.v7.widget.RecyclerView android:id="@+id/cars_list" tools:listitem="@layout/item_layout" android:layout_width="match_parent" android:layout_height="wrap_content"/> <ProgressBar android:visibility="gone" android:id="@+id/progress_bar" android:layout_centerInParent="true" android:layout_width="wrap_content" android:layout_height="wrap_content" /> </RelativeLayout>
Further each recyclerview item's design will be as follows, we are inflating the following layout in the adapter class(DataAdapter.java) which takes care of handling each item in the recyclerview. Since each item in the recyclerview is reused during scroll to generate new items, onBindViewHolder method in DataAdapter.java gets called continuously to generate each item.
item_layout.xml
<?xml version="1.0" encoding="utf-8"?> <android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="5dp" > <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:padding="5dp" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical"> <TextView android:id="@+id/car_name" android:layout_width="match_parent" android:layout_height="wrap_content" /> <TextView android:id="@+id/car_desc" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout> </android.support.v7.widget.CardView>
The android.support.v7.widget.CardView used in above layout gives a cards like finish to the recyclerview items, it gives a cool material finish to the entire recyclerview. It would look something like this >>
cardview example |
Your resulting directory structure will be similar to the following
add all the java files within your package folder in 'src' directory and add the layout files in layout folder inside 'res' directory |
Download full source code here
Nice sir most useful
ReplyDeletethanks for sharing the feedback
DeleteMany Manuals about Retrofit suck and doesnt work! You Project great and well done. Thanks!
ReplyDeleteMany manuals about retrofit on the Internet do not work even with source code. You Example great! Thanks!
ReplyDeleteglad to know that it helped you, thanks for sharing feedback
Deletethanks bro.I will try. I wanted this to show a POC to a client . I am a java developer but dont know android
ReplyDeletethanks for sharing feedback, glad it helped
DeleteThank you so much, this code is very useful and easy to understand.
ReplyDeleteI really do appreciate this article, it was just what I needed to carry out my project.
ReplyDeleteThank you.
nice article, helped me. thank you
ReplyDelete