Android: how do I setEnabled(true) on a CardView in onResume?

廉价感情. 提交于 2020-01-07 02:48:14

问题


I have a RecyclerView list with CardViews. I added the following code below to launch an activity (ActActivity) that allows the user to edit the CardView. The setEnabled(false) code is used to keep multiple instances of the activity from opening if the user clicks multiple times in rapid succession on the CardView. I only want one instance of the activity to be open at one time so that the user is only editing the single CardView that they clicked on.

My problem is that when I add the onResume() section to re-set setEnabled() to "true" the app crashes. When I remove the onResume() section then the setEnabled(false) code works correctly by not allowing multiple instances of the activity to open, but the problem is that any doubleclicks on the CardView disable a future single-click to correctly launch the ActActivity.

What am I missing here?

MainActivity.java

public class MainActivity extends AppCompatActivity implements
    RecyclerItemClickListener {

    lvContact = (RecyclerView) findViewById(R.id.lvContact);
    assert lvContact != null;
    lvContact.setHasFixedSize(true);

    contactListAdapter = new ContactListAdapter(this);
    contactListAdapter.setOnItemClickListener(this);

    LinearLayoutManager layoutManager = new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false);
    lvContact.setLayoutManager(layoutManager);
    lvContact.setAdapter(contactListAdapter);  
...
@Override
public void onItemClick(int position, View view) {
    CardView c = (CardView) view;
    c.setEnabled(false);
    ActActivity.start(this, contactListAdapter.getItem(position));
}

...
Override
protected void onResume() {
    super.onResume();

    CardView cardView1 = (CardView) findViewById(R.id.singlecard_view1);
    cardView1.setEnabled(true);
}

xml file for the RecyclerView:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#FFFFFF"
tools:context="com.v050.MainActivity">

<include
    android:id="@+id/toolbar"
    layout="@layout/toolbar" >
</include>

<LinearLayout
    android:id="@+id/todoListLayout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_below="@+id/toolbar"
    android:layout_above="@+id/s4"
    android:background="@color/background4main"
    android:layout_marginTop="6dp"
    android:layout_marginStart="6dp"
    android:layout_marginLeft="6dp"
    android:layout_marginEnd="6dp"
    android:layout_marginRight="6dp"
    android:layout_marginBottom="6dp"
    android:orientation="vertical"  >

<android.support.v7.widget.RecyclerView
    android:id="@+id/lvContact"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:scrollbars="vertical"  />

</LinearLayout>

<TextView
    android:id="@+id/s4"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true"
    android:gravity="center"
    android:textStyle="bold"
    android:textColor="#FFFFFF"
    android:background="@color/colorPrimary"
    android:textAppearance="?android:attr/textAppearanceMedium"
    android:paddingTop="15dp"
    android:paddingBottom="15dp"
    android:clickable="true"  />

</RelativeLayout>

xml file for the CardView:

<android.support.v7.widget.CardView
    xmlns:card_view="http://schemas.android.com/apk/res-auto"
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/singlecard_view1"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginTop="4dp"
    android:layout_marginBottom="4dp"
    card_view:cardBackgroundColor="@android:color/white"
    card_view:cardCornerRadius="6dp"
    card_view:cardElevation="4dp"
    android:foreground="?android:attr/selectableItemBackground"
    android:longClickable="true"  >

Logcat output does not like the "cardView1.setEnabled(true)" line in the onResume() section:

11-01 23:22:54.814 1399-1399/com.example.v50 E/AndroidRuntime: FATAL EXCEPTION: main
                                                                   java.lang.RuntimeException: Unable to resume activity {com.example.v50/com.v050.MainActivity}: java.lang.NullPointerException
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2575)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2603)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2089)
at android.app.ActivityThread.access$600(ActivityThread.java:130)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1195)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:4745)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:511)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:786)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.NullPointerException
at com.v050.MainActivity.onResume(MainActivity.java:279)
at android.app.Instrumentation.callActivityOnResume(Instrumentation.java:1184)
at android.app.Activity.performResume(Activity.java:5082)
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2565)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2603) 
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2089) 
at android.app.ActivityThread.access$600(ActivityThread.java:130) 
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1195) 
at android.os.Handler.dispatchMessage(Handler.java:99) 
at android.os.Looper.loop(Looper.java:137) 
at android.app.ActivityThread.main(ActivityThread.java:4745) 
at java.lang.reflect.Method.invokeNative(Native Method) 
at java.lang.reflect.Method.invoke(Method.java:511) 
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:786) 
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553) 
at dalvik.system.NativeStart.main(Native Method) 

One proposed answer that works is:

...     
@Override
public void onItemClick(int position, final View view) {
    view.setEnabled(false);
    ActActivity.start(this, contactListAdapter.getItem(position));
    view.post(new Runnable() {
        @Override
        public void run() {
            view.setEnabled(true);
        }
    });
 }

How does this compare to answers that use onResume?


回答1:


Here is problem .....

CardView is in the recycle view and you are trying from the main layout instead of item layout ....

here is your solution for your problem....

create cardview variable as global .......

private CardView cardview;

use it when the item clicked ......

@Override
public void onItemClick(int position, View view) {
    cardview = (CardView) view;
    cardview.setEnabled(false);
    ActActivity.start(this, contactListAdapter.getItem(position));
}

Note:- Always try to declare global variable which have use in many methods .....

EDIT:- try this for the first run in your onResume....

and put condition onResume ....

 Override
    protected void onResume() {
        super.onResume();
        if(cardview!=null){
        cardview.setEnabled(true);

     }

above problem will solve your First Run problem ....




回答2:


You can initialise the card view in onCreate of activity instead of onResume.

    @Override
    protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    CardView cardView1 = (CardView)findViewById(R.id.singlecard_view1);
    } 

    Override
    protected void onResume() {
    super.onResume();
    cardView1.setEnabled(true);
    }



回答3:


Have you initialized the RecyclerView contact list before following code:

CardView cardView1 = (CardView)findViewById(R.id.singlecard_view1);

If you haven't then the card view will not be created and findViewById(R.id.singlecard_view1); will return null.

Edited:
I think the view of the RecyclerView's items are not getting initialized untill activity is fully visible which cause findViewById(R.id.singlecard_view1) return null.

But as you have said you just want the edit activity to be started only once. You can achieve this by
-> adding android:launchMode="singleTask" for "ActActivity" in manifest file.
OR
->adding FLAG_ACTIVITY_CLEAR_TASK to Intent.



来源:https://stackoverflow.com/questions/40372223/android-how-do-i-setenabledtrue-on-a-cardview-in-onresume

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!