Передача QR-кода / Штрих-кода
Столкнулся с такой проблемой, мне надо передать отсканированный QR-кода / Штрих-кода в TextView. Вылетает ошибка.
Фрагмент кода где ошибка:
private void takeBarcodePicture() {
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File photo = new File(Environment.getExternalStorageDirectory(), "pic.jpg");
imageUri = FileProvider.getUriForFile(PictureBarcodeActivity.this,
BuildConfig.APPLICATION_ID + ".provider", photo);
intent.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
startActivityForResult(intent, CAMERA_REQUEST);
}
Ошибка :
Process: com.example.application, PID: 4080
java.lang.IllegalArgumentException: Couldn't find meta-data for provider with authority com.example.application.provider
at androidx.core.content.FileProvider.parsePathStrategy(FileProvider.java:606)
at androidx.core.content.FileProvider.getPathStrategy(FileProvider.java:579)
at androidx.core.content.FileProvider.getUriForFile(FileProvider.java:417)
at com.example.application.PictureBarcodeActivity.takeBarcodePicture(PictureBarcodeActivity.java:174)
at com.example.application.PictureBarcodeActivity.onRequestPermissionsResult(PictureBarcodeActivity.java:91)
at androidx.core.app.ActivityCompat$1.run(ActivityCompat.java:519)
at android.os.Handler.handleCallback(Handler.java:739)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5221)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694)
04-01 07:54:20.333 1517-3658/system_process E/eglCodecCommon: glUtilsParamSize: unknow param 0x00008cdf
04-01 07:54:20.333 1517-3658/system_process E/eglCodecCommon: glUtilsParamSize: unknow param 0x00008824
Manifest:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="com.example.application"
tools:ignore="ExtraText">
<uses-feature
android:name="android.hardware.camera"
android:required="true" />
<uses-permission
android:name="android.permission.ACCESS_COARSE_LOCATION"
android:maxSdkVersion="22" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="com.google.android.things.permission.MANAGE_GNSS_DRIVERS" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.YOUR_PHONE_TYPE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android:windowSoftInputMode" />
<uses-feature android:name="android.hardware.location.gps" />
<uses-feature android:name="android.hardware.camera.autofocus" />
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".PictureBarcodeActivity"></activity>
<activity android:name=".ScannedBarcodeActivity" />
<activity android:name=".FragmentClientDocDate" />
<activity android:name=".PhotoSave" />
<activity android:name=".Fragment3" />
<activity android:name=".Fragment2" />
<activity android:name=".Fragment1" />
<activity android:name=".MainFtagment" />
<activity android:name=".PageFragment" />
<activity android:name=".CustomDialogFragment" />
<activity android:name=".ClientDocListDate" />
<activity android:name=".ClientActivity" />
<activity android:name=".DocActivity" />
<activity android:name=".UserActivity" />
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<intent-filter>
<action android:name="android.media.action.IMAGE_CAPTURE" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="${applicationId}.provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths" />
</provider>
<meta-data
android:name="com.google.android.gms.vision.DEPENDENCIES"
android:value="barcode" />
</application>
</manifest>
Ответы (2 шт):
Автор решения: Barmaley
→ Ссылка
Коллега,
У вас в коде 3 ошибки:
Environment.getExternalStorageDirectory()- уже неактуален, начиная то ли c API 29 или 30 он обьявлен устаревщим и в 30-й по-моему вообще не работает. Соответственно файл надо создавать во внутреннем хранилище вашего приложения- Открытая передача
UriчерезputExtra()также уже давно запрещена, требуется его маскирование с помощью в данном случаеFileProvider, где маскировка пути делается черезxml/provider_paths(после подсказки @АндрейМихалев попытку ввестиFileProviderу вас появилась, но неудачная - см. п. 3) - У вас везде используется
androidx, аFileProviderвы пытаетесь использовать отsupport
Корректный код, приблизительно такой:
//REQUEST_TAKE_PICTURE - идентификатор запроса, что-то типа 101
private void takePicture(Activity activity) {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(activity.getPackageManager()) != null) {
File photo;
try {
photo=File.createTempFile("IMG", ".jpg", activity.getFilesDir());
} catch (Exception ex) {
logger.warn("Can't create photo file", ex);
return;
}
imageUri = FileProvider.getUriForFile(activity, "com.mydomain.fileprovider", photo);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
activity.startActivityForResult(takePictureIntent, REQUEST_TAKE_PICTURE);
}
else {
logger.warn("No camera supporting intent is available!");
}
}
Автор решения: Darsi
→ Ссылка
Решил проблему другим способом, используя библиотеку Zxing. Вот код для тех кто столкнулся с такой же бедой:
Добавил зависимость в build
compile 'com.google.zxing:core:3.3.3'
compile 'com.journeyapps:zxing-android-embedded:3.6.0@aar'
Код сканера:
public class ScanZxing extends AppCompatActivity {
Button btnScan;
TextView tv_qr_readTxt;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_scan_zxing);
btnScan = (Button) findViewById(R.id.btnScan);
tv_qr_readTxt = (TextView) findViewById(R.id.tv_qr_readTxt);
btnScan.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
IntentIntegrator integrator = new IntentIntegrator(ScanZxing.this);
integrator.setDesiredBarcodeFormats(IntentIntegrator.ALL_CODE_TYPES);
integrator.setPrompt("Scan");
integrator.setCameraId(0);
integrator.setBeepEnabled(false);
integrator.setBarcodeImageEnabled(false);
integrator.initiateScan();
}
});
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
IntentResult result = IntentIntegrator.parseActivityResult(requestCode, resultCode, data);
if (result != null) {
if (result.getContents() == null) {
Log.e("Scan*******", "Cancelled scan");
} else {
Log.e("Scan", "Scanned");
tv_qr_readTxt.setText(result.getContents());
Toast.makeText(this, "Scanned: " + result.getContents(), Toast.LENGTH_LONG).show();
}
} else {
super.onActivityResult(requestCode, resultCode, data);
}
}
}
XML
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="20dp"
android:orientation="vertical">
<Button
android:id="@+id/btnScan"
android:layout_width="fill_parent"
android:layout_height="50dp"
android:layout_below="@+id/editText"
android:text="От сканируйте QR-код"
android:textAllCaps="false"
android:textSize="16sp" />
<TextView
android:id="@+id/tv_qr_readTxt"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
Тут можно найти способ как переделать для Fragment https://medium.com/@dev.jeevanyohan/zxing-qr-code-scanner-android-implementing-in-activities-fragment-custom-colors-faa68bfc761d