ConcurrentModificationException Android AsyncTask

时间:2016-06-22 20:23:23

标签: android android-asynctask

在SearchView的OnQueryTextChange中调用updateUserSection方法。当我快速输入SearchView时,我得到一个ConcurrentModificationException(如果我慢慢输入,它会起作用)。我不能告诉导致这个问题的原因。

public void updateUserSection(String text){
    relevantUsers.clear();

    for(String key: allUsers.keySet()) {
        if ((key.toLowerCase().contains(text.toLowerCase()))) {
            relevantUsers.put(key, allUsers.get(key));
        }
    }

    // instance is a private reference to this AddTrailsAct, probably doesn't matter
    instance.generateButtons();
}

private synchronized void generateButtons() {

    usersLayout.removeAllViewsInLayout();

    // make the first row
    currentRow = new LinearLayout(getApplicationContext());

    // make it pretty
    makePretty(currentRow);

    // add the first row
    usersLayout.addView(currentRow);

    // limits 3 buttons per row
    rowIndex = 0;

    // iterate through relevantUsers and try to find pictures
    (new SetButtonTask(relevantUsers)).execute();
}

private class SetButtonTask extends AsyncTask<Void, Void, Void> {

    private HashMap<String, String> userList;
    private HashMap<String, Bitmap> nameToBitmap = new HashMap<String, Bitmap>();

    public SetButtonTask(HashMap<String, String> userList) {
        this.userList = userList;
    }

    @Override
    protected Void doInBackground(Void... v) {

        for (String name: userList.keySet()) {
            putToBitmap(name, userList.get(name));
        }

        return null;
    }

    @Override
    protected void onPostExecute(Void v) {

        // THE RUNTIME ERROR POINTS TO THE LINE BELOW
        for (String name: nameToBitmap.keySet()) {
            instance.addToUsersLayout(nameToBitmap.get(name), name);
        }
    }

    private void putToBitmap(String name, String id) {
        try {
            nameToBitmap.put(name, Bitmap.createScaledBitmap(
                    BitmapFactory.decodeStream((new URL("https://graph.facebook.com/" +
                            id +
                            "/picture?type=large")).openConnection().getInputStream()),
                    200,
                    200,
                    true));
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }
}

// add button to the usersLayout
private synchronized void addToUsersLayout(final Bitmap profPicBitmap, final String name) {

    runOnUiThread(new Runnable() {
        @Override
        public void run() {

            numTasks++;

            Log.d("myTag","the UiThread has " + numTasks + " threads running");
            // the button we'll be building
            final ImageButton b = new ImageButton(getApplicationContext());

            b.setImageBitmap(profPicBitmap);

            // touch animation
            b.setOnTouchListener(new View.OnTouchListener() {
                @Override
                public boolean onTouch(View v, MotionEvent event) {
                    // set filter when pressed
                    if (event.getAction() == MotionEvent.ACTION_DOWN) {
                        b.setColorFilter(new
                                PorterDuffColorFilter(getResources().getColor(R.color.skyBlue),
                                PorterDuff.Mode.MULTIPLY));
                    }

                    // handle "click"
                    if (event.getAction() == MotionEvent.ACTION_UP) {
                        Log.d("myTag", "imageButton pressed");
                        // add the trail
                        ((Project_18) getApplication()).getMe().addTrail(fb, relevantUsers.get(name));
                    }

                    // remove filter on release/cancel
                    if (event.getAction() == MotionEvent.ACTION_UP ||
                            event.getAction() == MotionEvent.ACTION_CANCEL) {
                        b.clearColorFilter();
                    }
                    return true;
                }
            });

            // contains button and name of the user
            LinearLayout buttonLayout = new LinearLayout(getApplicationContext());

            // make button look good and add to buttonLayout
            makePretty(b, name, buttonLayout);

            // add to buttonMap
            buttonMap.put(name, buttonLayout);

            // add buttonLayout to row
            currentRow.addView(buttonLayout);

            // row index handling
            if (rowIndex < 2) {
                rowIndex ++;
            } else {

                // reset index
                rowIndex = 0;

                // make new row
                currentRow = new LinearLayout(getApplicationContext());
                makePretty(currentRow);

                // add new row to the layout
                usersLayout.addView(currentRow);
            }
            numTasks--;
        }
    });
}

0 个答案:

没有答案