I created a Flashlight app. It is working for all devices except marshmallow. Even after I used the asking for permission. I feel that there is something wrong in the asking for permission of my code. Do you see any problems?
package com.funny.flashlight;
import android.Manifest;
import android.content.DialogInterface;
import android.content.pm.PackageManager;
import android.hardware.Camera;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.ImageButton;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity
{
private static final int REQUEST_CAMERA = 0;
ImageButton imageButton;
Camera camera;
Camera.Parameters parameters;
boolean isflash=false;
boolean isOn=false;
public void showCamera(View view)
{
if(checkSelfPermission(Manifest.permission.CAMERA)==PackageManager.PERMISSION_GRANTED)
{
showCameraPreview();
}
else
{
if (shouldShowRequestPermissionRationale(Manifest.permission.CAMERA))
{
Toast.makeText(this, "Camera Permission is needed to show Camera Preview",Toast.LENGTH_SHORT).show();
}
requestPermissions(new String[]{Manifest.permission.CAMERA},REQUEST_CAMERA);
}
}
#Override
public void onRequestPermissionsResult(int requestCode, #NonNull String[] permissions, #NonNull int[] grantResults) {
if (requestCode==REQUEST_CAMERA)
{
if (grantResults[0]==PackageManager.PERMISSION_GRANTED)
{
showCameraPreview();
}
else {
Toast.makeText(this, "Permission was not Granted", Toast.LENGTH_SHORT).show();
}
}
else {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imageButton = (ImageButton) findViewById(R.id.imageButton);
if (getApplicationContext().getPackageManager().hasSystemFeature(PackageManager.FEATURE_CAMERA_FLASH))
{
camera = Camera.open();
parameters = camera.getParameters();
isflash = true;
}
imageButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v)
{
if (isflash)
{
if (isOn)
{
imageButton.setImageResource(R.drawable.off);
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
camera.setParameters(parameters);
camera.stopPreview();
isOn = false;
}
else
{
imageButton.setImageResource(R.drawable.on);
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
camera.setParameters(parameters);
camera.startPreview();
isOn = true;
}
}
else
{
AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
builder.setTitle("Error");
builder.setMessage("FlashLight is not Available on this device");
builder.setPositiveButton("Ok", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
finish();
}
});
AlertDialog alertDialog = builder.create();
alertDialog.show();
}
}
});
}
#Override
protected void onStop()
{
super.onStop();
if(camera!=null)
{
camera.release();
camera=null;
}
}
}
Depending on what you're trying to do, I would suggest following this format for checking/requesting permissions:
private int CAMERA_PERM = 0;
if (ContextCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.CAMERA}, CAMERA_PERM);
}
Then for retrieving the response:
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
switch (requestCode) {
case CAMERA_PERM: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//Permission Granted
} else {
//Permission Denied
}
return;
}
}
}
Related
I am building an app that reads SMS's by converting them to speech.
After installing the apk it runs but when I close it and try to open it again it crashes.
It gives an error message saying the app keeps closing.
When I set it to only read after a button click it was working fine but after I changed it to read on initialization this problem came about.
Please help.
package com.example.receiver3;
import android.Manifest;
import android.content.ContentResolver;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.database.Cursor;
import android.net.Uri;
import android.speech.tts.TextToSpeech;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Button;
import android.widget.Toast;
import java.util.ArrayList;
import java.util.Locale;
public class MainActivity extends AppCompatActivity {
ListView listView;
Button btConvert, btNext;
private static final int PERMISSION_REQUEST_READ_CONTACTS = 100;
ArrayList<String> smsList;
TextToSpeech textToSpeech;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView = (ListView) findViewById(R.id.idList);
int permissionCheck = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_SMS);
if (permissionCheck == PackageManager.PERMISSION_GRANTED){
initializeTextToSpeech(); //edit
showContact();
}
else{
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_SMS}, PERMISSION_REQUEST_READ_CONTACTS);
}
btConvert = findViewById(R.id.bt_stop);
btNext = findViewById(R.id.bt_next);
btConvert.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
//get list value
for (String s : smsList) {
textToSpeech.stop();
}
}
});
Button button = (Button) findViewById(R.id.bt_next);
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
openActivity();
}
});
}
private void initializeTextToSpeech() { //edit
textToSpeech = new TextToSpeech(getApplicationContext(), new TextToSpeech.OnInitListener() {
#Override
public void onInit(int i) {
if (i == TextToSpeech.SUCCESS){
int lang = textToSpeech.setLanguage(Locale.UK);
}
}
});
}
public void openActivity(){
Intent intent = new Intent(this, Main2Activity.class);
startActivity(intent);
}
#Override
public void onRequestPermissionsResult(int requestCode, #NonNull String[] permissions, #NonNull int[] grantResults) {
if (requestCode == PERMISSION_REQUEST_READ_CONTACTS){
showContact();
initializeTextToSpeech(); //edit
}
else {
Toast.makeText(this, "Permission Required", Toast.LENGTH_SHORT).show();
}
}
private void showContact() {
Uri inboxUri = Uri.parse("content://sms/inbox");
smsList = new ArrayList<>();
ContentResolver contentResolver = getContentResolver();
Cursor cursor = contentResolver.query(inboxUri,null, null, null, null);
while (cursor.moveToNext()){
String number = cursor.getString(cursor.getColumnIndexOrThrow("address")).toString();
String body = cursor.getString(cursor.getColumnIndexOrThrow("body")).toString();
smsList.add("Number: "+number+ "\n" + "Body: "+body);
}
for (String s : smsList) {
textToSpeech.speak(s,TextToSpeech.QUEUE_ADD, null);
}
cursor.close();
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1,smsList);
listView.setAdapter(adapter);
}
public void speak() { //edit
for (String s : smsList) {
textToSpeech.speak(s,TextToSpeech.QUEUE_ADD, null);
}
}
#Override
protected void onPause() { //edit
super.onPause();
textToSpeech.stop();
}
#Override
protected void onStop() {
super.onStop();
textToSpeech.stop();
}
#Override
protected void onResume() { //edit
super.onResume();
showContact();
initializeTextToSpeech();
}
}
You are now calling showContact() which in turn calls textToSpeech.speak() before initialising the textToSpeech object with textToSpeech = new TextToSpeech().
The code works fine on the first run because the user hasn't given the requested permission yet and showContact() doesn't get called.
You need to change your onCreate:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView = (ListView) findViewById(R.id.idList);
int permissionCheck = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_SMS);
// *** MOVE THIS UP HERE. ***
textToSpeech = new TextToSpeech(getApplicationContext(), new TextToSpeech.OnInitListener() {
#Override
public void onInit(int i) {
if (i == TextToSpeech.SUCCESS){
int lang = textToSpeech.setLanguage(Locale.UK);
return;
}
}
});
if (permissionCheck == PackageManager.PERMISSION_GRANTED){
showContact();
return;
} else {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_SMS}, PERMISSION_REQUEST_READ_CONTACTS);
}
btConvert = findViewById(R.id.bt_convert);
btNext = findViewById(R.id.bt_next);
btConvert.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
//get list value
for (String s : smsList) {
textToSpeech.stop();
}
}
});
Button button = (Button) findViewById(R.id.bt_next);
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
openActivity();
}
});
}
But that alone won't be enough as TTS isn't ready immediately. It's usable only after the onInit() callback has run and you receive the TextToSpeech.SUCCESS state there.
So, if you want to speak something as soon as possible at application startup then it needs to be triggered from onInit().
Maybe you can think of something like:
int permissionCheck = ContextCompat.checkSelfPermission(this, Manifest.permission.READ_SMS);
if (permissionCheck != PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_SMS}, PERMISSION_REQUEST_READ_CONTACTS);
}
And then:
textToSpeech = new TextToSpeech(getApplicationContext(), new TextToSpeech.OnInitListener() {
#Override
public void onInit(int i) {
if (i == TextToSpeech.SUCCESS){
int lang = textToSpeech.setLanguage(Locale.UK);
if (permissionCheck == PackageManager.PERMISSION_GRANTED){
showContact();
}
}
}
});
I don't see why would you have the return; calls at all. And actually in the original code the return; exits the onCreate() before even trying to initialize the TTS if the permission is already given.
Please can somebody help me I am really new to this.
Right now I have a firebase database with data the user added manually. I want an additional function that the user can scan the barcode and the barcode number will come up and they can enter the details this way and save it to the database. The next time they scan that item the fields will already be there.
This is the code I have for the barcode scanner. I want to add the fields to enter text into the result handler with the barcode number plus additional details being saved to the database.
Please can anybody help me I am so lost.
package com.virtual.fridge.BarcodeScanner;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.hardware.Camera;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.Snackbar;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.
import android.util.Log;
import android.view.View;
import android.widget.Toast;
import com.google.zxing.Result;
import com.virtual.fridge.Manifest;
import com.virtual.fridge.R;
import me.dm7.barcodescanner.zxing.ZXingScannerView;
import static android.Manifest.permission.CAMERA;
/*SOURCE:
https://github.com/priyankapakhale/QRBarcodeScanner/blob/master/app/src/main/AndroidManifest.xml
https://www.youtube.com/watch?v=otkz5Cwdw38&t=3s
*/
public class BarcodeDetect extends AppCompatActivity implements ZXingScannerView.ResultHandler {
private static final int REQUEST_CAMERA = 1;
private ZXingScannerView scannerView;
private static int camId = Camera.CameraInfo.CAMERA_FACING_BACK;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
scannerView = new ZXingScannerView(this);
setContentView(scannerView);
int currentApiVersion = Build.VERSION.SDK_INT;
if(currentApiVersion >= Build.VERSION_CODES.M)
{
if(checkPermission())
{
Toast.makeText(BarcodeDetect.this, "Permission already granted!", Toast.LENGTH_LONG).show();
}
else
{
requestPermission();
}
}
}
private boolean checkPermission()
{
return (ContextCompat.checkSelfPermission(BarcodeDetect.this, CAMERA) == PackageManager.PERMISSION_GRANTED);
}
private void requestPermission()
{
ActivityCompat.requestPermissions(this, new String[]{CAMERA}, REQUEST_CAMERA);
}
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
switch (requestCode) {
case REQUEST_CAMERA:
if (grantResults.length > 0) {
boolean cameraAccepted = grantResults[0] == PackageManager.PERMISSION_GRANTED;
if (cameraAccepted){
Toast.makeText(BarcodeDetect.this, "Permission Granted, Now you can access camera", Toast.LENGTH_LONG).show();
}
else
{
Toast.makeText(BarcodeDetect.this, "Permission Denied, You cannot access and camera", Toast.LENGTH_LONG).show();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
if (shouldShowRequestPermissionRationale(CAMERA)) {
showMessageOKCancel("You need to allow access to both the permissions",
new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
requestPermissions(new String[]{CAMERA},
REQUEST_CAMERA);
}
}
});
return;
}
}
}
}
break;
}
}
private void showMessageOKCancel(String message, DialogInterface.OnClickListener okListener) {
new android.support.v7.app.AlertDialog.Builder(BarcodeDetect.this)
.setMessage(message)
.setPositiveButton("OK", okListener)
.setNegativeButton("Cancel", null)
.create()
.show();
}
#Override
public void onResume() {
super.onResume();
int currentapiVersion = android.os.Build.VERSION.SDK_INT;
if (currentapiVersion >= android.os.Build.VERSION_CODES.M) {
if (checkPermission()) {
if(scannerView == null) {
scannerView = new ZXingScannerView(this);
setContentView(scannerView);
}
scannerView.setResultHandler(this);
scannerView.startCamera();
} else {
requestPermission();
}
}
}
#Override
public void onDestroy() {
super.onDestroy();
scannerView.stopCamera();
}
#Override
public void handleResult(Result result) {
final String myResult = result.getText();
Log.d("QRCodeScanner", result.getText());
Log.d("QRCodeScanner", result.getBarcodeFormat().toString());
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("Scan Result");
builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
scannerView.resumeCameraPreview(BarcodeDetect.this);
}
});
builder.setNeutralButton("Visit", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(myResult));
startActivity(browserIntent);
}
});
builder.setMessage(result.getText());
AlertDialog alert1 = builder.create();
alert1.show();
}
}
#Override
public void handleResult(me.dm7.barcodescanner.zbar.Result result) {
String result_text=result.getContents();
if(result_text!=null && !result_text.isEmpty()){
/* you can fetch your fields here and can write code to save in database here */
}
}
I am trying to check runtime permissions inside a fragment by calling permissions class but in fragment overided method to get result of permissions granted or not is not working in fragment
Here is method of class where i check or request permissions
public boolean checkPermissionForExternalStorage(){
int result = ContextCompat.checkSelfPermission(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE);
if (result == PackageManager.PERMISSION_GRANTED){
return true;
} else {
return false;
}
}
public void requestPermissionForExternalStorage(){
if (ActivityCompat.shouldShowRequestPermissionRationale(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE)){
Toast.makeText(activity, "External Storage permission needed. Please allow in App Settings for additional functionality.", Toast.LENGTH_LONG).show();
} else {
ActivityCompat.requestPermissions(activity,new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
}
}
Here is my Fragment
package in.prsc.com.prscportal;
import android.Manifest;
import android.app.DownloadManager;
import android.app.Fragment;
import android.content.ActivityNotFoundException;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.Environment;
import android.support.annotation.Nullable;
import android.support.annotation.RequiresApi;
import android.support.v7.widget.LinearLayoutCompat;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.webkit.CookieManager;
import android.webkit.DownloadListener;
import android.webkit.URLUtil;
import android.webkit.ValueCallback;
import android.webkit.WebChromeClient;
import android.webkit.WebSettings;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import android.widget.ProgressBar;
import android.widget.Toast;
/**
* Created by Bhuvan on 05-Aug-16.
*/
public class LEP extends Fragment {
View myView;
ProgressBar pb;
WebView mWebView;
private ValueCallback<Uri> mUploadMessage;
public ValueCallback<Uri[]> uploadMessage;
public static final int REQUEST_SELECT_FILE = 100;
private final static int FILECHOOSER_RESULTCODE = 1;
public static int temp_perm;
MarshmallowPermissions marshmallowPermissions;
#Override
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
if (requestCode == REQUEST_SELECT_FILE) {
if (uploadMessage == null)
return;
uploadMessage.onReceiveValue(WebChromeClient.FileChooserParams.parseResult(resultCode, intent));
uploadMessage = null;
}
} else if (requestCode == FILECHOOSER_RESULTCODE) {
if (null == mUploadMessage)
return;
// Use MainActivity.RESULT_OK if you're implementing WebView inside Fragment
// Use RESULT_OK only if you're implementing WebView inside an Activity
Uri result = intent == null || resultCode != MainActivity.RESULT_OK ? null : intent.getData();
mUploadMessage.onReceiveValue(result);
mUploadMessage = null;
} else
Toast.makeText(getActivity().getApplicationContext(), "Failed to Upload Image", Toast.LENGTH_LONG).show();
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
myView = inflater.inflate(R.layout.web_front, container, false);
pb = (ProgressBar) myView.findViewById(R.id.progressBar);
mWebView = (WebView) myView.findViewById(R.id.webview);
marshmallowPermissions = new MarshmallowPermissions(getActivity());
if (Build.VERSION.SDK_INT >= 23) {
if (!marshmallowPermissions.checkPermissionForExternalStorage()) {
marshmallowPermissions.requestPermissionForExternalStorage();
}
}
return myView;
}
#Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults) {
switch (requestCode) {
case MarshmallowPermissions.EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// Here i have to do my code after permissions granted
} else {
// permission denied, boo! Disable the
// functionality that depends on this permission.
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
}
For Fragment, We have to pass Reference in Class
Create Constructor in MarshmallowPermissions Class
public MarshmallowPermissions(Context context, Fragment fragment) {
Log.e(TAG, "MarshMallowPermission() called with: " + "context = [" + context + "], activity = [" + fragment + "]");
this.fragment = fragment;
this.context = context;
}
public void requestPermissionForFragmentWriteExternalStorage() throws Exception {
try {
fragment.requestPermissions(new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},
EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
} catch (Exception e) {
e.printStackTrace();
throw e;
}
}
public boolean checkPermissionForWriteExternalStorage() {
int result = context.checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE);
if (result == PackageManager.PERMISSION_GRANTED) {
return true;
} else {
return false;
}
return false;
}
marshmallowPermissions = new MarshmallowPermissions(getActivity(),fragment);
I got the Answer
I tried and check permissions in my fragment instead of calling from other class and it works
Apply below code in oncreate of fragment
if (Build.VERSION.SDK_INT >= 23) {
checkPermissionForExternalStorage();
}
return myView;
}
#RequiresApi(api = Build.VERSION_CODES.M)
public boolean checkPermissionForExternalStorage(){
int result = ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.WRITE_EXTERNAL_STORAGE);
if (result == PackageManager.PERMISSION_GRANTED){
return true;
} else {
requestPermissions(new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
return true;
}
}
Override below method in fragment
#Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults) {
Log.d("req_result", "success");
switch (requestCode) {
case EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// Do your stuff here after user granted permissions
} else {
// permission denied, boo! Disable the
// functionality that depends on this permission.
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
I am trying to make a text scanner application with camera that recognizes text and shows in screen.But instead of showing camera it shows a black screen. How can I solve this.
My code is here
package com.myapp.game.easynepalirecharge;
import android.Manifest;
import android.app.ActionBar;
import android.content.pm.PackageManager;
import android.graphics.Camera;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.util.SparseArray;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.ViewGroup;
import android.widget.TextView;
import com.google.android.gms.vision.CameraSource;
import com.google.android.gms.vision.Detector;
import com.google.android.gms.vision.text.TextBlock;
import com.google.android.gms.vision.text.TextRecognizer;
import java.io.IOException;
public class MainActivity extends AppCompatActivity {
SurfaceView cameraView;
TextView textView;
CameraSource cameraSource;
final int REQUESTCAMERAPERMISSION = 105;
#Override
public void onRequestPermissionsResult(int requestCode, #NonNull String[] permissions, #NonNull final int[] grantResults) {
switch (requestCode) {
case REQUESTCAMERAPERMISSION:
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
if (ActivityCompat.checkSelfPermission(getApplication(), Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
return;
}
try {
cameraSource.start(cameraView.getHolder());
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
cameraView = (SurfaceView) findViewById(R.id.surfaceView);
textView = (TextView) findViewById(R.id.textView);
TextRecognizer textRecognizer = new TextRecognizer.Builder(getApplicationContext()).build();
if (!textRecognizer.isOperational()) {
Log.v("haha", "error not operational");
} else {
cameraSource = new CameraSource.Builder(getApplicationContext(), textRecognizer).
setFacing(CameraSource.CAMERA_FACING_BACK)
.setRequestedPreviewSize(3840, 2160)
.setRequestedFps(2.0f)
.setAutoFocusEnabled(true)
.build();
cameraView.getHolder().addCallback(new SurfaceHolder.Callback() {
#Override
public void surfaceCreated(SurfaceHolder holder) {
try {
if (ActivityCompat.checkSelfPermission(getApplicationContext(), Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
// TODO: Consider calling
ActivityCompat.requestPermissions(MainActivity.this, new String[]{Manifest.permission.CAMERA}, REQUESTCAMERAPERMISSION);
cameraSource.start(cameraView.getHolder());
return;
}
} catch (Exception e) {
e.printStackTrace();
}
}
#Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
}
#Override
public void surfaceDestroyed(SurfaceHolder holder) {
cameraSource.stop();
}
});
textRecognizer.setProcessor(new Detector.Processor<TextBlock>() {
#Override
public void release() {
}
#Override
public void receiveDetections(Detector.Detections<TextBlock> detections) {
final SparseArray<TextBlock> items = detections.getDetectedItems();
if (items.size() != 0) {
textView.post(new Runnable() {
#Override
public void run() {
StringBuilder stringBuilder = new StringBuilder();
for (int i = 0; i <= items.size(); i++) {
TextBlock item = items.valueAt(i);
stringBuilder.append(item.getValue());
stringBuilder.append("\n");
}
textView.setText(stringBuilder.toString());
}
});
}
}
}
);
}
}
}
and another thing I wanna ask. Which one is better. This or the tess two library?
have you stopped camera properly. Try to do camera functions in thread so that your single task does not be expensive. The reason i thought problem is that get your permission at run time.
try this
https://developer.android.com/training/permissions/requesting.html
I am trying create an app that will read a QR Code, This code worked intermittently but it would give Permission errors and would not load. I believe I have those fixed, but now I get a Black Screen. There are no errors so I do not know where to look, but I feel it has something to do with the permissions.
package com.sample.qrcodereadervision.Activity;
import com.google.android.gms.vision.CameraSource;
import com.google.android.gms.vision.Detector;
import com.google.android.gms.vision.barcode.Barcode;
import com.google.android.gms.vision.barcode.BarcodeDetector;
import com.sample.qrcodereadervision.R;
import android.Manifest;
import android.content.pm.PackageManager;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.design.widget.Snackbar;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.util.SparseArray;
import android.view.SurfaceView;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;
import java.io.IOException;
import permissions.dispatcher.NeedsPermission;
import permissions.dispatcher.OnPermissionDenied;
import permissions.dispatcher.OnShowRationale;
import permissions.dispatcher.PermissionRequest;
import permissions.dispatcher.PermissionUtils;
import permissions.dispatcher.RuntimePermissions;
#RuntimePermissions
public class QRcodeReader extends AppCompatActivity {
public final String TAG = getClass().getSimpleName();
private CameraSource cameraSource;
/** UI Parts : Preview screen */
private SurfaceView cameraView;
/** UI Parts : decoding results */
private TextView barcodeInfo;
private static final int REQUEST_CAMERA = 0x00000011;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.d("QRcodeReader", "onCreate");
setContentView(R.layout.activity_main);
if (ContextCompat.checkSelfPermission(this, Manifest.permission.CAMERA)
!= PackageManager.PERMISSION_GRANTED) {
requestCameraPermission();
}
}
#Override
protected void onStart() {
super.onStart();
Log.d(TAG, "onStart");
barcodeInfo = (TextView) findViewById(R.id.code_info);
cameraView = (SurfaceView) findViewById(R.id.camera_view);
startQRcodeReader();
// startCameraSource();
}
#Override
protected void onPause() {
super.onPause();
Log.d(TAG, "onPause");
}
//#Override
//public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
// Log.d(TAG, "onRequestPermissionsResult");
// QRcodeReaderPermissionsDispatcher.onRequestPermissionsResult(this, requestCode, grantResults);
//}
private void startQRcodeReader() {
Log.d(TAG, "startQRcodeReader");
BarcodeDetector barcodeDetector = new BarcodeDetector.Builder(this)
.setBarcodeFormats(Barcode.QR_CODE)
.build();
cameraSource = new CameraSource
.Builder(this, barcodeDetector)
.setAutoFocusEnabled(true)
.build();
QRcodeReaderPermissionsDispatcher.startCameraSourceWithCheck(QRcodeReader.this);
//requestCameraPermission();
//QR Code reading
barcodeDetector.setProcessor(
new Detector.Processor<Barcode>() {
#Override
public void release() {
}
#Override
public void receiveDetections(Detector.Detections<Barcode> detections) {
final SparseArray<Barcode> barcodes = detections.getDetectedItems();
if (barcodes.size() != 0) {
barcodeInfo.post(
new Runnable() {
public void run() {
barcodeInfo.setText(
barcodes.valueAt(0).displayValue
);
}
});
}
}
});
}
#NeedsPermission(Manifest.permission.CAMERA)
void startCameraSource() {
Log.d(TAG, "startCameraSource");
Toast.makeText(this, "\n" +
"Start the camera source", Toast.LENGTH_SHORT)
.show();
try {
releaseCameraAndPreview();
if (cameraSource != null) {
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
cameraSource.start(cameraView.getHolder());
return;
}
}
} catch (IOException | SecurityException e) {
Log.w(TAG, e);
}
}
#SuppressWarnings("unused")
#OnPermissionDenied(Manifest.permission.CAMERA)
void deniedPermission() {
Log.d(TAG, "deniedPermission");
if (PermissionUtils.shouldShowRequestPermissionRationale(this, Manifest.permission.CAMERA)) {
Toast.makeText(this, "\n" +
"It failed to camera startup .", Toast.LENGTH_SHORT)
.show();
}
}
#SuppressWarnings("unused")
#OnShowRationale(Manifest.permission.CALL_PHONE)
void showRationalForStorage(final PermissionRequest request) {
Log.d(TAG, "showRationalForStorage");
Toast.makeText(this, "\n" +
"The camera of the use permit is required", Toast.LENGTH_SHORT)
.show();
request.proceed();
}
private void releaseCameraAndPreview() {
if (cameraSource != null) {
cameraSource.release();
cameraSource = null;
}
}
private void requestCameraPermission() {
Log.i(TAG, "CAMERA permission has NOT been granted. Requesting permission.");
if (ActivityCompat.shouldShowRequestPermissionRationale(this,
Manifest.permission.CAMERA)) {
Log.i(TAG,
"Displaying camera permission rationale to provide additional context.");
Snackbar.make(findViewById(R.id.code_info), R.string.permission_camera_rationale,
Snackbar.LENGTH_INDEFINITE)
.setAction(R.string.ok, new View.OnClickListener() {
#Override
public void onClick(View view) {
ActivityCompat.requestPermissions(QRcodeReader.this,
new String[]{Manifest.permission.CAMERA},
REQUEST_CAMERA);
}
})
.show();
} else {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.CAMERA},
REQUEST_CAMERA);
}
}
#Override
public void onRequestPermissionsResult(int requestCode, #NonNull String permissions[],
#NonNull int[] grantResults) {
Log.d(TAG, "onRequestPermissionsResult");
switch (requestCode) {
case REQUEST_CAMERA: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
QRcodeReaderPermissionsDispatcher.onRequestPermissionsResult(this, requestCode, grantResults);
startCameraSource();
} else {
finish();
}
}
break;
}
}
}
The Manifest
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.sample.qrcodereadervision">
<uses-permission android:name="android.permission.CAMERA" />
<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.autofocus"/>
<application
android:theme="#style/AppTheme"
android:label="#string/app_name"
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:supportsRtl="true">
<activity android:name=".Activity.QRcodeReader">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<meta-data android:name="com.google.android.gms.vision.DEPENDENCIES" android:value="barcode"/>
</application>
</manifest>
pretty late for it but it will help you.
After that you have setup your camera and added preview and everything else. Just call
recreate();
Usage example in your Camera Activity like this.
camera = prepareCamera(camera); // a method to get camera instance
preview = createCameraPreview(camera) // a method which returns object of surfaceview
showCameraPreview(preview); // adding preview to the frame
recreate(); // <---This line should be called every time we setup a camera preview
Add the same permissions in manifest as well.