android - 片段无故失去对活动的引用
问题描述
在我的一个片段中,我有时会遇到一个异常,指出 myContext
为空。
目前,我无法重现该问题,因为我尝试以多种不同方式访问崩溃代码,但没有一致的结果。
这是我得到的崩溃日志:
E/AndroidRuntime: FATAL EXCEPTION: main
Process: eu.side.aurora, PID: 12940
java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference
at android.widget.Toast.<init>(Toast.java:101)
at android.widget.Toast.makeText(Toast.java:258)
at eu.side.aurora.views.fragments.StepStock.lambda$onCreateView$2$StepStock(StepStock.java:161)
以及如果引用的代码
InterventionsViewModel interventionsViewmodel = ViewmodelProviders.of(getActivity()).get(InterventionsViewModel)
interventionsViewmodel.getExceptions().observe(getActivity(), exception ->{
if(exception instanceof QuantityOverflowException){
Toast.makeText(getActivity(), "No you just can't add more stock than there is available!", Toast.LENGTH_SHORT).show();
}
if(exception instanceof ScannedArticleNotFoundException){
Toast.makeText(getActivity(), "This article doesn't even exist! Get your shit together please!²", Toast.LENGTH_SHORT).show();
}
});
奇怪的是,我几乎在我的片段中的任何地方都引用了 getActivty()onCreateView
并且它只在那里崩溃。
要使用下面的视图访问代码,我只需按+或-按钮从我的列表中添加或删除文章。当它达到最大值时,它会发送一个Toast
通知用户。
当点击加号或减号按钮时,它们会通知ViewModel
,这将改变我之前观察到的可观察对象。
有谁知道这是从哪里来的?我假设它来自我的片段与我的片段分离,Activity
但我无法弄清楚它是如何做到这一点的,因为我在创建片段后再也没有碰过我的片段。
在此先感谢,马蒂厄
编辑:根据要求,这里是完整片段的代码包 eu.side.aurora.views.fragments;
public class StepStock extends Fragment {
private INextStep nextStep;
@BindView(R.id.articles_autocomplete)
AutoCompleteTextView articlesAutocomplete;
@BindView(R.id.articles_recycler)
RecyclerView articleRecycler;
private AccountManager accountManager;
private Account account;
private ArrayList<DetailedArticle> articles;
private ArrayList<Article> stockedArticles;
private StockRecyclerAdapter stockAdapter;
private InterventionsViewModel interventionViewModel;
public StepStock() {
// Required empty public constructor
}
/**
* Use this factory method to create a new instance of
* this fragment using the provided parameters.
*
* @return A new instance of fragment StepStock.
*/
// TODO: Rename and change types and number of parameters
public static StepStock newInstance() {
return new StepStock();
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_step_stock, container, false);
ButterKnife.bind(this, view);
interventionViewModel = ViewModelProviders.of(getActivity()).get(InterventionsViewModel.class);
/* UI Intialization */
articleRecycler.setLayoutManager(new LinearLayoutManager(getContext(), LinearLayoutManager.VERTICAL, false));
/**
* Stock recycler view
* Used to keep track of stock used in an intervention
* OnPlus -> Add one from article
* OnMinus -> Remove one from article
* */
stockedArticles = new ArrayList<>();
stockAdapter = new StockRecyclerAdapter(stockedArticles, new StockRecyclerAdapter.OnArticleClickListener() {
@Override
public void onArticleClicked(int position) {
//new intent
}
@Override
public void onPlusClicked(int position) {
interventionViewModel.addOneToStockAtArticle(stockAdapter.getData().get(position));
}
@Override
public void onMinusClicked(int position) {
interventionViewModel.minusOneOrRemoveAtArticle(stockAdapter.getData().get(position));
}
});
interventionViewModel.getCurrentIntervention().observe(getActivity(), intervention -> {
if(intervention!= null && intervention.getArticles() != null)
stockAdapter.putData(intervention.getArticles());
});
interventionViewModel.getExceptions().observe(getActivity(), exception ->{
if(exception instanceof QuantityOverflowException){
Toast.makeText(getActivity(), "No you just can't add more stock than there is available!", Toast.LENGTH_SHORT).show();
}
if(exception instanceof ScannedArticleNotFoundException){
Toast.makeText(getActivity(), "This article doesn't even exist! Get your shit together please!²", Toast.LENGTH_SHORT).show();
}
});
return view;
}
@Override
public void onAttach(Context context) {
super.onAttach(context);
if(context instanceof INextStep){
nextStep = (INextStep) context;
}
else{
throw new RuntimeException(context.toString() + " must implement INextStep");
}
}
@Override
public void onDetach() {
super.onDetach();
nextStep = null;
}
}
解决方案
我会删除此代码
interventionViewModel.getExceptions().observe(this, exception ->{
if(exception instanceof QuantityOverflowException){
Toast.makeText(getActivity(), "No you just can't add more stock than there is available!", Toast.LENGTH_SHORT).show();
}
if(exception instanceof ScannedArticleNotFoundException){
Toast.makeText(getActivity(), "This article doesn't even exist! Get your shit together please!²", Toast.LENGTH_SHORT).show();
}
});
并覆盖onactivitycreated方法并将其放在那里。然后,您可以确定它getActivity()
不会返回 null。另请注意,在观察方法中,我传递的是片段的实例而不是活动,因此观察者将尊重片段的生命周期。
推荐阅读
- java - Project setup in IntelliJ IDEA for three java modules, one used as a module for the other two
- hibernate - 如何使用 JpaRepository 进行批量(多行)插入?
- arrays - 找到积为 N 的 K 个数,保持 K 个数的最大值为最小值
- python - 为什么我不能通过 usint tf.reshape() 将 (None, 375) 重塑为 (25,15)
- javascript - 三元运算符中的反应路由器
- java - 在 QueryDsl 中按总和排序
- xcode - 有没有办法以编程方式截取 Apple TV(连接 HDMI 的)屏幕的屏幕截图?
- html - 不应该显示的边框底部
- c# - 从 doc(x) 文件 .NET 中提取嵌入表
- docker - Docker的Nginx IP过滤器不起作用