Monday, January 13, 2020

How to Create a Contextual Action Mode Menu in Android

No comments email this post Edit Post

Contextual Action Mode in Android provides a temporary action bar that appears when users perform specific actions such as long-pressing an item.

It is commonly used in:

  • File managers
  • Gallery applications
  • Email apps
  • Chat applications
  • RecyclerView item selection

Unlike a floating context menu, Contextual Action Mode displays actions directly inside the top app bar for a cleaner and more modern user experience.

In this tutorial, we will learn:

  • What ActionMode is
  • How to activate contextual action mode
  • How to handle menu clicks
  • How to customize ActionMode appearance
  • Modern Android best practices

What Is Contextual Action Mode?

Contextual Action Mode is a temporary toolbar overlay that appears when the user selects or long-presses content.

It allows users to perform contextual operations such as:

  • Delete
  • Share
  • Edit
  • Copy
  • Select multiple items

What We Will Build

In this Android example:

  • User long-presses a TextView
  • Contextual Action Bar appears
  • Custom menu options are shown
  • Click events are handled
  • Toolbar overlay customization is applied

Step 1 — Create activity_main.xml

Create:


res/layout/activity_main.xml

<?xml version="1.0" encoding="utf-8"?>

<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:android=
    "http://schemas.android.com/apk/res/android"

    xmlns:app=
    "http://schemas.android.com/apk/res-auto"

    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <TextView
        android:id="@+id/text_view"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Long Press Me"
        android:textSize="30sp"

        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintEnd_toEndOf="parent"/>

</androidx.constraintlayout.widget.ConstraintLayout>

Step 2 — Create Menu Resource

Create:


res/menu/example_menu.xml

<?xml version="1.0" encoding="utf-8"?>

<menu
    xmlns:android=
    "http://schemas.android.com/apk/res/android">

    <item
        android:id="@+id/option_1"
        android:icon="@drawable/ic_delete"
        android:title="Delete"
        android:showAsAction="ifRoom"/>

    <item
        android:id="@+id/option_2"
        android:icon="@drawable/ic_share"
        android:title="Share"
        android:showAsAction="ifRoom"/>

</menu>

Step 3 — Implement MainActivity.java


package com.example.contextualactionmode;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.view.ActionMode;

import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity
        extends AppCompatActivity {

    private ActionMode actionMode;

    @Override
    protected void onCreate(
            Bundle savedInstanceState
    ) {

        super.onCreate(savedInstanceState);

        setContentView(
                R.layout.activity_main
        );

        TextView textView =
                findViewById(R.id.text_view);

        textView.setOnLongClickListener(v -> {

            if (actionMode != null) {

                return false;
            }

            actionMode =
                    startSupportActionMode(
                            actionModeCallback
                    );

            return true;
        });
    }

    private final ActionMode.Callback
            actionModeCallback =
            new ActionMode.Callback() {

        @Override
        public boolean onCreateActionMode(
                ActionMode mode,
                Menu menu
        ) {

            mode.getMenuInflater().inflate(
                    R.menu.example_menu,
                    menu
            );

            mode.setTitle(
                    "Choose Action"
            );

            return true;
        }

        @Override
        public boolean onPrepareActionMode(
                ActionMode mode,
                Menu menu
        ) {

            return false;
        }

        @Override
        public boolean onActionItemClicked(
                ActionMode mode,
                MenuItem item
        ) {

            int id = item.getItemId();

            if (id == R.id.option_1) {

                Toast.makeText(
                        MainActivity.this,
                        "Delete clicked",
                        Toast.LENGTH_SHORT
                ).show();

                mode.finish();

                return true;
            }

            if (id == R.id.option_2) {

                Toast.makeText(
                        MainActivity.this,
                        "Share clicked",
                        Toast.LENGTH_SHORT
                ).show();

                mode.finish();

                return true;
            }

            return false;
        }

        @Override
        public void onDestroyActionMode(
                ActionMode mode
        ) {

            actionMode = null;
        }
    };
}

How Contextual Action Mode Works

The workflow is:

  1. User long-presses a View
  2. ActionMode starts
  3. Custom contextual toolbar appears
  4. Menu options are displayed
  5. User selects action
  6. ActionMode closes automatically

Why ActionMode Is Useful

Contextual Action Mode improves user experience because:

  • Actions appear only when needed
  • UI stays clean
  • Selection-based actions become intuitive
  • Supports multi-selection workflows

Customizing ActionMode Appearance

Inside:


res/values/themes.xml

Add:


<style
    name="Theme.MyApp"
    parent="Theme.Material3.DayNight.NoActionBar">

    <item
        name="actionModeBackground">
        @color/purple_500
    </item>

    <item
        name="windowActionBarOverlay">
        true
    </item>

</style>

What Does windowActionBarOverlay Do?

When enabled:


windowActionBarOverlay = true

the contextual toolbar appears on top of the existing Toolbar instead of pushing the layout downward.


Modern Android Improvements

Modern Android applications often use Contextual Action Mode with:

  • RecyclerView selection
  • SelectionTracker API
  • Material Design 3
  • Jetpack Compose
  • Toolbar integration

Common Mistakes Developers Make

1. Using Deprecated Support Libraries

Always use:


androidx

instead of old:


android.support

2. Forgetting to Finish ActionMode

Always call:


mode.finish()

after action completion.


3. Not Handling Multiple Selections Properly

RecyclerView contextual actions should properly track selected items.


ActionMode vs PopupMenu

ActionMode PopupMenu
Toolbar overlay UI Floating popup menu
Best for selections Best for quick actions
Supports multi-select Usually single-item actions

Modern Alternative in Jetpack Compose

Jetpack Compose applications can implement contextual toolbars using:

  • TopAppBar
  • Selection containers
  • Compose state management

FAQ

What triggers Contextual Action Mode?

Usually long-click events or item selection.

Can ActionMode work with RecyclerView?

Yes. RecyclerView multi-selection is one of the most common ActionMode use cases.

Should modern apps still use ActionMode?

Yes. Contextual Action Mode is still widely used in Android applications for selection-based actions.


Conclusion

Contextual Action Mode provides a clean and modern way to perform temporary selection-based actions in Android applications.

Using ActionMode improves:

  • User experience
  • Toolbar interaction
  • Selection workflows
  • UI organization

Modern Android applications should combine ActionMode with RecyclerView selection systems, Material Design components, and lifecycle-aware architecture for scalable implementations.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

Saturday, January 4, 2020

Understanding Activities, Fragments, and Intents in Android

No comments email this post Edit Post

Activities, Fragments, and Intents are some of the most important building blocks of Android application development.

Every Android developer must understand how these components work together to build scalable and responsive mobile applications.

In this guide, we will learn:

  • What Activities are
  • Activity lifecycle methods
  • What Fragments are
  • How Intents work
  • Modern Android development best practices

What Is an Activity in Android?

An Activity represents a single user interface screen in an Android application.

Examples:

  • Login screen
  • Home screen
  • Profile screen
  • Settings page

Activities are responsible for:

  • Displaying UI
  • Handling user interaction
  • Managing lifecycle events
  • Launching other screens

Why Activities Are Important

Activities act as the entry point for user interaction in Android applications.

Every Android app usually contains multiple activities connected together through navigation flows.


Declaring Activities in AndroidManifest.xml

Every Activity must be declared inside:


AndroidManifest.xml

Example:


<activity
    android:name=".MainActivity" />

Android Activity Lifecycle

Android manages Activities using lifecycle methods.

These lifecycle callbacks help developers:

  • Manage memory
  • Handle app state
  • Pause background tasks
  • Restore UI state

Main Activity Lifecycle Methods

Method Purpose
onCreate() Initialize Activity
onStart() Activity becomes visible
onResume() Activity enters foreground
onPause() Activity partially hidden
onStop() Activity no longer visible
onRestart() Restarting stopped Activity
onDestroy() Cleanup before destruction

Typical Activity Launch Flow

When the app starts:


onCreate()
onStart()
onResume()

Back Button Lifecycle Flow

When user presses Back:


onPause()
onStop()
onDestroy()

Example Activity Lifecycle Logging


public class MainActivity
        extends AppCompatActivity {

    @Override
    protected void onCreate(
            Bundle savedInstanceState
    ) {

        super.onCreate(savedInstanceState);

        Log.d(
                "Lifecycle",
                "onCreate invoked"
        );
    }

    @Override
    protected void onStart() {

        super.onStart();

        Log.d(
                "Lifecycle",
                "onStart invoked"
        );
    }

    @Override
    protected void onResume() {

        super.onResume();

        Log.d(
                "Lifecycle",
                "onResume invoked"
        );
    }

    @Override
    protected void onPause() {

        super.onPause();

        Log.d(
                "Lifecycle",
                "onPause invoked"
        );
    }

    @Override
    protected void onStop() {

        super.onStop();

        Log.d(
                "Lifecycle",
                "onStop invoked"
        );
    }

    @Override
    protected void onDestroy() {

        super.onDestroy();

        Log.d(
                "Lifecycle",
                "onDestroy invoked"
        );
    }
}

Important Lifecycle Concepts

Foreground State

Activity is interactive during:


onResume()

Visible State

Activity is visible between:


onStart() → onStop()

Entire Lifetime

Activity exists between:


onCreate() → onDestroy()

What Is a Fragment?

A Fragment is a reusable UI component hosted inside an Activity.

Fragments help developers:

  • Create modular UI
  • Support tablets and foldables
  • Reuse components
  • Improve navigation flexibility

Why Modern Apps Use Fragments

Modern Android devices have multiple screen sizes and orientations.

Fragments allow applications to adapt dynamically across:

  • Phones
  • Tablets
  • Foldables
  • Large screens

Fragment Lifecycle

Fragments have their own lifecycle separate from Activities.

Important Fragment methods:

  • onAttach()
  • onCreate()
  • onCreateView()
  • onViewCreated()
  • onStart()
  • onResume()
  • onPause()
  • onDestroyView()
  • onDestroy()

What Is an Intent in Android?

Intent is a messaging object used for communication between Android components.

Intents are used to:

  • Open Activities
  • Start Services
  • Send Broadcasts
  • Launch external applications

Types of Intents


1. Explicit Intent

Explicit Intent directly specifies the target Activity or component.

Example:


Intent intent =
    new Intent(
        MainActivity.this,
        SecondActivity.class
    );

startActivity(intent);

2. Implicit Intent

Implicit Intent specifies an action instead of a class name.

Android automatically finds applications capable of handling the action.

Examples:

  • Opening camera
  • Sending email
  • Opening maps
  • Sharing content

Example — Open Browser Using Implicit Intent


Intent intent =
    new Intent(
        Intent.ACTION_VIEW,
        Uri.parse("https://developer.android.com")
    );

startActivity(intent);

Modern Android Architecture Recommendations

Modern Android development now prefers:

  • Single Activity Architecture
  • Navigation Component
  • Jetpack Compose
  • MVVM Architecture
  • ViewModel
  • StateFlow
  • Coroutines

Common Mistakes Beginners Make

1. Forgetting Activity Declaration

Undeclared Activities cause runtime crashes.


2. Heavy Work in onCreate()

Avoid heavy database or network operations inside:


onCreate()

3. Misusing Fragments

Fragments should remain modular and reusable.


4. Memory Leaks Through Context References

Improper lifecycle handling may cause memory leaks.


Activity vs Fragment

Activity Fragment
Independent screen Reusable UI component
Declared in Manifest Attached to Activity
Own window Shares Activity window
Lifecycle managed by Android Lifecycle tied to Activity

FAQ

Can an app have multiple Activities?

Yes. Most Android applications contain multiple Activities.

Can Fragments exist without Activities?

No. Fragments must be hosted inside Activities.

What is the modern navigation approach?

Navigation Component with Single Activity Architecture is the modern recommended approach.


Conclusion

Activities, Fragments, and Intents form the foundation of Android application architecture.

Understanding lifecycle management and component communication is essential for building scalable and responsive Android applications.

Modern Android development combines these components with lifecycle-aware architecture, Kotlin, Jetpack libraries, and reactive state management for production-grade applications.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

Sunday, November 10, 2019

How to Create a Video Intro Splash Screen in Android Using VideoView

No comments email this post Edit Post

Many modern Android applications display an intro video or animated splash screen before opening the main application interface.

Video splash screens are commonly used for:

  • Brand introductions
  • Gaming applications
  • Media applications
  • Startup animations
  • Promotional app launches

In this tutorial, we will learn how to create a fullscreen video intro splash screen in Android using:

  • VideoView
  • MediaPlayer listeners
  • Raw resource videos
  • Automatic screen navigation

What We Will Build

In this Android example:

  • Application launches with fullscreen video
  • Video automatically starts playing
  • Next screen opens after video completion
  • Error handling is implemented
  • Video is loaded from raw resources

Step 1 — Create activity_main.xml

Create:


res/layout/activity_main.xml

<?xml version="1.0" encoding="utf-8"?>

<RelativeLayout
    xmlns:android=
    "http://schemas.android.com/apk/res/android"

    android:layout_width="match_parent"

    android:layout_height="match_parent"

    android:background="@android:color/black">

    <VideoView
        android:id="@+id/videoView"

        android:layout_width="match_parent"

        android:layout_height="match_parent"

        android:layout_alignParentTop="true"

        android:layout_alignParentBottom="true"

        android:layout_alignParentStart="true"

        android:layout_alignParentEnd="true"/>

</RelativeLayout>

Step 2 — Add Video File

Inside:


res/

create a new folder named:


raw

Add your intro video file inside:


res/raw/

Example:


intro_video.mp4

Step 3 — Create MainActivity.java

Create:


MainActivity.java

package com.example.videosplash;

import androidx.appcompat.app.AppCompatActivity;

import android.content.Intent;
import android.media.MediaPlayer;
import android.net.Uri;
import android.os.Bundle;
import android.widget.Toast;
import android.widget.VideoView;

public class MainActivity
        extends AppCompatActivity {

    private VideoView videoView;

    @Override
    protected void onCreate(
            Bundle savedInstanceState
    ) {

        super.onCreate(savedInstanceState);

        setContentView(
                R.layout.activity_main
        );

        videoView =
                findViewById(R.id.videoView);

        String videoPath =
                "android.resource://"
                        + getPackageName()
                        + "/"
                        + R.raw.intro_video;

        Uri uri = Uri.parse(videoPath);

        videoView.setVideoURI(uri);

        videoView.start();

        videoView.setOnCompletionListener(
                new MediaPlayer
                        .OnCompletionListener() {

            @Override
            public void onCompletion(
                    MediaPlayer mp
            ) {

                Intent intent =
                        new Intent(
                                MainActivity.this,
                                HomeActivity.class
                        );

                startActivity(intent);

                finish();
            }
        });

        videoView.setOnErrorListener(
                new MediaPlayer
                        .OnErrorListener() {

            @Override
            public boolean onError(
                    MediaPlayer mp,
                    int what,
                    int extra
            ) {

                Toast.makeText(
                        MainActivity.this,
                        "Error while playing video",
                        Toast.LENGTH_LONG
                ).show();

                return true;
            }
        });
    }

    @Override
    protected void onPause() {

        super.onPause();

        if (videoView != null) {

            videoView.pause();
        }
    }

    @Override
    protected void onResume() {

        super.onResume();

        if (videoView != null) {

            videoView.start();
        }
    }

    @Override
    protected void onDestroy() {

        super.onDestroy();

        if (videoView != null) {

            videoView.stopPlayback();
        }
    }
}

Step 4 — Create HomeActivity.java

Create:


HomeActivity.java

package com.example.videosplash;

import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;

public class HomeActivity
        extends AppCompatActivity {

    @Override
    protected void onCreate(
            Bundle savedInstanceState
    ) {

        super.onCreate(savedInstanceState);

        setContentView(
                R.layout.activity_home
        );
    }
}

Step 5 — Create activity_home.xml


<?xml version="1.0" encoding="utf-8"?>

<LinearLayout
    xmlns:android=
    "http://schemas.android.com/apk/res/android"

    android:layout_width="match_parent"

    android:layout_height="match_parent"

    android:gravity="center"

    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"

        android:layout_height="wrap_content"

        android:text="Home Screen"

        android:textSize="28sp"/>

</LinearLayout>

Step 6 — Update AndroidManifest.xml

Inside:


AndroidManifest.xml

Add:


<application>

    <activity
        android:name=".HomeActivity"/>

    <activity
        android:name=".MainActivity">

        <intent-filter>

            <action
                android:name=
                "android.intent.action.MAIN"/>

            <category
                android:name=
                "android.intent.category.LAUNCHER"/>

        </intent-filter>

    </activity>

</application>

How This Video Splash Screen Works

The workflow is:

  1. App launches MainActivity
  2. VideoView loads intro video
  3. Video starts automatically
  4. Completion listener detects video end
  5. HomeActivity opens automatically

Why Use VideoView?

VideoView provides:

  • Simple video playback
  • Built-in MediaPlayer integration
  • Easy lifecycle handling
  • Minimal setup

Common Beginner Mistakes

1. Placing Video Outside raw Folder

Videos must be inside:


res/raw/

2. Using Large Video Files

Huge videos increase:

  • APK size
  • Loading time
  • Memory usage

3. Forgetting Lifecycle Handling

Always pause and release VideoView properly during lifecycle changes.


Modern Android Recommendations

Modern Android applications often prefer:

  • Lottie animations
  • MotionLayout
  • Jetpack Compose animations
  • Animated logos
  • Lightweight startup screens

VideoView vs ExoPlayer

VideoView ExoPlayer
Simple implementation Advanced media features
Good for splash videos Best for streaming apps
Basic playback controls Professional media engine

Performance Optimization Tips

  • Use compressed MP4 videos
  • Keep intro short
  • Avoid very high resolutions
  • Release media resources properly
  • Use splash screen API for lightweight startups

FAQ

Can VideoView stream online videos?

Yes, VideoView can stream videos using network URLs.

What is the modern alternative to VideoView?

ExoPlayer is the modern recommended media playback library for advanced applications.

Should apps use long intro videos?

No. Long intro videos may negatively affect user experience and app startup performance.


Conclusion

Video splash screens can create visually engaging application startup experiences when implemented correctly.

Using VideoView with MediaPlayer listeners allows developers to build simple intro video systems with minimal code.

Modern Android applications should balance branding animations with startup performance, smooth navigation, and user experience optimization.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

Sunday, November 3, 2019

Android Architecture Components Tutorial — MVVM, Room, LiveData & ViewModel

No comments email this post Edit Post

Modern Android development focuses heavily on scalable architecture, lifecycle awareness, and maintainable code structures.

Google introduced Android Architecture Components to solve common Android development problems such as:

  • Configuration changes
  • Memory leaks
  • Lifecycle issues
  • Bloated Activities and Fragments
  • Difficult state management

In this tutorial series, we will build a complete Note Taking Application using:

  • Room Database
  • ViewModel
  • LiveData
  • RecyclerView
  • Repository Pattern
  • MVVM Architecture
  • Java

Complete Tutorial Series

  • Part 1 — Introduction
  • Part 2 — Entity
  • Part 3 — DAO & RoomDatabase
  • Part 4 — Repository
  • Part 5 — ViewModel
  • Part 6 — RecyclerView + Adapter
  • Part 7 — Add Note Activity
  • Part 8 — Swipe to Delete
  • Part 9 — Update Functionality
  • Part 10 — ListAdapter

Part 1 — Introduction

In this tutorial series, we will build a complete Note Taking App using Android Architecture Components and modern Android development practices.

The application will support:

  • Insert Notes
  • Read Notes
  • Update Notes
  • Delete Notes
  • Persistent SQLite storage

We will follow Google’s officially recommended Android app architecture principles.


What Are Android Architecture Components?

Android Architecture Components are libraries provided by Google to help developers build:

  • Lifecycle-aware applications
  • Maintainable codebases
  • Scalable app structures
  • Testable applications

These components reduce boilerplate code and simplify state management in Android applications.


Why Traditional Android Apps Become Problematic

In older Android applications:

  • Activities become too large
  • Fragments handle too much logic
  • Database code mixes with UI code
  • Configuration changes destroy UI state
  • Memory leaks become common

This creates tightly coupled and difficult-to-maintain applications.


What Problems Do ViewModel and LiveData Solve?

ViewModel

ViewModel stores and manages UI-related data in a lifecycle-conscious way.

Benefits:

  • Survives screen rotations
  • Preserves UI data
  • Separates UI from business logic
  • Reduces Activity complexity

LiveData

LiveData is an observable data holder class that is lifecycle-aware.

It automatically updates UI components only when they are active.

Benefits:

  • Automatic UI updates
  • Lifecycle awareness
  • Prevents crashes
  • Avoids memory leaks

What Is Room Persistence Library?

Room is a database abstraction layer built on top of SQLite.

Instead of manually handling SQLiteOpenHelper and SQL boilerplate code, Room uses:

  • Annotations
  • Entities
  • DAO interfaces
  • Compile-time query validation

Why Room Is Better Than Raw SQLite

Raw SQLite Room Database
Large boilerplate code Minimal code
Manual cursor handling Automatic object mapping
Runtime SQL errors Compile-time query validation
Difficult maintenance Cleaner architecture

What Is DAO?

DAO stands for:


Data Access Object

DAO contains all database operations such as:

  • Insert
  • Update
  • Delete
  • Read queries

What Is Repository Pattern?

Repository acts as an abstraction layer between:

  • ViewModel
  • Data sources

Benefits:

  • Cleaner architecture
  • Single source of truth
  • Easy testing
  • Better scalability

Understanding MVVM Architecture

The architecture used in this tutorial is:


MVVM

which stands for:

  • Model
  • View
  • ViewModel

MVVM Architecture Flow


UI (Activity / Fragment)
        ↓
ViewModel
        ↓
Repository
        ↓
Room Database

Benefits of MVVM

  • Separation of concerns
  • Scalable architecture
  • Easy maintenance
  • Lifecycle awareness
  • Better testing support
  • Cleaner codebase

Technologies Used in This Series

  • Java
  • AndroidX
  • RecyclerView
  • Room Database
  • LiveData
  • ViewModel
  • MVVM

Modern Android Recommendations

Modern Android development now commonly uses:

  • Kotlin
  • Jetpack Compose
  • StateFlow
  • Coroutines
  • Hilt Dependency Injection
  • Navigation Component

However, understanding MVVM with Java and XML layouts is still extremely important for Android fundamentals and legacy projects.


What We Will Build in This Series

The final Note App will include:

  • SQLite local storage
  • Modern RecyclerView UI
  • CRUD operations
  • Swipe-to-delete
  • Update note functionality
  • Lifecycle-aware architecture
  • MVVM implementation

Official Android Architecture Guide

Google Official Guide:

developer.android.com/jetpack/docs/guide


Common Beginner Mistakes

1. Putting Database Logic Inside Activity

Database operations should be separated using Repository and ViewModel.


2. Ignoring Lifecycle Awareness

Configuration changes can destroy Activities and cause data loss.


3. Using AsyncTask

Modern Android development now prefers:

  • Coroutines
  • Executors
  • WorkManager

FAQ

Why use MVVM in Android?

MVVM creates scalable, maintainable, and lifecycle-aware Android applications.

Is Room better than SQLiteOpenHelper?

Yes. Room reduces boilerplate code and provides compile-time SQL validation.

Can ViewModel survive screen rotation?

Yes. ViewModel survives configuration changes like screen rotations.


Conclusion

Android Architecture Components help developers build scalable, maintainable, and lifecycle-aware applications.

Using MVVM, Room, ViewModel, and LiveData significantly improves code quality and application stability.

In the next part of this series, we will create our first Room Entity class and start building the Note Database.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

How to Update UI Every Minute Using BroadcastReceiver in Android

No comments email this post Edit Post

Android applications sometimes need to perform tasks automatically at fixed time intervals.

Examples include:

  • Clock applications
  • Countdown timers
  • Session tracking
  • Analytics updates
  • Dashboard refresh systems

Android provides a system broadcast called:


Intent.ACTION_TIME_TICK

This broadcast triggers every minute when the system clock changes minute values.

In this tutorial, we will learn how to update the user interface every minute using a BroadcastReceiver in Android.


What Is ACTION_TIME_TICK?

ACTION_TIME_TICK is a system broadcast sent by Android every minute.

It allows applications to:

  • Refresh UI automatically
  • Update timers
  • Track minute changes
  • Execute lightweight periodic tasks

Important Limitation

The ACTION_TIME_TICK broadcast:

  • Cannot be registered in AndroidManifest.xml
  • Must be registered dynamically at runtime

What We Will Build

In this Android example:

  • Application listens for minute changes
  • Counter increases every minute
  • UI updates automatically
  • BroadcastReceiver registers dynamically

Step 1 — Create activity_main.xml

Create the layout file:


<?xml version="1.0" encoding="utf-8"?>

<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <TextView
        android:id="@+id/textViewCounter"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="0"
        android:textSize="60sp"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintEnd_toEndOf="parent"/>

</androidx.constraintlayout.widget.ConstraintLayout>

Step 2 — Implement MainActivity.java

Open:


MainActivity.java

Add the following code:


package com.example.minuteupdater;

import androidx.appcompat.app.AppCompatActivity;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Bundle;
import android.widget.TextView;

public class MainActivity
        extends AppCompatActivity {

    private TextView textViewCounter;

    private BroadcastReceiver minuteReceiver;

    private int counter = 0;

    @Override
    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        textViewCounter =
                findViewById(R.id.textViewCounter);
    }

    private void startMinuteUpdater() {

        IntentFilter intentFilter =
                new IntentFilter(
                        Intent.ACTION_TIME_TICK
                );

        minuteReceiver =
                new BroadcastReceiver() {

                    @Override
                    public void onReceive(
                            Context context,
                            Intent intent
                    ) {

                        counter++;

                        textViewCounter.setText(
                                String.valueOf(counter)
                        );
                    }
                };

        registerReceiver(
                minuteReceiver,
                intentFilter
        );
    }

    @Override
    protected void onResume() {

        super.onResume();

        startMinuteUpdater();
    }

    @Override
    protected void onPause() {

        super.onPause();

        if (minuteReceiver != null) {

            unregisterReceiver(minuteReceiver);
        }
    }
}

How This Implementation Works

The workflow is:

  1. Activity starts
  2. BroadcastReceiver registers dynamically
  3. Android sends ACTION_TIME_TICK every minute
  4. Receiver captures broadcast
  5. Counter increments
  6. UI updates automatically

Why Dynamic Registration Is Required

Android does not allow:


ACTION_TIME_TICK

inside:


AndroidManifest.xml

for battery optimization reasons.

Therefore, developers must register it dynamically using:


registerReceiver()

Why unregisterReceiver() Is Important

Failing to unregister BroadcastReceivers can cause:

  • Memory leaks
  • Application crashes
  • Lifecycle issues

Always unregister receivers inside:


onPause()
or
onDestroy()

Common Mistakes Developers Make

1. Registering Receiver Multiple Times

Repeated registrations can cause duplicate callbacks.


2. Forgetting unregisterReceiver()

This may cause:

  • IllegalArgumentException
  • Memory leaks

3. Performing Heavy Work Inside onReceive()

BroadcastReceivers should only perform lightweight operations.


Modern Android Recommendations

Modern Android applications should prefer:

  • WorkManager
  • Lifecycle-aware components
  • ViewModel
  • Coroutines
  • Jetpack Compose state handling

ACTION_TIME_TICK vs Timer

ACTION_TIME_TICK CountDownTimer
System-level minute updates Custom timer implementation
Battery optimized Runs continuously
Every minute only Flexible intervals

FAQ

Can ACTION_TIME_TICK run in background?

It works only while the application process is active.

Can ACTION_TIME_TICK be declared in AndroidManifest.xml?

No. Android restricts manifest registration for this broadcast.

What is the modern alternative?

For periodic background work, WorkManager is the recommended modern solution.


Conclusion

BroadcastReceivers provide an efficient way to react to system events in Android.

Using:


Intent.ACTION_TIME_TICK

developers can update UI automatically every minute with minimal overhead.

Modern Android applications should combine lifecycle-aware architecture with optimized background processing solutions for scalable performance.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

How to Learn Android Programming Effectively as a Beginner

No comments email this post Edit Post

Many beginners struggle when starting Android development because they are unsure where to begin.

Common questions include:

  • Should I read books?
  • Should I watch YouTube tutorials?
  • Should I buy paid courses?
  • How do I actually start building apps?

The truth is that there is no single perfect learning method for everyone. However, there are practical approaches that consistently help beginners become better Android developers faster.

In this guide, we will discuss a realistic roadmap to learning Android programming effectively.


1. Start With a Beginner-Friendly Book or Course

When you know absolutely nothing about programming, structured learning is important.

A good beginner book or video course helps you:

  • Understand programming basics
  • Learn Android terminology
  • Avoid confusion
  • Follow a proper learning order

Trying to learn everything randomly from the internet can overwhelm beginners because:

  • Information may be outdated
  • Tutorial quality varies
  • There is too much content available

Recommended Beginner Resources

  • Head First Java
  • Android Developer Documentation
  • Kotlin Official Documentation
  • Android Basics by Google

Important Tip

Do not spend months only reading theory.

Your goal should be:

  • Understand basics quickly
  • Start building projects early
  • Learn by solving real problems

2. Start Building Real Android Projects

The fastest way to learn Android development is by building applications.

Theory alone will not make concepts stick permanently. Practical implementation is what builds real development skills.


Best Beginner Android Project Ideas

  • To-do list app
  • Notes app
  • Expense tracker
  • Calculator app
  • Habit tracker
  • Weather app
  • Quiz app

Why Building Projects Is Important

While building projects, you naturally learn:

  • UI design
  • Navigation
  • RecyclerView
  • SQLite or Room database
  • API integration
  • Architecture patterns
  • Debugging

Every project introduces new real-world challenges that improve your problem-solving ability.


3. Use Google and Stack Overflow Extensively

Professional developers constantly search for solutions online.

Even experienced Android developers use:

  • Google
  • Stack Overflow
  • GitHub
  • Official Android documentation
  • Reddit communities

How to Search Properly

Instead of searching:


How to build Instagram app?

Search specific problems like:


How to implement RecyclerView pagination in Android

How to save Room database data in Android

Always Check Content Freshness

Android development changes rapidly.

Always check:

  • Publication date
  • Android API version
  • Library version
  • Official recommendations

4. Watch YouTube Tutorials Strategically

YouTube is excellent for:

  • Visual learning
  • UI implementation
  • Project walkthroughs
  • Architecture explanations

However, YouTube tutorials should supplement learning — not completely replace documentation and practical coding.


Common Problems With YouTube Tutorials

  • Outdated code
  • Copy-paste learning
  • Incomplete explanations
  • Bad architecture practices

Best Way to Use Tutorials

  1. Watch tutorial for overview
  2. Understand the concept
  3. Build project yourself
  4. Modify features independently
  5. Experiment with improvements

5. Learn Kotlin Instead of Only Java

Modern Android development primarily uses Kotlin.

Google officially recommends Kotlin for Android applications.


Why Kotlin Is Better for Modern Android

Java Kotlin
More boilerplate code Cleaner syntax
Older Android language Official modern language
Verbose Concise and safer

6. Learn Modern Android Development

Modern Android interviews and companies expect developers to know:

  • Kotlin
  • Jetpack Compose
  • MVVM Architecture
  • Coroutines
  • Room Database
  • Retrofit
  • Flow & StateFlow
  • Hilt Dependency Injection
  • Navigation Component

7. Understand That Learning Takes Time

Programming can feel frustrating in the beginning.

You will frequently encounter:

  • Errors
  • Crashes
  • Confusing concepts
  • Debugging problems

This is completely normal.

Every experienced developer learned through:

  • Practice
  • Mistakes
  • Debugging
  • Experimentation

Recommended Beginner Android Learning Roadmap

Phase 1 — Programming Basics

  • Variables
  • Functions
  • Loops
  • Conditions
  • OOP concepts

Phase 2 — Android Basics

  • Activities
  • Fragments
  • Layouts
  • RecyclerView
  • Intents

Phase 3 — Intermediate Android

  • API integration
  • Room database
  • Firebase
  • Authentication
  • Architecture patterns

Phase 4 — Advanced Android

  • Jetpack Compose
  • Clean Architecture
  • Dependency Injection
  • Performance optimization
  • Scalable app architecture

Important Advice for Beginners

  • Do not compare yourself with others
  • Focus on consistency
  • Build projects continuously
  • Learn debugging properly
  • Read official documentation
  • Practice daily

Conclusion

Learning Android programming becomes easier when you combine:

  • Structured learning
  • Practical projects
  • Google searches
  • Documentation reading
  • Continuous experimentation

The most important step is starting real projects as early as possible. That is where actual learning happens.

Modern Android development offers powerful tools and opportunities for developers willing to learn consistently.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and developer tooling products.

CodeChain Dev — Build Modern Products. Solve Real Problems.

Saturday, November 2, 2019

How to Integrate Razorpay Payment Gateway in Android

No comments email this post Edit Post

Razorpay is one of the most widely used payment gateways in India for Android applications.

It supports:

  • UPI payments
  • Credit cards
  • Debit cards
  • Net banking
  • Wallet payments

Razorpay integration is fast, developer-friendly, and requires minimal code for basic payment implementation.

In this tutorial, we will learn how to integrate Razorpay Payment Gateway in Android using the official Razorpay Android SDK.


Features of Razorpay Android SDK

  • Fast payment integration
  • Multiple payment methods
  • UPI support
  • Secure payment processing
  • Custom branding support
  • Production-ready checkout UI

Requirements

  • Minimum SDK 19 or higher
  • Android Studio
  • Internet connection
  • Razorpay account

Step 1 — Create New Android Project

Open Android Studio and create a new Android project.

  1. Click File → New Project
  2. Select Empty Activity
  3. Choose Java or Kotlin
  4. Finish project setup

Step 2 — Add Razorpay Dependency

Open build.gradle and add:


dependencies {

    implementation 'com.razorpay:checkout:1.6.33'
}

Then sync the Gradle project.


Step 3 — Add Permissions and API Key

Open AndroidManifest.xml.

Add Internet permission:


<uses-permission
    android:name="android.permission.INTERNET"/>

Add Razorpay API Key

Inside the <application> tag:


<meta-data
    android:name="com.razorpay.ApiKey"
    android:value="YOUR_RAZORPAY_KEY"/>

Replace:


YOUR_RAZORPAY_KEY

with your actual Razorpay API key.


Step 4 — Create activity_checkout.xml

Create layout file inside:


res/layout/activity_checkout.xml

<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:gravity="center"
    android:padding="16dp">

    <EditText
        android:id="@+id/editTextAmount"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="Enter Amount"
        android:inputType="numberDecimal"/>

    <Button
        android:id="@+id/buttonPay"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Pay Now"
        android:layout_marginTop="16dp"/>

</LinearLayout>

Step 5 — Create CheckoutActivity.java

Create:


CheckoutActivity.java

package com.example.razorpayexample;

import androidx.appcompat.app.AppCompatActivity;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;

import com.razorpay.Checkout;
import com.razorpay.PaymentResultListener;

import org.json.JSONObject;

public class CheckoutActivity
        extends AppCompatActivity
        implements PaymentResultListener {

    private EditText editTextAmount;

    private Button buttonPay;

    @Override
    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_checkout);

        editTextAmount =
                findViewById(R.id.editTextAmount);

        buttonPay =
                findViewById(R.id.buttonPay);

        buttonPay.setOnClickListener(
                new View.OnClickListener() {

                    @Override
                    public void onClick(View view) {

                        if (editTextAmount.getText()
                                .toString()
                                .trim()
                                .isEmpty()) {

                            Toast.makeText(
                                    CheckoutActivity.this,
                                    "Enter payment amount",
                                    Toast.LENGTH_SHORT
                            ).show();

                            return;
                        }

                        startPayment();
                    }
                });
    }

    private void startPayment() {

        final Activity activity = this;

        final Checkout checkout =
                new Checkout();

        try {

            JSONObject options =
                    new JSONObject();

            options.put(
                    "name",
                    "CodeChain Dev"
            );

            options.put(
                    "description",
                    "Demo Payment"
            );

            options.put(
                    "currency",
                    "INR"
            );

            String payment =
                    editTextAmount
                            .getText()
                            .toString();

            double total =
                    Double.parseDouble(payment);

            total = total * 100;

            options.put("amount", total);

            JSONObject prefill =
                    new JSONObject();

            prefill.put(
                    "email",
                    "example@gmail.com"
            );

            prefill.put(
                    "contact",
                    "9999999999"
            );

            options.put(
                    "prefill",
                    prefill
            );

            checkout.open(activity, options);

        } catch (Exception e) {

            Toast.makeText(
                    activity,
                    "Payment Error: "
                            + e.getMessage(),
                    Toast.LENGTH_SHORT
            ).show();

            e.printStackTrace();
        }
    }

    @Override
    public void onPaymentSuccess(
            String razorpayPaymentId
    ) {

        Toast.makeText(
                this,
                "Payment Successful",
                Toast.LENGTH_SHORT
        ).show();
    }

    @Override
    public void onPaymentError(
            int code,
            String response
    ) {

        Toast.makeText(
                this,
                "Payment Failed",
                Toast.LENGTH_SHORT
        ).show();
    }
}

How Razorpay Payment Flow Works

The workflow is:

  1. User enters amount
  2. User clicks Pay button
  3. Razorpay Checkout opens
  4. User completes payment
  5. Payment callback returns success or failure

Understanding Razorpay Amount System

Razorpay expects payment amount in:


Paise

Example:

INR Paise
1 INR 100
500 INR 50000

That is why:


total = total * 100;

Common Mistakes Developers Make

1. Using Wrong API Key

Always use:

  • Test key for development
  • Live key for production

2. Forgetting Internet Permission

Without Internet permission, Razorpay Checkout cannot connect to servers.


3. Trusting Frontend Success Only

Frontend payment success is NOT enough for production applications.


Important Production Security Recommendations

Production applications should ALWAYS:

  • Verify payments on backend
  • Validate Razorpay signature
  • Store transaction logs securely
  • Prevent duplicate transactions
  • Use HTTPS APIs

Modern Android Improvements

Modern Android applications can improve this integration using:

  • Kotlin
  • MVVM Architecture
  • Jetpack Compose
  • Coroutines
  • Retrofit API integration
  • Secure backend validation

Razorpay vs UPI Intent Integration

Razorpay UPI Intent
Supports multiple payment methods Mainly UPI only
Professional checkout UI Basic app switching
Backend payment ecosystem Lightweight integration

FAQ

Does Razorpay support UPI?

Yes. Razorpay supports UPI payments along with cards, wallets, and net banking.

Can I test payments without real money?

Yes. Razorpay provides test mode with test credentials.

Is backend verification necessary?

Yes. Production systems must verify payment signatures securely on backend.


Conclusion

Razorpay provides one of the simplest ways to integrate secure payment functionality into Android applications.

Its SDK reduces development complexity while supporting multiple payment methods through a professional checkout experience.

For production applications, developers should combine frontend payment flow with secure backend verification systems.


About the Author

Salil Jha is a Full Stack and Mobile Developer specializing in Android, React Native, fintech systems, scalable SaaS platforms, and payment integrations.

CodeChain Dev — Build Modern Products. Solve Real Problems.