Benutzerdefiniertes Kontrollkästchen Bild Android

182

Gibt es eine einfache Möglichkeit, ein benutzerdefiniertes Bild für ein Kontrollkästchen zu verwenden? Ich möchte das "markierte" Verhalten von Google Mail duplizieren. Ich möchte also ein Kontrollkästchen haben, das, wenn es aktiviert ist, ein ausgefüllter Stern ist. Und wenn nicht markiert, ist ein leerer Stern. Muss ich eine Bildansicht verwenden und meine eigene Logik selbst erstellen?

Falmarri
quelle

Antworten:

128

Kontrollkästchen sind untergeordnete Elemente von Button. Sie können Ihrem Kontrollkästchen einfach ein Hintergrundbild mit mehreren Status geben, wie hier unter "Schaltflächenstil" beschrieben:

... und hier beispielhaft dargestellt :

Jean
quelle
26
Danke, ich habe hier genau das gefunden, was ich brauchte it-ride.blogspot.com/2010/04/…, aber ich hätte es auf Ihre Weise tun müssen, wenn ich ein echtes benutzerdefiniertes Bild haben wollte = P
Falmarri
2
Danke dir. Genau das, wonach ich gesucht habe - ich habe den ganzen Zustand herausgefunden, aber ich habe android: background anstelle von android: button eingestellt und stattdessen 2 Tasten erhalten. Jetzt funktioniert alles gut.
Artem
1
-1. Die folgende android:buttonLösung ist viel besser als die Verwendung von Hintergrundattributen!
Orabîg
8
@ Orabîg: Diese Ablehnung ist falsch. Die Frage ist perfekt beantwortet ("Benutzerdefiniertes Kontrollkästchen"). Die Tatsache, dass für diese bestimmte Sternschaltfläche eine Verknüpfung vorhanden ist, macht diese Antwort nicht ungültig.
Am
Während dies vielleicht ein alter Beitrag ist, möchte ich hinzufügen, dass Android Studio auch die android: button = "@ android: drawable / btn_star" -Methode verwendet
Angry 84
288

Erstellen Sie eine Auswahl für ein zeichnbares Kontrollkästchen:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
    <item android:drawable="@drawable/checkbox" 
          android:state_checked="false"/>
    <item android:drawable="@drawable/checkboxselected" 
          android:state_checked="true"/>
    <item android:drawable="@drawable/checkbox"/>    
</selector>

Stellen Sie sicher, dass Ihr Kontrollkästchen so ist android:button="@drawable/checkbox_selector"

<CheckBox
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:button="@drawable/checkbox_selector"
    android:text="CheckBox"
    android:textAppearance="?android:attr/textAppearanceLarge"
    android:textColor="@color/Black" />
Mohamed Hisham Ibn Hanifa
quelle
In welchem ​​Datensatz geben Sie diesen Selektor an? In der XML-Datei selbst, in der Sie auch die CheckBox angeben?
Tom Hammond
Tom: Erstellen Sie Ihre Auswahl in zeichnbaren Ordner und Kontrollkästchen in Layout-Ordner
Mohamed Hisham Ibn Hanifa
Ich musste "Button" für "Hintergrund" in der CheckBox
Francisco Corrales Morales
Zum Auffüllen siehe stackoverflow.com/questions/4037795/…
PiTheNumber
2
Ich habe mein Projekt auf Android X aktualisiert, danach konnte ich mein Kontrollkästchen nicht mehr anpassen, wie Sie vor API Level 21 gesagt haben, und Android: Button funktioniert nicht.
Misagh Aghakhani
44

Kopieren Sie die Datei btn_check.xml von android-sdk / platform / android - # / data / res / drawable in den Zeichenordner Ihres Projekts und ändern Sie die Bildzustände "Ein" und "Aus" in Ihre benutzerdefinierten Bilder.

Dann braucht deine XML nur noch android:button="@drawable/btn_check"

<CheckBox
    android:button="@drawable/btn_check"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:checked="true" />

Wenn Sie verschiedene Standard-Android-Symbole verwenden möchten, können Sie verwenden android:button="@android:drawable/..."

WOUNDEDStevenJones
quelle
2
Schlechter Rat. Symbole können von Version zu Version geändert werden und verschwinden möglicherweise überhaupt. Wenn Ihnen das Standardsymbol wirklich gefällt, können Sie es aus Quellen abrufen.
Korniltsev Anatoly
Wollen Sie damit sagen, dass es eine schlechte Idee ist, die Standardsymbole direkt über "@android: drawable / ..." zu referenzieren, oder dieser Vorgang vollständig?
WOUNDEDStevenJones
2
Beispiel: Wenn Sie auf Holo-Symbole verweisen, stürzt Ihre App auf Geräten vor der Wabe ab. Es ist wirklich schwierig, solche Probleme zu warten und zu beheben. Daher kopiere ich normalerweise nicht nur XML, sondern auch die Bilder, um hundertprozentig sicher zu sein, dass die Ressourcen gefunden werden. Dies ist auch sehr wichtig, um sicherzustellen, dass die Benutzeroberfläche auf jedem Gerät gleich aussieht.
Korniltsev Anatoly
15

res / drawable / day_selector.xml

    <?xml version="1.0" encoding="utf-8"?>
    <selector xmlns:android="http://schemas.android.com/apk/res/android" >
        <item android:drawable="@drawable/dayselectionunselected"
              android:state_checked="false"/>
        <item android:drawable="@drawable/daysselectionselected"
              android:state_checked="true"/>
        <item android:drawable="@drawable/dayselectionunselected"/>
    </selector>

res / layout / my_layout.xml

<CheckBox
    android:id="@+id/check"
    android:layout_width="39dp"
    android:layout_height="39dp"
    android:background="@drawable/day_selector"
    android:button="@null"
    android:gravity="center"
    android:text="S"
    android:textColor="@color/black"
    android:textSize="12sp" />
Rahul
quelle
1
Einige Erklärungen würden neuen Benutzern helfen, zu verstehen, wie Ihr Code das Problem löst.
Brian Tompsett - 莱恩 莱恩
7

Wenn Sie Android Open Source Code haben, finden Sie die Stildefinition unter:
src / frameworks / base / core / res / res / values

<style name="Widget.CompoundButton.CheckBox">
    <item name="android:background">
        @android:drawable/btn_check_label_background
    </item>
    <item name="android:button">
        ?android:attr/listChoiceIndicatorMultiple
    </item>
</style>
Achellies
quelle
4

Versuch es -

package com;

import android.content.Context;
import android.content.res.TypedArray;
import android.util.AttributeSet;
import android.view.View;
import android.widget.ImageView;



public class CheckBoxImageView extends ImageView implements View.OnClickListener {
    boolean checked;
    int defImageRes;
    int checkedImageRes;
    OnCheckedChangeListener onCheckedChangeListener;

    public CheckBoxImageView(Context context, AttributeSet attr, int defStyle) {
        super(context, attr, defStyle);
        init(attr, defStyle);
    }

    public CheckBoxImageView(Context context, AttributeSet attr) {
        super(context, attr);
        init(attr, -1);
    }

    public CheckBoxImageView(Context context) {
        super(context);
    }

    public boolean isChecked() {
        return checked;
    }

    public void setChecked(boolean checked) {
        this.checked = checked;
        setImageResource(checked ? checkedImageRes : defImageRes);
    }

    private void init(AttributeSet attributeSet, int defStyle) {
        TypedArray a = null;
        if (defStyle != -1)
            a = getContext().obtainStyledAttributes(attributeSet, R.styleable.CheckBoxImageView, defStyle, 0);
        else
            a = getContext().obtainStyledAttributes(attributeSet, R.styleable.CheckBoxImageView);
        defImageRes = a.getResourceId(0, 0);
        checkedImageRes = a.getResourceId(1, 0);
        checked = a.getBoolean(2, false);
        a.recycle();
        setImageResource(checked ? checkedImageRes : defImageRes);
        setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        checked = !checked;
        setImageResource(checked ? checkedImageRes : defImageRes);
        onCheckedChangeListener.onCheckedChanged(this, checked);
    }

    public void setOnCheckedChangeListener(OnCheckedChangeListener onCheckedChangeListener) {
        this.onCheckedChangeListener = onCheckedChangeListener;
    }

    public static interface OnCheckedChangeListener {
        void onCheckedChanged(View buttonView, boolean isChecked);
    }
}

Fügen Sie dieses Attribut hinzu -

<declare-styleable name="CheckBoxImageView">
        <attr name="default_img" format="integer"/>
        <attr name="checked_img" format="integer"/>
        <attr name="checked" format="boolean"/>
</declare-styleable>

Verwenden Sie wie -

 <com.adonta.ziva.consumer.wrapper.CheckBoxImageView
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:id="@+id/checkBox"
        android:layout_width="40dp"
        android:layout_height="40dp"
        android:layout_alignParentRight="true"
        android:layout_centerVertical="true"
        android:clickable="true"
        android:padding="5dp"
        app:checked_img="@drawable/check_box_checked"
        app:default_img="@drawable/check_box" />

Es wird alle Ihre Porbleme reparieren.

Neo
quelle
Es fehlen die onSaveInstanceState()und onRestoreInstanceState()Methoden, ich denke, der überprüfte Zustand würde bei der Rotation verloren gehen
EpicPandaForce
2

Eine andere Option ist die Verwendung eines ToggleButton mit Null-Hintergrund und einer benutzerdefinierten Schaltfläche.

Unten sehen Sie ein Beispiel, das auch eine Auswahl für die Textfarbe enthält.

<ToggleButton
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:button="@drawable/toggle_selector"
    android:background="@null"
    android:paddingLeft="10dp"
    android:layout_centerHorizontal="true"
    android:gravity="center"
    android:textColor="@drawable/toggle_text"
    android:textOn="My on state"
    android:textOff="My off state" />

toggle_selector.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item
        android:state_checked="true"
        android:drawable="@drawable/state_on" />

    <item
        android:drawable="@drawable/state_off" />

</selector>

toggle_text.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item
        android:state_checked="true"
        android:color="@color/app_color" />

    <item
        android:color="@android:color/darker_gray" />

</selector>
Androidevil
quelle
2

Wenn Sie benutzerdefinierte Adapter als android:focusable="false"und android:focusableInTouchMode="false"verwenden, um Listenelemente während der Verwendung des Kontrollkästchens anklickbar zu machen.

<CheckBox
        android:id="@+id/checkbox_fav"
        android:focusable="false"
        android:focusableInTouchMode="false"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:button="@drawable/checkbox_layout"/>

In drawable> checkbox_layout.xml

<selector xmlns:android="http://schemas.android.com/apk/res/android" >
    <item android:drawable="@drawable/uncked_checkbox"
        android:state_checked="false"/>
    <item android:drawable="@drawable/selected_checkbox"
        android:state_checked="true"/>
    <item android:drawable="@drawable/uncked_checkbox"/>
</selector>
Chitransh Goud
quelle
1

Wenn Sie androidx.appcompat: appcompat verwenden und möchten, dass ein benutzerdefiniertes Zeichen (vom Typ selectorwith android:state_checked) neben neuen Plattformversionen auch auf alten Plattformversionen funktioniert, müssen Sie verwenden

    <CheckBox
        app:buttonCompat="@drawable/..."

anstatt

    <CheckBox
        android:button="@drawable/..."
Enselic
quelle
1

Basierend auf den Antworten von Enselic und Rahul.

Es funktioniert bei mir (vor und nach API 21):

<CheckBox
    android:id="@+id/checkbox"
    android:layout_width="40dp"
    android:layout_height="40dp"
    android:text=""
    android:gravity="center"

    android:background="@drawable/checkbox_selector"
    android:button="@null"
    app:buttonCompat="@null" />
alexrnov
quelle