Using ZXingScannerPage with XF, my content page has weird behavior - xamarin

I am making an app in xamarin forms of which I will have a login similar to that of whatapp web, an on-screen qr that will be scanned by the phone, in the emulator with visual studio 2017 I have no problems, but when I export the app to an apk and the I install on a mobile device, the app reads the qr and returns to the previous login screen, not showing any reaction, which should be to go to the next screen where I have a dashboard.
What can be? I enclose my code used.
btnScanQRCode.IsEnabled = false;
var scan = new ZXingScannerPage();
scan.OnScanResult += (result) =>
{
scan.IsScanning = false;
Device.BeginInvokeOnMainThread(async () =>
{
await Application.Current.MainPage.Navigation.PopAsync();
var resultado = JsonConvert.DeserializeObject<QrCode>(result.Text);
JObject qrObject = JObject.Parse(JsonConvert.SerializeObject(resultado));
JsonSchema schema = JsonSchema.Parse(SettingHelper.SchemaJson);
bool valid = qrObject.IsValid(schema);
if (valid == true)
{
App.Database.InsertQrCode(resultado);
QrCode qr = App.Database.GetQrCode();
await _viewModel.Login();
await Navigation.PushAsync(new Organization());
}
else
{
await DisplayAlert("False", JsonConvert.SerializeObject(resultado), "ok");
}
});
};
await Application.Current.MainPage.Navigation.PushAsync(scan);
btnScanQRCode.IsEnabled = true;

This was originally a comment, but through the writing i realized this is the answer.
You need to debug your code. Attach a device and deploy the app in Debug config. Step through your code and see where it fails.
It sounds like it's crashing silently and probably on the line where you Deserialize result.Text in a QrCode. result.Text is just a string and will never deserialize into an object. You probably need a constructor that takes a string like QrCode(result.Text).

First scan then use the result to do other things in your app.
var scanner = new ZXing.Mobile.MobileBarcodeScanner();
var result = await scanner.Scan();
Check for proper camera permissions. I bet your problem is there.

Related

AWS Chime SDK js does not recognize video and audio elements

I am attempting to get the basic tutorial for the AWS Chime SDK to work in our application and the meetingSession.audioVideo.listVideoInputDevices() always returns nothing/null.
I am running this on lastest chrome, my operating system is a windows 10 workspace instance. I have headphones plugged in; but that shouldn't make a difference.
My expected result is to return at least one device for the video. Here is the output from the Logger.
2020-08-26T15:29:19.127Z [INFO] MyLogger - attempting to trigger media device labels since they are hidden
chime-bundle.js:1 2020-08-26T15:29:19.133Z [INFO] MyLogger - unable to get media device labels
chime-bundle.js:1 2020-08-26T15:29:19.134Z [INFO] MyLogger - API/DefaultDeviceController/listVideoInputDevices null -> []
chime-bundle.js:1 Uncaught (in promise) TypeError: Cannot read property 'deviceId' of undefined
*Note. The video and audio elements are not hidden.
I have tried the code snippits from various demos. Which are all just a copy of AWS's walkthrough. So pretty much zero information. I have researched how the audio devices work in html5 and looking through the files provided in the sdk-js, I am even more confused. Can someone point me in the right direction?
Here is the basic code, you can get it, and a description from the link above.
var fetchResult = await window.fetch(
window.encodeURI("<our endpoint for backend (running c# instead of node)>",
{
method: 'POST'
}
);
let result = await fetchResult.json();
console.log("Result from Chime API:", result);
const logger = new ConsoleLogger('MyLogger', LogLevel.INFO);
const deviceController = new DefaultDeviceController(logger);
const meetingResponse = result.JoinInfo.Meeting;
const attendeeResponse = result.JoinInfo.Attendee;
const configuration = new MeetingSessionConfiguration(meetingResponse, attendeeResponse);
// In the usage examples below, you will use this meetingSession object.
const meetingSession = new DefaultMeetingSession(
configuration,
logger,
deviceController
);
console.log("MEETING SESSION", meetingSession);
//SETUP AUDIO
const audioElement = document.getElementById('notary-audio');
meetingSession.audioVideo.bindAudioElement(audioElement);
const videoElement = document.getElementById('notary-video');
// Make sure you have chosen your camera. In this use case, you will choose the first device.
const videoInputDevices = await meetingSession.audioVideo.listVideoInputDevices();
// The camera LED light will turn on indicating that it is now capturing.
// See the "Device" section for details.
await meetingSession.audioVideo.chooseVideoInputDevice(videoInputDevices[0].deviceId);
const observer = {
audioVideoDidStart: () => {
console.log('Started');
},
audioVideoDidStop: sessionStatus => {
// See the "Stopping a session" section for details.
console.log('Stopped with a session status code: ', sessionStatus.statusCode());
},
audioVideoDidStartConnecting: reconnecting => {
if (reconnecting) {
// e.g. the WiFi connection is dropped.
console.log('Attempting to reconnect');
}
},
// videoTileDidUpdate is called whenever a new tile is created or tileState changes.
videoTileDidUpdate: tileState => {
// Ignore a tile without attendee ID and other attendee's tile.
if (!tileState.boundAttendeeId || !tileState.localTile) {
return;
}
// videoTileDidUpdate is also invoked when you call startLocalVideoTile or tileState changes.
console.log(`If you called stopLocalVideoTile, ${tileState.active} is false.`);
meetingSession.audioVideo.bindVideoElement(tileState.tileId, videoElement);
localTileId = tileState.tileId;
},
videoTileWasRemoved: tileId => {
if (localTileId === tileId) {
console.log(`You called removeLocalVideoTile. videoElement can be bound to another tile.`);
localTileId = null;
}
}
};
meetingSession.audioVideo.addObserver(observer);
meetingSession.audioVideo.start();

Connect Xamarin to DB

I'm starting learning Xamarin and i face problem in connecting app with DB. i built rest web services with method get and i uplode it in host. after that i add this code in app
private async Task<List<testClass>> GetlistAsync()
{
var uri = new Uri(string.Format("my web service link", string.Empty));
var response = await httpClient.GetAsync(uri);
List<testClass> Items = new List<testClass>();
if (response.IsSuccessStatusCode)
{
var content = await response.Content.ReadAsStringAsync();
Items = JsonConvert.DeserializeObject<List<testClass>>(content);
}
return Items;
}
the problem is whenever i add run. the code will stop after httpclint. getasync line without doing lines after it
pleas help as fast as possible
thanks

How to show all images from a folder in Xamarin Cross-Platform app?

I am using VS 2017 to create a cross platform (UWP, Android, iOS) Xamarin app. I am trying to show all images from a folder on device as thumbnails (similar to gallery app, sample screenshot attached).
I have looked into WrapLayout sample code provided on Xamarin website (Link), but it's loading all images from internet using JSON
protected override async void OnAppearing()
{
base.OnAppearing();
var images = await GetImageListAsync();
foreach (var photo in images.Photos)
{
var image = new Image
{
Source = ImageSource.FromUri(new Uri(photo + string.Format("?width={0}&height={0}&mode=max", Device.OnPlatform(240, 240, 120))))
};
wrapLayout.Children.Add(image);
}
}
async Task<ImageList> GetImageListAsync()
{
var requestUri = "https://docs.xamarin.com/demo/stock.json";
using (var client = new HttpClient())
{
var result = await client.GetStringAsync(requestUri);
return JsonConvert.DeserializeObject<ImageList>(result);
}
}
I have also looked into Xamarin Media Plugin (Link), but it shows only one image at a time. Sample code -
await CrossMedia.Current.Initialize();
var file = await CrossMedia.Current.PickPhotoAsync();
if (file == null)
return;
MainImage.Source = ImageSource.FromStream(() =>
{
var stream = file.GetStream();
file.Dispose();
return stream;
});
But I am unable to find a way to implement these two (or any other methods) in such a way that I can create my own gallery section in my app.
You need to create an Activity in your specific platform. This activity will be launched as an intent throught your PCL project using, for instance, Dependency Services.
In this custom Activity you should have a GridView which fills its source from the current directory if the file fits your restrictions, such a specific extension, size, etc.
Finally, to get the selected image you just send the image path or whatever you need to the PCL project with DependencyService.

Is it possible to launch native apps using Microsoft bot framework?

I am creating a Cortana skill on the Cortana canvas, I have a button.
I wanted to know if it possible to have an 'imback' type of button to open a webpage.
Ye, for example
var message = context.MakeMessage() as IMessageActivity;
message.ChannelData = JObject.FromObject(new
{
action = new { type = "LaunchUri", uri = "skype:echo123?call" }
});
await context.PostAsync(message);
this code will start a call with echo123 user on skype
Reference: https://learn.microsoft.com/en-us/cortana/tutorials/bot-skills/bot-entity-channel-data
You can supply an openUrl to a card action, or even use ChannelData to send a LaunchUri command, deep linking to an application. (I haven't tried this, but I assume 'http://websitename.com' will launch in the Cortana host platform's default browser.)
activity.ChannelData = new {
action = new { type = "LaunchUri", uri = "http://websitename.com"}
};

Geofence is not being triggered in the background in windows phone 8.1

I'm trying to implement geofencing in Windows phone 8.1. First I wanted to create a sample Project to understand how it Works, but i couldnt make it works. What I'm trying to achieve is basically, I'll set the coordinates and close the app by pressing back button and it will trigger a toast notification when the phone is in the area of interest.
I've created a blank Windows phone(silverlight) 8.1 Project(geofence_test_01) and added a Windows RT Component Project(BackgroundTask) into the same solution. Added a reference for BackgroundTask in the geofence_test_01 Project.
ID_CAP_LOCATION is enabled in the app manifest.
MainPage.xaml has only one button to start geofencing.
<Button Name="btnStart" Content="Start" Click="btnStart_Click"/>
In btnSave_Click, I call a method which creates the geofence and registers the background task.
private void btnStart_Click(object sender, RoutedEventArgs e)
{
Init_BackgroundGeofence();
registerBackgroundTask();
}
private async Task Init_BackgroundGeofence()
{
//----------------- Crating Geofence ---------------
var geofenceMonitor = GeofenceMonitor.Current;
var geoId = "building9";
var positionBuilding9 = new BasicGeoposition()
{
Latitude = 47.6397,
Longitude = -122.1289
};
var geofence = new Geofence(geoId, new Geocircle(positionBuilding9, 100),
MonitoredGeofenceStates.Entered | MonitoredGeofenceStates.Exited,
false, TimeSpan.FromSeconds(10));
geofenceMonitor.Geofences.Add(geofence);
}
private async Task registerBackgroundTask()
{
//----------------- Register Background Task ---------------
var backgroundAccessStatus =
await BackgroundExecutionManager.RequestAccessAsync();
var geofenceTaskBuilder = new BackgroundTaskBuilder
{
Name = "GeofenceBackgroundTask",
TaskEntryPoint = "BackgroundTask.GeofenceBackgroundTask"
};
var trigger = new LocationTrigger(LocationTriggerType.Geofence);
geofenceTaskBuilder.SetTrigger(trigger);
var geofenceTask = geofenceTaskBuilder.Register();
}
And finally, in BackgroundTask, I've the following code:
namespace BackgroundTask
{
public sealed class GeofenceBackGroundTask : IBackgroundTask
{
public void Run(IBackgroundTaskInstance taskInstance)
{
var geofenceMonitor = GeofenceMonitor.Current;
var geoReports = geofenceMonitor.ReadReports();
var geoId = "building9";
foreach (var geofenceStateChangeReport in geoReports)
{
var id = geofenceStateChangeReport.Geofence.Id;
var newState = geofenceStateChangeReport.NewState;
if (id == geoId && newState == GeofenceState.Entered)
{
//------ Call NotifyUser method when Entered -------
notifyUser();
}
}
}
private void notifyUser()
{
var toastTemplate = ToastTemplateType.ToastText02;
var toastXML = ToastNotificationManager.GetTemplateContent(toastTemplate);
var textElements = toastXML.GetElementsByTagName("text");
textElements[0].AppendChild(toastXML.CreateTextNode("You are in!"));
var toast = new ToastNotification(toastXML);
ToastNotificationManager.CreateToastNotifier().Show(toast);
}
}
}
I get no error when building and deploying this in the emulator. I set a breakpoint in the backgroundTask but I've not seen that part of code is called yet. It never hits the breakpoint. I test it by using Additional Tools of the emulator, in Location tab, by clicking somewhere in my geofence area on the map, waiting for a while, but it never hits the breakpoint. Hope somebody can tell me what i am missing here...
I've checked these following links to build this application:
http://www.jayway.com/2014/04/22/windows-phone-8-1-for-developers-geolocation-and-geofencing/
Geofence in the Background Windows Phone 8.1 (WinRT)
Toast notification & Geofence Windows Phone 8.1
http://java.dzone.com/articles/geofencing-windows-phone-81
Thanks
You can download the project here:
https://drive.google.com/file/d/0B8Q_biJCWl4-QndYczR0cjNhNlE/view?usp=sharing
---- Some clues
Thanks to Romasz, I've checked the Lifecycle events and i see "no background tasks" even after registerBackgroundTask() is executed.... Apparently there is something wrong/missing in registerBackgroundTask() method.
I've tried to build my sample (it was easier for me to build a new one) basing on your code and it seems to be working. You can take a look at it at my GitHub.
There are couple of things that may have gone wrong in your case:
remember to add capabilities in WMAppManifest file (IS_CAP_LOCATION) and Package.appxmanifest (Location)
check the names (of namespaces, classes and so on) in BackgroundTask
check if your BackgroundTask project is Windows Runtime Componenet and is added to your main project as a reference
I know you have done some of this things already, but take a look at my sample, try to run it and maybe try to build your own from the very beginning.
Did you add your background task in the Package.appxmanifest under Declarations with the correct supported task types (Namely Location)?

Resources