使用strings.xml传递数据时可展开布局信息被覆盖问题求助
解决可展开布局中字符串资源被覆盖的问题
看起来你遇到了一个很典型的变量复用导致的数据覆盖问题!我来帮你捋捋问题出在哪,再给你具体的解决办法:
问题根源
你在ActivitiesActivity里定义的activity_name_int、activity_phone_in...这类变量是类的成员变量,当你创建多个可展开区块时,每次给这些变量赋值都会覆盖之前的内容。比如你先给第一个区块赋值activity1_website,接着创建第二个区块时又把变量改成activity2_website,那之前绑定的第一个区块因为引用的是同一个变量,最终显示的就会是最后一次赋值的结果。
解决方案
核心思路是让每个可展开区块拥有自己独立的数据存储,不再共享类成员变量。这里提供两种常见的实现方式:
方式1:用数据类封装每个区块的信息
首先定义一个专门存储单个区块信息的数据类,把每个区块需要的资源ID都封装进去:
public class ActivityBlockData { public int nameResId; public int phoneResId; public int websiteResId; // 构造方法,传入对应资源ID public ActivityBlockData(int nameResId, int phoneResId, int websiteResId) { this.nameResId = nameResId; this.phoneResId = phoneResId; this.websiteResId = websiteResId; } }
然后在Activity里准备所有区块的数据源:
// 把所有需要展示的区块信息存到列表里 List<ActivityBlockData> blockList = new ArrayList<>(); blockList.add(new ActivityBlockData( R.string.activity1_name, R.string.activity1_phone, R.string.activity1_website )); blockList.add(new ActivityBlockData( R.string.activity2_name, R.string.activity2_phone, R.string.activity2_website )); // 还可以继续添加更多区块
最后遍历列表,为每个数据实例创建对应的可展开布局并绑定数据:
// parentLayout是你放置可展开布局的容器 for (ActivityBlockData blockData : blockList) { // 加载头部和子项布局(根据你自己的布局文件名调整) View headerView = LayoutInflater.from(this).inflate(R.layout.expandable_header, parentLayout, false); View childView = LayoutInflater.from(this).inflate(R.layout.expandable_child, parentLayout, false); // 设置头部文本 TextView headerName = headerView.findViewById(R.id.tv_header_name); headerName.setText(blockData.nameResId); // 设置子项的电话和网站 TextView tvPhone = childView.findViewById(R.id.tv_child_phone); tvPhone.setText(blockData.phoneResId); TextView tvWebsite = childView.findViewById(R.id.tv_child_website); tvWebsite.setText(blockData.websiteResId); // 将头部和子项添加到你的可展开布局组件中 // 这里根据你使用的可展开布局实现来调整,比如自定义ExpandableLayout或者第三方库 ExpandableLayout expandableLayout = new ExpandableLayout(this); expandableLayout.setHeaderView(headerView); expandableLayout.setChildView(childView); parentLayout.addView(expandableLayout); }
方式2:如果使用ExpandableListView的情况
如果你是用系统的ExpandableListView,那需要自定义一个适配器,在适配器里直接从数据源获取对应位置的数据,避免共享变量:
public class ActivityExpandableAdapter extends BaseExpandableListAdapter { private Context mContext; private List<ActivityBlockData> mBlockList; public ActivityExpandableAdapter(Context context, List<ActivityBlockData> blockList) { mContext = context; mBlockList = blockList; } @Override public int getGroupCount() { return mBlockList.size(); } @Override public int getChildrenCount(int groupPosition) { return 1; // 每个头部对应一个子项,可根据需求调整 } @Override public Object getGroup(int groupPosition) { return mBlockList.get(groupPosition); } @Override public Object getChild(int groupPosition, int childPosition) { return mBlockList.get(groupPosition); } @Override public long getGroupId(int groupPosition) { return groupPosition; } @Override public long getChildId(int groupPosition, int childPosition) { return childPosition; } @Override public boolean hasStableIds() { return true; } @Override public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { if (convertView == null) { convertView = LayoutInflater.from(mContext).inflate(R.layout.expandable_header, parent, false); } ActivityBlockData data = mBlockList.get(groupPosition); TextView headerName = convertView.findViewById(R.id.tv_header_name); headerName.setText(data.nameResId); return convertView; } @Override public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) { if (convertView == null) { convertView = LayoutInflater.from(mContext).inflate(R.layout.expandable_child, parent, false); } ActivityBlockData data = mBlockList.get(groupPosition); TextView tvPhone = convertView.findViewById(R.id.tv_child_phone); TextView tvWebsite = convertView.findViewById(R.id.tv_child_website); tvPhone.setText(data.phoneResId); tvWebsite.setText(data.websiteResId); return convertView; } @Override public boolean isChildSelectable(int groupPosition, int childPosition) { return false; // 根据需求设置是否可点击 } }
然后在Activity里设置适配器:
ExpandableListView expandableListView = findViewById(R.id.expandable_list); ActivityExpandableAdapter adapter = new ActivityExpandableAdapter(this, blockList); expandableListView.setAdapter(adapter);
关键注意点
确保每个区块的资源ID都是从独立的数据源(比如上面的ActivityBlockData实例)中获取,而不是依赖类成员变量。这样每个区块都会绑定自己专属的数据,就不会出现被最后一个区块覆盖的问题了。
内容的提问来源于stack exchange,提问作者Wafflekonez
相关产品推荐
相关产品推荐

