Hi can anyone teach me how to use zbar/zxing for qr code reader? I have tried many of the sample codes online but none seems to work. Btw im using android studio.
I used zxing-android-embedded. Handles the zxing-core for you, automatically opens the camera on a separate thread, and even has docs/examples for custom usage. Also, the authors commit often (every ~2 weeks) and respond fast to issues. It scans QR's and Barcodes out of the box.
Add the permissions for the Camera in your AndroidManifest.xml:
<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.autofocus" />
Add this to your build.gradle (app):
repositories {
jcenter()
}
dependencies {
compile 'com.journeyapps:zxing-android-embedded:3.0.2#aar'
compile 'com.google.zxing:core:3.2.0'
}
Create a callback in your Activity:
private BarcodeCallback callback = new BarcodeCallback() {
#Override
public void barcodeResult(BarcodeResult result) {
// Do something with the scanned QR code.
// result.getText() returns decoded QR code.
fooBar(result.getText());
}
#Override
public void possibleResultPoints(List<ResultPoint> resultPoints) {
}
};
onCreate()
mBarcodeView = (BarcodeView) findViewById(R.id.barcode_view);
// Choose only one!!!
mBarcodeView.decodeSingle(callback);
// Or
mBarcodeView.decodeContinuous(callback);
onResume()
mBarcodeView.resume();
onPause()
mBarcodeView.pause();
In your Activity's XML layout, add the BarcodeView
<com.journeyapps.barcodescanner.BarcodeView
android:id="#+id/barcode_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_centerVertical="true"
android:layout_centerHorizontal="true">
</com.journeyapps.barcodescanner.BarcodeView>
Hope this helps!
Related
I am trying to show live stream from camera & microphone in <video> html element.
In blazor file (sample.razor) I invoke method to request and show video:
protected override async Task OnAfterRenderAsync(bool firstRender)
{
await base.OnAfterRenderAsync(firstRender);
if (firstRender)
{
await JSRuntime.InvokeVoidAsync("requestMediaAndShow");
}
}
In javascript file (sample.js) I request stream and assign to video html element.
// Create request options
let options = {
audio: true,
video: true
};
// Request user media
navigator.mediaDevices
.getUserMedia(options)
.then(gotLocalStream)
.catch(logError);
But when I am requesting i catch an error like "NotAllowedError: Permission denied".
AndroidManifest.xml contains:
<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
MainActivity.cs contains:
public class MainActivity : MauiAppCompatActivity
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
ActivityCompat.RequestPermissions(this, new[] { Manifest.Permission.Camera, Manifest.Permission.RecordAudio, Manifest.Permission.ModifyAudioSettings }, 0);
}
}
Any ideas how to request audio and video stream by javascript in BlazorWebView natively on android?
PS. On both on website and natively on Windows platform works great and no extra permissions are required.
Although the Android permissions seem to be granted OK, I suspected the website permissions were not. Not sure if the author of this question is the same person, but an issue was opened on the .NET MAUI repo as well about this.
While we are looking into making this work out of the box, another helpful user has posted this workaround for now.
Implement your own handler like so
public class MauiWebChromeClient : WebChromeClient
{
public override void OnPermissionRequest(PermissionRequest request)
{
request.Grant(request.GetResources());
}
}
public class MauiBlazorWebViewHandler : BlazorWebViewHandler
{
protected override WebChromeClient GetWebChromeClient()
{
return new MauiWebChromeClient();
}
}
And register this handler in your MauiProgram.cs:
builder.ConfigureMauiHandlers(handlers =>
{
handlers.AddHandler<IBlazorWebView, MauiBlazorWebViewHandler>();
});
This will automatically grant all the requested permissions from the web side of things.
I think you are missing some parts of the permission checks. You should read this section about runtime permissions that were introduced in Android 6.0. For example, I cannot see any override of OnRequestPermissionsResult in MainActivity.
https://learn.microsoft.com/en-us/xamarin/android/app-fundamentals/permissions?tabs=macos#runtime-permission-checks-in-android-60
In my onCreate I call the following function to detect the weather.
private void detectWeather() {
if( !checkLocationPermission() ) {
return;
}
Awareness.getSnapshotClient(this).getWeather()
.addOnSuccessListener(new OnSuccessListener<WeatherResponse>() {
#Override
public void onSuccess(WeatherResponse weatherResponse) {
Weather weather = weatherResponse.getWeather();
}
})
.addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(#NonNull Exception e) {
Log.e("Testing", "Could not get weather: " + e);
}
});
}
In my Manifest file I have added the following meta data and permissions:
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="com.google.android.gms.permission.ACTIVITY_RECOGNITION" />
<meta-data
android:name="com.google.android.awareness.API_KEY"
android:value="MYKEY"/>
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="MYKEY"/>
And in my Gradle file I've added the following dependencies.
compile 'com.google.android.gms:play-services:+'
compile 'com.google.android.gms:play-services-gcm:+'
compile 'com.google.android.gms:play-services-location:+'
compile 'com.google.android.gms:play-services-awareness:+'
The app launches fine and gets to the awareness API, however it throws the following error in the log: com.google.android.gms.common.api.ApiException: 15. I can't really find the explanation for this error in the documentation nor on Google/Stackoverflow. Am I missing something obvious?
For future readers, weather and place is now deprecated in the Google Awareness API.
An alternative is the NumberEight SDK, which can do a lot more than Awareness (although no regioning is available at the time of writing).
It performs a wide variety of context recognition tasks on both iOS and Android including:
Real-time physical activity detection
Current place categories
Motion detection
Reachability
Local weather
It can also record user context for reports and analysis via the online portal.
To quickly receive weather updates in Java, you would write:
NumberEight ne = new NumberEight();
ne.onWeatherUpdated(
new NumberEight.SubscriptionCallback<NEWeather>() {
#Override
public void onUpdated(#NonNull Glimpse<NEWeather> glimpse) {
Log.d("CurrentWeather", glimpse.getMostProbable().toString());
}
});
Here are some iOS and Android example projects.
Disclosure: I'm one of the developers.
i have a sales summary print out and has a QR Code ,
i want to develop an app (IOS and android) that reads the QR code , extract all information,do some calculations,and display in specific form , i tried zxing library but it did not extract all information from the receipt.any tip?
You can use google vision API to achieve this. I personally used this and found it great. The below code snippets should help you.
Put this below line in the gradle.
compile 'com.google.android.gms:play-services:9.4.0'
Use BarcodeDetector and CameraSource classes to capture the QR code on real time and decode it.
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() { // Use the post method of the TextView
public void run() {
barcodeInfo.setText( // Update the TextView
barcodes.valueAt(0).displayValue
);
}
});
}
}
});
Use a SparseArray to fetch the detections and the displayValue of the elements of this sparse array returns the deocded string.
After extracting the string one can do anything, be it displaying the string or make some calculation out of it etc.
This library is the most popular and easiest of reading QR codes in your Android application.
You should also have a look at the Wiki section of this library for learning about how to integrate this library into your Android Application and how to use this library.
This is how you can use this library.
1. Add this library to your project by adding following line into your dependencies inside build.gradle(Module: app) file
compile 'com.github.nisrulz:qreader:2.0.0'
2. Then, after syncing project files, add the SurfaceView element provided by this library into your XML layout file.
<SurfaceView
android:id="#+id/camera_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
3. Declare the SurfaceView & QREader inside your Activity's Java file & then initialize it inside onCreate() method.
class MainActivity extends AppCompatActivity{
private SurfaceView mySurfaceView;
private QREader qrEader;
#Override
protected void onCreate(final Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Setup SurfaceView
// -----------------
mySurfaceView = (SurfaceView) findViewById(R.id.camera_view);
// Init QREader
// ------------
qrEader = new QREader.Builder(this, mySurfaceView, new QRDataListener() {
#Override
public void onDetected(final String data) {
Log.d("QREader", "Value : " + data);
text.post(new Runnable() {
#Override
public void run() {
text.setText(data);
}
});
}
}).facing(QREader.BACK_CAM)
.enableAutofocus(true)
.height(mySurfaceView.getHeight())
.width(mySurfaceView.getWidth())
.build();
}
4. Initialize it inside onResume()
#Override
protected void onResume() {
super.onResume();
// Init and Start with SurfaceView
// -------------------------------
qrEader.initAndStart(mySurfaceView);
}
There are many more possibilities you can do with this library, so I recommend you to visit the GitHub repository and check it out. It's worth a shot!
I'm trying to make a service that will run every 10 seconds to check a queue and if there is some data in the queue upload the given uri (uri of a picture just taken from the app) to a certain url.
I have created something along these lines
public QueueProcessor(final Context context){
this.mContext = context.getApplicationContext();
}
/**
* Starts processing the items on a separate thread.
*/
public void process() {
Runnable running = new Runnable() {
#Override
public void run() {
try{
Log.i(RUN_QP_TAG, "Processing queue");
// more here
isRunning = true;
Queue theQ = Queue.getInstance();
if(theQ.getSize() > 0){
WorkQItem itm = theQ.pop();
if(itm.hasImage()){
pushImageUploadToProcess(itm);
}
}
} catch (Exception e) {
// TODO: handle exception
}
finally{
//also call the same runnable to call it at regular interval
handler.postDelayed(this, 10000);
}
}
};
new Thread(running).start();
}
The pushImageUploadToProcess takes the WorkQItem and tries to upload the image from the item (which is saved as String picUri) by opening the uri and writing the bytes. However I get a permissions denied exception when trying to open the picUri location.
MediaDocumentsProvider uri content://com.android.providers.media.documents/document/image%3A531 from pid=795, uid=10327 requires android.permission.MANAGE_DOCUMENTS, or grantUriPermission()
How can I allow this Thread/Runnable to have access to the URI?
Note I have tried the upload directly from a button event and it does work.
I have the following permissions in the manifest:
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.READ_PROFILE" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.MANAGE_DOCUMENTS" />
You should implement runtime permission, for that use below code
PermissionsManager.getInstance().requestAllManifestPermissionsIfNecessary(this, new PermissionsResultAction() {
#Override
public void onGranted() {
// Proceed with initialization
}
#Override
public void onDenied(String permission) {
// Notify the user that you need all of the permissions
}
});
add below dependency in your app gradle
compile 'com.anthonycr.grant:permissions:1.0'
It looks like the actual permission error is not the real issue. The real issue was the way I was choosing and picking the image.
I ended up using https://gist.github.com/Mariovc/f06e70ebe8ca52fbbbe2 this picker and it seemed to work without any issues.
I tweaked this code a little bit to suit my needs as any image picked from the camera needed to be saved too so that if there are several images being done and each is needed for later use the relative uri initially will get overwritten therefore you need a fixed one (e.g: to be saved).
I am creating a hybrid application by using android and offline html5 pages in android asset.
navigator.online is not working in Android Webview.
Please help
If anyone is still searching for this one. The solution for me was to register a broadcast receiver in my activity to detect connection change.
#Override
protected void onPause() {
super.onPause();
if (connectivityChangeReceiver!=null) unregisterReceiver(connectivityChangeReceiver);
}
#Override
protected void onResume()
{
super.onResume();
IntentFilter intentFilter = new IntentFilter("android.net.conn.CONNECTIVITY_CHANGE");
registerReceiver(connectivityChangeReceiver,intentFilter);
}
private BroadcastReceiver connectivityChangeReceiver = new BroadcastReceiver() {
public void onReceive(Context context, Intent intent)
{
mWebView.setNetworkAvailable(isNetworkAvailable(context));
}
};
Make sure that you provide below permissions in the AndroidMenifest.xml file:
<uses-permission android:name="android.permission.INTERNET />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
you might want to add the following line of code for your events
document.addEventListener("online", onOnline, false);
document.addEventListener("offline", onOffline, false);
make sure you check the values in the functions function onOnline(){} & function onOffline(){}
Are you sure you are not mistaking the spelling?
it should be navigator.onLine (camelCase)
Webview is partially supported. Please check browser compatibility in the documentation: documentation link