我正在我的活动班级内请求电话许可。由于某种原因,我在checkSelfPermission()
方法内传递的 Context 似乎为空,这导致了空指针异常。我已经尝试了几乎所有内容(this
,ActivityName.this
,getContext()
,getApplicationContext()
)。我尝试过的一切都给了空指针异常。我应该通过Context
才能正常工作吗?
注意:对makephonecall()
方法的调用是从我的适配器类在按下按钮时启动的。
public void makephonecall()
{
try {
if (ContextCompat.checkSelfPermission(BloodVaultActivity2.this,
Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(BloodVaultActivity2.this,
new String[]{Manifest.permission.CALL_PHONE}, REQUEST_CALL);
} else {
Intent intent = new Intent(Intent.ACTION_CALL);
intent.setData(Uri.parse("tel:" + number));
startActivity(intent);
}
}
catch (NullPointerException e){
e.printStackTrace();
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
if(requestCode == REQUEST_CALL)
{
if(grantResults.length>0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
{
makephonecall();
}
else
{
Toast.makeText(getApplicationContext(), "Permission Denied", Toast.LENGTH_SHORT).show();
}
}
}
适配器类:
package bd.edu.bubt.regup;
import android.*;
import android.Manifest;
import android.app.Activity;
import android.app.Application;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import java.util.ArrayList;
public class BloodVaultAdapter extends ArrayAdapter<BloodVaultItem> {
ArrayList<BloodVaultItem> adapterlist = new ArrayList<>();
int REQUEST_CALL = 1;
public BloodVaultAdapter(Context context, int textViewResourceId, ArrayList<BloodVaultItem> objects){
super(context, textViewResourceId, objects);
adapterlist = objects;
}
@Override
public int getCount(){
return super.getCount();
}
@Override
public View getView(final int position, View convertView, ViewGroup parent){
View v = convertView;
LayoutInflater inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
v = inflater.inflate(R.layout.blood_vault_list_view_layout, null);
TextView name = (TextView) v.findViewById(R.id.name);
TextView group = (TextView) v.findViewById(R.id.group);
Button call = (Button) v.findViewById(R.id.call);
call.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
BloodVaultItem bloodVaultItem = getItem(position);
String number = bloodVaultItem.getContact();
BloodVaultActivity2 bloodVaultActivity2 = new BloodVaultActivity2();
bloodVaultActivity2.number = number;
bloodVaultActivity2.makephonecall();
}
});
name.setText("Name: " +adapterlist.get(position).getName());
group.setText("Blood Group: " +adapterlist.get(position).getGroup());
return v;
}
}
Logcat:
06-13 01:42:36.920 13102-13102/bd.edu.bubt.regup W/System.err: java.lang.NullPointerException: Attempt to invoke virtual method 'int android.content.Context.checkPermission(java.lang.String, int, int)' on a null object reference
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at android.support.v4.content.ContextCompat.checkSelfPermission(ContextCompat.java:430)
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at bd.edu.bubt.regup.BloodVaultActivity2.makephonecall(BloodVaultActivity2.java:182)
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at bd.edu.bubt.regup.BloodVaultAdapter$1.onClick(BloodVaultAdapter.java:63)
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at android.view.View.performClick(View.java:5637)
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at android.view.View$PerformClick.run(View.java:22429)
06-13 01:42:36.921 13102-13102/bd.edu.bubt.regup W/System.err: at android.os.Handler.handleCallback(Handler.java:751)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at android.os.Handler.dispatchMessage(Handler.java:95)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at android.os.Looper.loop(Looper.java:154)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at android.app.ActivityThread.main(ActivityThread.java:6119)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at java.lang.reflect.Method.invoke(Native Method)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
06-13 01:42:36.922 13102-13102/bd.edu.bubt.regup W/System.err: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776)
06-13 01:42:36.928 1382-1455/? W/audio_hw_generic: Not supplying enough data to HAL, expected position 137954329 , only wrote 137954160
06-13 01:42:36.975 1382-1455/? W/audio_hw_generic: Hardware backing HAL too slow, could only write 0 of 720 frames
06-13 01:42:40.154 1382-1456/? W/audio_hw_generic: Not supplying enough data to HAL, expected position 138261974 , only wrote 138108960
06-13 01:43:28.433 2223-8977/com.google.android.apps.nexuslauncher I/ClearcutLoggerApiImpl: disconnect managed GoogleApiClient
01-01 00:00:00.000 0-0/? E/Internal: device offline
答案 0 :(得分:1)
尝试通过context
(在适配器的构造函数中接收)代替BloodVaultActivity2.this
,即
ContextCompat.checkSelfPermission(context,Manifest.permission.CALL_PHONE)
另外,
BloodVaultActivity2 bloodVaultActivity2 =新的BloodVaultActivity2();
调用方法的方法不正确,因为这会创建您的活动的新实例,而是将您的context
转换为BloodVaultActivity2
并在Adapter的构造函数中从您的Activity中传递this
if(mContext instanceof YourActivityName){
((YourActivityName)mContext).yourActivityMethod();
}
在Activity和Adapter之间进行交互的更好方法是使用接口。 https://android.jlelse.eu/click-listener-for-recyclerview-adapter-2d17a6f6f6c9
答案 1 :(得分:0)
更新:根本原因是您正在为单击项目创建活动的新实例,因此看到空指针。由于您已经在适配器中传递了上下文,因此请按照Manoj在https://stackoverflow.com/a/56573418/3318025
中显示的方式进行操作答案 2 :(得分:0)
如果您使用创建类的对象
BloodVaultActivity2 bloodVaultActivity2 = new BloodVaultActivity2();
bloodVaultActivity2.number = number;
bloodVaultActivity2.makephonecall();
由于它是一个具有生命周期感知方法的活动类,因此不会调用该函数,一种方法是创建一个使用上下文调用该函数的接口,或者将上下文转换为具有您要使用的方法的活动跑 更改它,
public class BloodVaultAdapter extends ArrayAdapter<BloodVaultItem> {
Context context;
public BloodVaultAdapter(Context context, int textViewResourceId,
ArrayList<BloodVaultItem> objects){
super(context, textViewResourceId, objects);
this.context=context;
adapterlist = objects;
}
然后
call.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
BloodVaultItem bloodVaultItem = getItem(position);
String number = bloodVaultItem.getContact();
(( BloodVaultActivity2)context).makephonecall();
}
});
答案 3 :(得分:0)
最后,我找到了解决这个问题的方法。我只是结合了Astha和Manoj的答案中link1和link2的解决方案。
首先,我使用以下命令捕获了context
类的adapter
:
Context context;
public BloodVaultAdapter(Context context, int textViewResourceId, ArrayList<BloodVaultItem> objects){
super(context, textViewResourceId, objects);
this.context = context;
adapterlist = objects;
}
将context
作为makephonecallmethod()
类的adapter
的参数第二次传递:
call.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
BloodVaultItem bloodVaultItem = getItem(position);
String number = bloodVaultItem.getContact();
BloodVaultActivity2 bloodVaultActivity2 = new BloodVaultActivity2();
bloodVaultActivity2.number = number;
bloodVaultActivity2.makephonecall(context);
}
});
在context
类中,将传递的checkSelfPermission()
用作Activity
的参数:
Context mcontext;
public void makephonecall(Context context)
{
this.mcontext = context;
try {
if (ContextCompat.checkSelfPermission(context,
Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(BloodVaultActivity2.this,
new String[]{Manifest.permission.CALL_PHONE}, REQUEST_CALL);
} else {
String dial = "tel:" + number;
context.startActivity(new Intent(Intent.ACTION_CALL, Uri.parse(dial)));
}
}
catch (NullPointerException e){
e.printStackTrace();
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
if(requestCode == REQUEST_CALL)
{
if(grantResults.length>0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
{
makephonecall(mcontext);
}
else
{
Toast.makeText(getApplicationContext(), "Permission Denied", Toast.LENGTH_SHORT).show();
}
}
}