简体   繁体   中英

Firebase getting ID for specific node to delete/update

first time using Firebase and pretty new to android studio, i'm trying to make a schedule app where a user can create many schedules and it would be associated to their account.

At the moment a user can create an account, create a schedule (i just have 2 fields for this, will add the rest once i get the issue sorted) and also have multiple schedules.

I would like to be able to update/delete a schedule of a user but i'm struggling to get the ID of the specific schedule node in which I need to delete.


This is what i have in Firebase with a single user and 2 schedules

火力地堡模型

EDITED FROM HERE

  • I added a toast when i long click a list item which displays the corresponding scheduleId of that schedule. keep in mind this is to help so i can just long click and show if the item displays the proper scheduleId.

Part of ScheduleActivity.java

What the problem is

  • I have a listView with all the schedules that has a listener

    • In the listener I have this line which gets the ID, but the issue is since its on the listener, i wont get the ID of the schedule until i click the list item and view the details, then Im only able to view the scheduleId, otherwise i get a NULL value.

    scheduleId = scheduleList.get(position).getScheduleId();


public class ScheduleActivity extends AppCompatActivity implements View.OnClickListener {

    private List<Schedule> scheduleList;
    private List<String> scheduleIdList;
    private DatabaseReference scheduleReference;
    private String userId;
    public static final String SCHEDULE_TITLE = "title";
    public static final String SCHEDULE_DESCRIPTION = "description";
    private String scheduleId;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_schedule);

        getSupportActionBar().hide();

        scheduleList = new ArrayList<>();
        scheduleIdList = new ArrayList<>();

        userId = FirebaseAuth.getInstance().getCurrentUser().getUid();


        scheduleReference = FirebaseDatabase.getInstance().getReference(DBStrings.DB_SCHEDULES);

        registerForContextMenu(scheduleListView);

       // when a user clicks any of list items
        scheduleListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> adapterView, View view, int position, long id) {
                Schedule schedule = scheduleList.get(position);

                // this gets the id but the issue is i need to first click the list item then ill get the correct id, otherwise i get a NPE because i haven't accessed the list item yet
                // need to figure out how to implement this in the onStart() method so i can get the scheduleId beforehand
                scheduleId = scheduleList.get(position).getScheduleId();

                // intent that takes me to the activity to view the schdule details
               Intent viewSchedule = new Intent(ScheduleActivity.this, ViewSchedule.class);
                viewSchedule.putExtra(SCHEDULE_TITLE, schedule.getTitle());
                viewSchedule.putExtra(SCHEDULE_DESCRIPTION, schedule.getDescription());

                startActivity(viewSchedule);
            }

            }
        });
    }

    // when a user long clicks a list item, brings up menu with option to edit/delete
// Also display a toast with scheduleID so i can see if the proper id is being retrieved
    @Override
    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) {
        super.onCreateContextMenu(menu, v, menuInfo);

        Toast.makeText(ScheduleActivity.this, "id: " + scheduleId, Toast.LENGTH_SHORT).show();
        getMenuInflater().inflate(R.menu.schedule_menu, menu);
    }


    // switch statement for delete/ redirect to edit activity that i left out


    // load schedule data into list view
    @Override
    protected void onStart() {
        super.onStart();

        scheduleReference.child(userId).addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(@NonNull DataSnapshot snapshot) {

                scheduleList.clear();
                scheduleIdList.clear();

                for(DataSnapshot dataSnapshot : snapshot.getChildren()) {
                    Schedule schedule = dataSnapshot.getValue(Schedule.class);

                    // add schedules to list to show in list view
                    scheduleList.add(schedule);

                    // Add all the ids of schedules in a list, i used this in my scheduleListView.setOnItemListener to grab the scheduleId.
                    scheduleIdList.add(schedule.getScheduleId());
                }

                System.out.println("id list: " + scheduleIdList);

                ScheduleListAdapter adapter = new ScheduleListAdapter(ScheduleActivity.this, scheduleList);
                scheduleListView.setAdapter(adapter);
            }

            @Override
            public void onCancelled(@NonNull DatabaseError error) {
                System.out.println("ERROR: " + error.toException());
            }
        });
    }

    private void deleteSchedule(String scheduleId) {

// At the moment i can only delete a item if i first view it by clicking, then i need to go back and it allows me to delete it, this is obviously because my listview listener issue (It does not let me delete without first clicking the item to view/access it)        scheduleReference.child(userId).child(scheduleId).removeValue();

        Toast.makeText(ScheduleActivity.this, "Schedule " + scheduleId + " was deleted!", Toast.LENGTH_LONG).show();


    }

}


List view of schedules

列表显示


The issue is in the scheduleListView.setOnItemClickListener , i need to find a way to grab the id maybe in onStart method or somewhere eother than the listener, but since I do not have access to the position like i did here, i am struggling to implement this.

public void onItemClick(AdapterView<?> adapterView, View view, int position, long id) {
        Schedule schedule = scheduleList.get(position);

        // Talking about this <position>
        scheduleId = scheduleList.get(position).getScheduleId();
}


Images to explain it better当我尝试长按而不访问实际列表项时为空字符串

我在这里访问列表项,然后返回到上一个屏幕

然后我得到 scheduleId 很好

I hope it makes sense, i would need to access each list item then go back to be able to delete a specific one.

private void deleteSchedule(String scheduleId) {
    String userId = FirebaseAuth.getInstance().getCurrentUser().getUid();
    scheduleReference.child(userId).child(scheduleId).removeValue();
    Toast.makeText(ScheduleActivity.this, "Schedule " + scheduleId + " was deleted!", Toast.LENGTH_LONG).show();
}

You have to get your scheduleId when the user clicks on delete schedule Only Then you can get the original path of the schedule and can remove that schedule

If you don't know how to get a specific schedule id then I can help you with that too. but you need recyclerview for that. you can simply achieve that with recyclerview and interface

Updated Answer for updated Question Maybe this can help you. I have added LongClick Listner Here you can do the same as well. I don't have exp with listview but my logic says it will work in your case. also, try to learn recyclerview. because recyclerview is needed for every android developer.

scheduleListView.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
    @Override
    public boolean onItemLongClick(AdapterView<?> adapterView, View view, int position, long id) {
        PopupMenu popup = new PopupMenu(Test.this, view);
        popup.getMenuInflater().inflate(R.menu.schedule_menu, popup.getMenu());
        popup.setOnMenuItemClickListener(item -> {
// You can compare here your menu id and perform action as id  like item.getItemId() == R.id.delete 
// also get Item by position like scheduleListView.getAdapter().getItem(position);
            Toast.makeText(Test.this,"You Clicked : " + item.getTitle(), Toast.LENGTH_SHORT).show();
            return true;
        });
        popup.show();//showing popup menu
        return false;
    }
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM