You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android:接口向Tab Fragment传日期数据仅第二个接收异常

问题原因

你的BranchProfitabilityActivity里只维护了一个SendData类型的变量,两个Fragment依次调用setSendData(this)时,第二个Fragment的引用会直接覆盖第一个的。所以后续修改日期触发回调时,只有最后被赋值的那个Fragment(也就是第二个)能收到数据。

修复方案

1. 修改Activity代码,用集合存储所有Fragment的回调引用

public class BranchProfitabilityActivity extends AppCompatActivity {

    // 将单个变量改为集合,保存所有注册的Fragment回调
    private List<SendData> sendDataList = new ArrayList<>();
    private Calendar calendar;
    private int selectedMonth, selectedYear;

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

        calendar = Calendar.getInstance(TimeZone.getDefault());
        selectedMonth = calendar.get(Calendar.MONTH);
        selectedYear = calendar.get(Calendar.YEAR);

        String[] tabTiles = {"LIFE", "GENERAL"};

        ViewPager2 viewPager = findViewById(R.id.view_pager);
        TabLayout tabLayout = findViewById(R.id.profit_tabs);

        ProfitabilityViewPagerAdapter myAdapter = new ProfitabilityViewPagerAdapter(this);
        myAdapter.addFragment(new BranchProfitabilityFragmentLife());
        myAdapter.addFragment(new BranchProfitabilityFragmentGeneral());

        viewPager.setOrientation(ViewPager2.ORIENTATION_HORIZONTAL);
        viewPager.setAdapter(myAdapter);

        new TabLayoutMediator(tabLayout, viewPager,
                (tab, position) -> tab.setText(tabTiles[position])).attach();
    }

    public interface SendData {
        void SendYearMonth(int iYear, int iMonth);
    }

    // 修改注册逻辑,将Fragment添加到集合而非覆盖
    public void registerSendData(SendData sendData) {
        if (!sendDataList.contains(sendData)) {
            sendDataList.add(sendData);
            // 注册后立即发送当前选中的年月
            sendData.SendYearMonth(selectedYear, selectedMonth);
        }
    }

    // 添加注销方法,Fragment销毁时移除引用,避免内存泄漏
    public void unregisterSendData(SendData sendData) {
        sendDataList.remove(sendData);
    }

    private void LoadDataFromYearMonth(int year, int month) {
        // 遍历集合,给所有注册的Fragment发送数据
        for (SendData sendData : sendDataList) {
            if (sendData != null) {
                sendData.SendYearMonth(year, month);
            }
        }
    }

    // 补充DatePicker选中事件处理(示例)
    /*
    private void onDatePickerChanged(int year, int month) {
        selectedYear = year;
        selectedMonth = month;
        LoadDataFromYearMonth(year, month);
    }
    */
}

2. 修改两个Fragment的注册/注销逻辑

BranchProfitabilityFragmentLife

public class BranchProfitabilityFragmentLife extends Fragment implements BranchProfitabilityActivity.SendData {

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View xView = inflater.inflate(R.layout.fragment_branch_profitability_life, container, false);
        return xView;
    }

    @Override
    public void onStart() {
        super.onStart();
        // 在Fragment可见时注册回调
        if (getActivity() instanceof BranchProfitabilityActivity) {
            ((BranchProfitabilityActivity) getActivity()).registerSendData(this);
        }
    }

    @Override
    public void onStop() {
        super.onStop();
        // 在Fragment不可见时注销回调
        if (getActivity() instanceof BranchProfitabilityActivity) {
            ((BranchProfitabilityActivity) getActivity()).unregisterSendData(this);
        }
    }

    @Override
    public void SendYearMonth(int iYear, int iMonth) {
        RequestData(iYear, iMonth);
    }

    private void RequestData(int year, int month) {
        // 你的数据请求逻辑
    }
}

BranchProfitabilityFragmentGeneral

public class BranchProfitabilityFragmentGeneral extends Fragment implements BranchProfitabilityActivity.SendData {

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View xView = inflater.inflate(R.layout.fragment_branch_profitability_general, container, false);
        return xView;
    }

    @Override
    public void onStart() {
        super.onStart();
        if (getActivity() instanceof BranchProfitabilityActivity) {
            ((BranchProfitabilityActivity) getActivity()).registerSendData(this);
        }
    }

    @Override
    public void onStop() {
        super.onStop();
        if (getActivity() instanceof BranchProfitabilityActivity) {
            ((BranchProfitabilityActivity) getActivity()).unregisterSendData(this);
        }
    }

    @Override
    public void SendYearMonth(int iYear, int iMonth) {
        RequestData(iYear, iMonth);
    }

    private void RequestData(int year, int month) {
        // 你的数据请求逻辑
    }
}

额外说明

  • 将回调注册从onCreateView移到onStart,注销移到onStop,既能保证Fragment可见时才接收数据,也能避免内存泄漏。
  • 用集合存储所有回调引用后,每个Fragment都会收到Activity发送的年月数据,不会再出现被覆盖的问题。

内容的提问来源于stack exchange,提问作者D.madushanka

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.15 05:20:28