2011-01-28 42 views
18

En la aplicación en la que he estado trabajando, me gustaría tener un botón de estado múltiple (en mi caso, tres), en lugar de los dos que proporciona ToggleButton. Intenté comenzar el mío que se extiende a Button, siguiendo la fuente CompoundButton, pero honestamente leer sobre su fuente fue un poco abrumador.Multi-State Toggle Button

¿Hay alguna manera de hacer un botón de alternar entre tres estados utilizando solo un selector xml o algo así, o quizás otro método en el que no haya pensado? Estoy más bien perdido en cómo hacer esto.

Respuesta

10

Definitivamente puede definir un selector para usar como fondo que tiene tres entradas. La pregunta es qué atributos de botón puede usar para el selector. Puede tener dos atributos booleanos, por ejemplo, A y B, y definir el selector en términos de A, B y valor predeterminado. (A & & B satisfará A, por lo que más bien podrían ser considerados como A,! Un & & B y! Un & &! B). Se puede sobrecargar los atributos existentes (seleccionado, centrado, etc.) o, más elegantemente, defina sus propios atributos personalizados usando la receta descrita in this thread.

+0

Mirando el hilo que vinculó: entiendo el paso 1, pero tengo algunas preguntas sobre 2. Al crear una nueva vista, ¿sería mejor extender View, Button u otra cosa? ¿Y hay otros métodos que debería sobrecargar además de los constructores y onCreateDrawableState()? Mis disculpas si estas son básicas, esta es mi primera aplicación real. – Melde

+0

¡No importa, lo tengo funcionando! Gracias por el empuje en la dirección correcta, lo aprecio. – Melde

+0

@moonfire es su código propietario? También estoy tratando de crear un botón de palanca tri-estado, y me gustaría ver algunas otras soluciones para entender cómo hacerlo. – JohnMetta

18

he implementado un botón de múltiples estados de conmutación, el código fuente está here

Esto es como se ve:

enter image description here

Y es muy fácil de usar:

<org.honorato.multistatetogglebutton.MultiStateToggleButton 
    android:id="@+id/mstb_multi_id" 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:layout_marginTop="10dip" 
    mstb:values="@array/planets_array" /> 

En su actividad:

MultiStateToggleButton button2 = (MultiStateToggleButton) this.findViewById(R.id.mstb_multi_id); 
button2.setOnValueChangedListener(new ToggleButton.OnValueChangedListener() { 
    @Override 
    public void onValueChanged(int value) { 
     Log.d(TAG, "Value: " + value); 
    } 
}); 
+0

Gracias, lo he probado y funciona bien;) –

+0

¿cómo lo personalizaste como en la imagen? En sus documentos, no mencionó ningún tipo de minimización. – Choletski

+0

Esa es una versión anterior, intenta buscar confirmaciones más antiguas. Pero básicamente tendrás que modificar los fondos arrastrables del fondo. – jlhonora

10

Puede crear un ImageButton personalizado para lograr esto, necesita 3 imágenes diferentes en este caso. También puede agregar más estados si lo desea.

public class FlashButton extends ImageButton { 

    public enum FlashEnum { 
     AUTOMATIC, ON, OFF 
    } 

    public interface FlashListener { 
     void onAutomatic(); 
     void onOn(); 
     void onOff(); 
    } 

    private FlashEnum mState; 
    private FlashListener mFlashListener; 

    public FlashButton(Context context, AttributeSet attrs) { 
     super(context, attrs); 

     //Sets initial state 
     setState(FlashEnum.AUTOMATIC); 
    } 


    @Override 
    public boolean performClick() { 
     super.performClick(); 
     int next = ((mState.ordinal() + 1) % FlashEnum.values().length); 
     setState(FlashEnum.values()[next]); 
     performFlashClick(); 
     return true; 
    } 


    private void performFlashClick() { 
     if(mFlashListener == null)return; 
     switch (mState) { 
      case AUTOMATIC: 
       mFlashListener.onAutomatic(); 
       break; 
      case ON: 
       mFlashListener.onOn(); 
       break; 
      case OFF: 
       mFlashListener.onOff(); 
       break; 
     } 
    } 

    private void createDrawableState() { 
     switch (mState) { 
      case AUTOMATIC: 
       setImageResource(R.drawable.ic_flash_auto); 
       break; 
      case ON: 
       setImageResource(R.drawable.ic_flash_on); 
       break; 
      case OFF: 
       setImageResource(R.drawable.ic_flash_off); 
       break; 
     } 
    } 


    public FlashEnum getState() { 
     return mState; 
    } 

    public void setState(FlashEnum state) { 
     if(state == null)return; 
     this.mState = state; 
     createDrawableState(); 

    } 

    public FlashListener getFlashListener() { 
     return mFlashListener; 
    } 

    public void setFlashListener(FlashListener flashListener) { 
     this.mFlashListener = flashListener; 
    } 

} 
+0

Estás haciendo perezosos a la gente;) – yajnesh

2

¿Por qué no utilizar RadioGroup y radios de estilo en el interior?

<RadioGroup 
    android:layout_width="match_parent" 
    android:layout_height="wrap_content" 
    android:orientation="horizontal"> 

    <RadioButton 
     android:layout_width="match_parent" 
     android:layout_weight="1" 
     android:layout_height="wrap_content" 
     android:background="@drawable/your_drawable_selector" 
     android:button="@android:color/transparent" 
     android:gravity="center_horizontal" //center text 
     android:text="text" 
     /> 
...