I'm trying to use a native android library called "ImageCropper" available here: https://github.com/ArthurHub/Android-Image-Cropper
I created android bindings, but when I try to consume it from XF custom rendered, it throws an error saying: "java.lang.NoClassDefFoundError: Failed resolution of: Landroidx/appcompat/app/AppCompatActivity"
I'm compiling my XF app with target version set to API 29. Not sure what I'm missing or how would I proceed to fix this issue. Any suggestions are heartly appreciated. Thanks.
PS: XF custom renderer: https://pastebin.com/85Mdsy8c
public class ImagePickerService : IImagePickerService
{
public IImageSourceUtility ImageSourceUtility => new ImageSourceUtility();
private void StartActivity()
{
var currentActivity = MainActivity.AppActivity;
if (currentActivity != null)
{
var cropImageOptions = new CropImageOptions();
cropImageOptions.MultiTouchEnabled = true;
cropImageOptions.Guidelines = CropImageView.Guidelines.On;
cropImageOptions.AspectRatioX = 1;
cropImageOptions.AspectRatioY = 1;
cropImageOptions.FixAspectRatio = true;
cropImageOptions.Validate();
var intent = new Intent();
intent.SetClass(currentActivity, Class.FromType(typeof(ImagePickerOnResultActivity)));
intent.PutExtra(CropImage.CropImageExtraSource, null as global::Android.Net.Uri); // Image Uri
intent.PutExtra(CropImage.CropImageExtraOptions, cropImageOptions);
currentActivity.StartActivity(intent);
}
else
{
throw new InvalidOperationException("Could not get current activity.");
}
}
public Task<ImageSource> PickImageAsync()
{
StartActivity();
return Task.Run(() =>
{
_waitHandle.WaitOne();
var result = _pickAsyncResult;
_pickAsyncResult = null;
return result;
});
}
private static ImageSource _pickAsyncResult;
private static EventWaitHandle _waitHandle = new AutoResetEvent(false);
// if crashes(in release mode after linking), see plugin desc for proguard config change required for this theme
[Activity(Label = "CropImageActivity", Theme = "@style/Base.Theme.AppCompat")]
//[Activity(Theme = "@style/Base.Theme.AppCompat")]
public class ImagePickerOnResultActivity : Activity
{
protected override void OnCreate(Bundle savedInstanceState)
{
//base.OnCreate(savedInstanceState);
// start activity
var x = CropImage.Activity();
x.SetGuidelines(CropImageView.Guidelines.On)
.Start(this);
}
protected override void OnActivityResult(int requestCode, [GeneratedEnum] Result resultCode, Intent data)
{
if (requestCode == CropImage.CropImageActivityRequestCode)
{
CropImage.ActivityResult result = CropImage.GetActivityResult(data);
if (resultCode == Result.Ok)
{
var croppedFileUri = new Uri(result.Uri.ToString());
_pickAsyncResult = ImageSource.FromFile(croppedFileUri.LocalPath);
_waitHandle.Set();
}
else if ((int)resultCode == CropImage.CropImageActivityResultErrorCode)
{
Java.Lang.Exception error = result.Error;
}
}
}
}
}
org GH repo (but bindings used here is outdated): https://github.com/matheusneder/Xamarin.Android.ImageCropper/tree/master/Source/Xamarin.Android.ImageCropper.App
Okay, so even with the target version set to API level 29, androidX packages were not being included for some reason. So, manually including AndroidX packages by adding the following package references in csproj file of the android project got rid of the above-mentioned error.
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.2.0.1" />
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.2.0.1" />
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
This library required the following additional packages:
<PackageReference Include="Xamarin.AndroidX.AppCompat" Version="1.1.0.1" />
<PackageReference Include="Xamarin.AndroidX.ExifInterface" Version="1.1.0.1" />
A better approach would be including these dependencies inside the binding library itself, but I could not figure out how to do it.
Anyway, this solution works for now, and I'm able to compile my XF project and use features from this library as expected.