16

I'm looking to use enums for a list inside of a spinner widget on android. I have my enums setup as follows:

public enum States{

AL("Alabama"), 
AK("Alaska"), 
AR("Arkansas"), 
AZ("Arizona"), 
CA("California"), 
CO("Colorado"),
    ... (etc.)
}

My current array adapter is setup as follows:

mAddressState.setAdapter(new ArrayAdapter<States>(this, android.R.layout.simple_list_item_1, States.values()));

This almost works, but in my spinner list I end up with the abbreviations, rather than the state names (which is what I'm going for). Is there a workaround to get this setup correctly?

RyanInBinary
  • 1,533
  • 3
  • 19
  • 47

5 Answers5

39

I hope that this helps someone. It took me a while to figure it out for myself. The trick is to override toString in your enum. The code for your states enum would be:

public enum States{
  AL("Alabama"), 
  AK("Alaska"), 
  AR("Arkansas"), 
  AZ("Arizona"), 
  CA("California"), 
  CO("Colorado"),
    ... (etc.);

  private String theState;

  States(String aState) {
    theState = aState;
  }

  @Override public String toString() {
    return theState;
  }
}

Then, create the adapter just as you do:

   mAddressState.setAdapter(new ArrayAdapter<States>(this,
      android.R.layout.simple_list_item_1, States.values()));

and the long names will show up in the spinner. To get the abbreviated name from the adapter, to store the selected one for instance, use the enum.name() function. For instance:

Spinner spinner = (Spinner) myView.findViewById(R.id.theState);
String selected = ((States)spinner.getSelectedItem()).name();
LocalTrav
  • 405
  • 4
  • 6
2

Here is how to do it using Kotlin and Material TextInputLayout which can be used as Spinner replacement, first implement it like described in this answer: https://stackoverflow.com/a/57746352/2472350

first define the enum like this:

enum class States(val label: String) {
    AL("Alabama"), 
    AK("Alaska"), 
    AR("Arkansas"), 
    AZ("Arizona"), 
    CA("California"), 
    CO("Colorado"),;

    override fun toString(): String {
        return label
    }
}

then set an adapter like this:

val items = OrderStatusType.values()
val adapter = ArrayAdapter(requireContext(), R.layout.spinner_item_tv, items)
autoCompleteTextView.setAdapter(adapter)

the spinner_item_tv could be any TextView, like this:

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/spinner_item_tv"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    tools:text="@tools:sample/cities" />

to get the selected item:

val selectedState = autoCompleteTextView.text.toString()

you can also find the enum value by searching through them like this:

val selectedState = States.values().firstOrNull { it.label == autoCompleteTextView.text.toString() } 
// could be null if nothing is selected
Amin Keshavarzian
  • 3,646
  • 1
  • 37
  • 38
1

Let's try to provide the answer with the help of an example

public enum Day { SUNDAY, MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY } 

Consider the above enum. Now you can add it to an adapter in the following ways:

Method 1:

ArrayAdapter<Day> adapter = new ArrayAdapter<Day>(activity, android.R.layout.simple_spinner_dropdown_item, Day.values());

Note: You can override toString method in enum definition to display required values incase of advanced enums.

Method 2:

public static final List<String> daysList = Stream.of(Day.values()).map(Day::name).collect(Collectors.toList());
ArrayAdapter<String> adapter = new ArrayAdapter<String>(activity, android.R.layout.simple_spinner_dropdown_item, daysList);
0

Add an enum constructor like so... then replace States.values() with States.fullName()

public enum States{

    AL("Alabama"), 
    AK("Alaska"), 
    ... (etc.)

    private String fullName;

    States(String fullName) {
        this.fullName = fullName;
    }

    public String fullName()   { return fullName; }
}
uperez
  • 122
  • 3
  • That didn't work. I was actually doing that already and did not specify, sorry. The array adapter doesn't seem to be fond of me trying to do that. mAddressState.setAdapter(new ArrayAdapter(this, android.R.layout.simple_list_item_1, States.getStateName())); I also tried setting the array adapter type to new ArrayAdapter Still didn't do what I was after. Any other advice? – RyanInBinary Aug 25 '11 at 19:05
0

maybe you could try overriding the toString() function as shown here here . I haven't tried it yet but I was just about to.

Fahd
  • 256
  • 6
  • 15