如何修复有关expandableList的Android冻结框架问题?

时间:2019-04-01 12:59:28

标签: android performance frozen

首先,我已经审查了很多问题,但是找不到这个问题的明确答案。

我借助 Retrofit2 和Gson从服务器获取JSON数据。我的列表中有可扩展项,因此我使用下面添加的 ExpandableLayout 库进行列表。

问题是,当JSON太多时,行数增加了,我得到了大约1分钟的列表屏幕。实际上,有时我无法在与我测试过相同型号的其他设备上完成渲染事件,并且屏幕冻结。我无法添加错误代码,因为我无法在此处调试远程设备。

在Firebase性能数据中,我得到了100%冻结的帧反馈。没有崩溃数据。

我的列表行是这样的:

https://github.com/iammert/ExpandableLayout

如果没有按钮和下面的 imageview ,我可以使用 textview 很好地完成此操作,该视图仅包含名称,但是视图会增加渲染时间,有时需要超过1分钟。

public class MenuActivity extends AppCompatActivity {

private List<MenuItemModel.Item> items = new ArrayList<>();

ExpandableLayout sectionLinearLayout;

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

    ...

    }
    EditText editText = findViewById(R.id.edittext);
    sectionLinearLayout = findViewById(R.id.el);

    sectionLinearLayout.setRenderer(new ExpandableLayout.Renderer<MainItem, Modifier>() {
        @Override
        public void renderParent(View view, MainItem model, boolean isExpanded, int parentPosition, Section section) {
            LinearLayout layout = view.findViewById(R.id.layout_parent);
            layout.setBackgroundColor(Color.WHITE);
            TextView parentText = view.findViewById(R.id.tvParent);
            parentText.setText(model.name);
            final Button currentButton = view.findViewById(R.id.action_button_parent);
            LinearLayout buttonMenu = view.findViewById(R.id.button_menu_parent);

            // Set icons according to availability
            List<Links> linksList = model.item.getLinks();
            List<String> appList = new ArrayList<>();
            for (Links link: linksList) {
                appList.add(link.getApp());
            }
            Map<String,ImageView> iconMap = new HashMap<>();
            final ImageView uber_icon = view.findViewById(R.id.uber_icon);
            uber_icon.setTag("uber");
            iconMap.put((String) uber_icon.getTag(),uber_icon);
            final ImageView dd_icon = view.findViewById(R.id.dd_icon);
            dd_icon.setTag("doordash");
            iconMap.put((String) dd_icon.getTag(), dd_icon);

            for (String app:appList){
                for(Map.Entry m:iconMap.entrySet()) {
                    if (m.getKey().equals(app)) {
                        ImageView iconview = (ImageView) m.getValue();
                        iconview.setVisibility(VISIBLE);
                    }
                }
            }

            // Check statuses and set actionbutton
            if (model.status == 1){
                currentButton.setBackgroundResource(R.drawable.available);
                currentButton.setTag(R.drawable.available);
            } else if (model.status == 2){
                currentButton.setBackgroundResource(R.drawable.sold_out_red);
                currentButton.setTag(R.drawable.sold_out_red);
            } else {
                currentButton.setBackgroundResource(R.drawable.mixed_button);
                currentButton.setTag(R.drawable.mixed_button);
            }

            parentText.setTextColor(getResources().getColor(R.color.black));
            parentText.setTextSize(20);

            if (!(section.children.size() == 0)) {
                view.findViewById(R.id.arrow).setBackgroundResource(isExpanded ? R.drawable.arrow_down : R.drawable.arrow_right);
            }

            currentButton.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    openParentButtonMenu(currentButton, view, linksList);
                }
            });

            layout.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    sectionLinearLayout.checkexpand(section);
                    closeActionButtonMenu(buttonMenu,currentButton);
                }
            });
        }

        @Override
        public void renderChild(View view, Modifier model, int parentPosition, int childPosition) {
            LinearLayout layout = view.findViewById(R.id.layout_child);
            int color = childPosition%2;
            if (color == 0){
                layout.setBackgroundColor(getResources().getColor(R.color.colorGrayLighter));
            } else {
                layout.setBackgroundColor(Color.WHITE);
            }

            TextView childText = view.findViewById(R.id.tvChild);
            childText.setText(model.name);
            childText.setTextColor(getResources().getColor(R.color.black));
            childText.setTextSize(18);
            final Button currentButton = view.findViewById(R.id.action_button_child);
            LinearLayout buttonMenu = view.findViewById(R.id.button_menu_child);

            // Set icons according to availability
            List<Links> linksList = model.subItem.getLinks();
            List<String> appList = new ArrayList<>();
            for (Links link: linksList) {
                appList.add(link.getApp());
            }
            Map<String,ImageView> iconMap = new HashMap<>();
            final ImageView uber_icon = view.findViewById(R.id.uber_icon);
            uber_icon.setTag("uber");
            iconMap.put((String) uber_icon.getTag(),uber_icon);
            final ImageView dd_icon = view.findViewById(R.id.doordash_icon);
            dd_icon.setTag("doordash");
            iconMap.put((String) dd_icon.getTag(), dd_icon);
            for (String app:appList){
                for(Map.Entry m:iconMap.entrySet()) {
                    if (m.getKey().equals(app)) {
                        ImageView iconview = (ImageView) m.getValue();
                        iconview.setVisibility(VISIBLE);
                    }
                }
            }

            // Check statuses and set actionbutton
            if (model.status == 1){
                currentButton.setBackgroundResource(R.drawable.available);
                currentButton.setTag(R.drawable.available);
            } else if (model.status == 2){
                currentButton.setBackgroundResource(R.drawable.sold_out_red);
                currentButton.setTag(R.drawable.sold_out_red);
            } else {
                currentButton.setBackgroundResource(R.drawable.mixed_button);
                currentButton.setTag(R.drawable.mixed_button);
            }

            currentButton.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    openChildButtonMenu(currentButton, view, linksList);
                }
            });
            layout.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    closeActionButtonMenu(buttonMenu,currentButton);
                }
            });
        }
    });

    ...

    getMenuItems();
}

...

private void getMenuItems() {
    progressDialog = createProgressDialog(MenuActivity.this);

    String token = "Token " + PreferenceManager.getToken(MenuActivity.this);
    int companyID = PreferenceManager.getCompanyID(MenuActivity.this);
    APIGetMenu service = SettingsService.getRetrofitInstanceForSettings().create(APIGetMenu.class);

    service.getMenu(token,companyID)
            .subscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new Observer<MenuItemModel>() {
                @Override
                public void onSubscribe(Disposable d) {

                }

                @Override
                public void onNext(MenuItemModel menuItemModel) {
                   items = menuItemModel.getItems();

                }

                @Override
                public void onError(Throwable e) {
                    progressDialog.dismiss();
                    Toast.makeText(MenuActivity.this, "Something went wrong...Please try again ", Toast.LENGTH_LONG).show();
                    Log.i("MenuActivity", String.valueOf(e));
                }

                @Override
                public void onComplete() {
                    Log.i("MenuActivity", "GET is Success");
                    for (MenuItemModel.Item item:items){
                        List<MenuItemModel.Item.SubItem> subItems = item.getSubItems();
                        sectionLinearLayout.addSection(getSection(item,subItems));
                    }
                    progressDialog.dismiss();                      
}

private ProgressDialog createProgressDialog(Context mContext) {
    ...
}

...

public void closeActionButtonMenu(LinearLayout buttonMenu, Button actionButton){
    if (buttonMenu != null){
        if (buttonMenu.getVisibility() == VISIBLE){
            buttonMenu.setVisibility(GONE);
            actionButton.setVisibility(VISIBLE);
        }
    }
}

public void openParentButtonMenu(Button currentButton, View view, List<Links> links){
    currentButton.setVisibility(GONE);
    LinearLayout menu = view.findViewById(R.id.button_menu_parent);
    final Button available = view.findViewById(R.id.action_button1_parent);
    final Button soldOut = view.findViewById(R.id.action_button2_parent);

    Object tag = currentButton.getTag();
    int backgroundID = R.drawable.available;
    int backgroundID2 = R.drawable.mixed_button;

    if ( (Integer) tag == backgroundID) {
        available.setBackgroundResource(R.drawable.available_white);
        available.setTag(R.drawable.available_white);
        soldOut.setBackgroundResource(R.drawable.sold_out_red);
        soldOut.setTag(R.drawable.sold_out_red);
    } else if ((Integer) tag == backgroundID2) {
        available.setBackgroundResource(R.drawable.available);
        available.setTag(R.drawable.available);
        soldOut.setBackgroundResource(R.drawable.sold_out_red);
        soldOut.setTag(R.drawable.sold_out_red);
    } else {
        available.setBackgroundResource(R.drawable.available);
        available.setTag(R.drawable.available);
        soldOut.setBackgroundResource(R.drawable.sold_out_white);
        soldOut.setTag(R.drawable.sold_out_white);
    }

    menu.setVisibility(VISIBLE);

    available.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            currentButton.setTag(R.drawable.available);
            closeButtonMenu(available, currentButton, menu, links);
        }
    });

    soldOut.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            currentButton.setTag(R.drawable.sold_out_red);
            closeButtonMenu(soldOut, currentButton, menu, links);
        }
    });


}

public void openChildButtonMenu(Button currentButton, View view, List<Links> links){
    currentButton.setVisibility(GONE);
    LinearLayout menu = view.findViewById(R.id.button_menu_child);
    final Button available = view.findViewById(R.id.action_button1_child);
    final Button soldOut = view.findViewById(R.id.action_button2_child);

    Object tag = currentButton.getTag();
    int backgroundID = R.drawable.available;
    int backgroundID2 = R.drawable.mixed_button;

    if ( (Integer) tag == backgroundID) {
        available.setBackgroundResource(R.drawable.available_white);
        available.setTag(R.drawable.available_white);
        soldOut.setBackgroundResource(R.drawable.sold_out_red);
        soldOut.setTag(R.drawable.sold_out_red);
    } else if ((Integer) tag == backgroundID2) {
        available.setBackgroundResource(R.drawable.available);
        available.setTag(R.drawable.available);
        soldOut.setBackgroundResource(R.drawable.sold_out_red);
        soldOut.setTag(R.drawable.sold_out_red);
    } else {
        available.setBackgroundResource(R.drawable.available);
        available.setTag(R.drawable.available);
        soldOut.setBackgroundResource(R.drawable.sold_out_white);
        soldOut.setTag(R.drawable.sold_out_white);
    }

    menu.setVisibility(VISIBLE);

    available.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            currentButton.setTag(R.drawable.available);
            closeButtonMenu(available, currentButton, menu, links);
        }
    });
    soldOut.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            currentButton.setTag(R.drawable.sold_out_red);
            closeButtonMenu(soldOut, currentButton, menu, links);
        }
    });
}

public void closeButtonMenu(Button selectedButton, Button currentButton, LinearLayout menu, List<Links> links) {
    menu.setVisibility(GONE);
    Object tag = selectedButton.getTag();
    int backgroundID1 = R.drawable.available;
    int backgroundID2 = R.drawable.available_white;
    int backgroundID3 = R.drawable.sold_out_white;
    int backgroundID4 = R.drawable.sold_out_red;

    if ((Integer) tag == backgroundID1) {
        call86(links, "available", currentButton);
    } else if ((Integer) tag == backgroundID2) {
        currentButton.setBackgroundResource(R.drawable.available);
    } else if ((Integer) tag == backgroundID3) {
        currentButton.setBackgroundResource(R.drawable.sold_out_red);
    } else if ((Integer) tag == backgroundID4) {
        call86(links, "soldOutToday", currentButton);
    }
    currentButton.setVisibility(VISIBLE);
}

public void call86(List<Links> links, String comeFrom, Button currrentButton){
    ...
}

public Section<MainItem, Modifier> getSection(MenuItemModel.Item item, List<MenuItemModel.Item.SubItem> subItems) {
    Section<MainItem, Modifier> section = new Section<>();
    boolean haveModifiers = !(subItems == null || subItems.isEmpty());
    section.parent = new MainItem(item, getStatus(item), haveModifiers);
    for (MenuItemModel.Item.SubItem subItem:subItems){
        Modifier modifier = new Modifier(subItem, getStatusForModifiers(subItem));
        section.children.add(modifier);
    }
    section.expanded = false;
    return section;
}

private int getStatus(MenuItemModel.Item item) {
    ...
}

private int getStatusForModifiers(MenuItemModel.Item.SubItem modifier)       {
    ...
}

我使用的库在这里:

https://thoughtbot.com/blog/introducing-expandablerecyclerview

我的问题是:

  1. 该如何解决冻结的问题?

  2. 我应该使用以下可扩展的 recyclerview 库还是 ExpandableListeView ?如果您认为所使用的设备是具有1 GB RAM的Amazon设备,那么您认为我现在使用的库在性能方面是否有所不同?

可扩展的RecyclerView: {{3}}

谢谢您的帮助

0 个答案:

没有答案