glide-xamarin-android
glide-xamarin-android copied to clipboard
Subclass ViewTarget
I'm trying to port this code to C# and this is what I've got so far
public class GlideImageGetter : Java.Lang.Object, Html.IImageGetter, Drawable.ICallback
{
private Context mContext;
private TextView mTextView;
private HashSet<ImageGetterViewTarget> mTargets;
public static GlideImageGetter Get(View view)
{
return (GlideImageGetter)view.GetTag(Resource.Id.drawable_callback_tag);
}
public void Clear()
{
GlideImageGetter prev = Get(mTextView);
if (prev == null)
return;
foreach (var target in prev.mTargets)
{
Glide.Clear(target);
}
}
public GlideImageGetter(Context context, TextView textView)
{
mContext = context;
mTextView = textView;
Clear();
mTargets = new HashSet<ImageGetterViewTarget>();
mTextView.SetTag(Resource.Id.drawable_callback_tag, this);
}
public Drawable GetDrawable(string source)
{
UrlDrawable urlDrawable = new UrlDrawable();
Glide.With(mContext)
.Load(source)
.DiskCacheStrategy(DiskCacheStrategy.All)
.Into(new ImageGetterViewTarget(mTextView, urlDrawable, mTargets));
return urlDrawable;
}
public void InvalidateDrawable(Drawable who)
{
mTextView.Invalidate();
}
public void ScheduleDrawable(Drawable who, IRunnable what, long when) { }
public void UnscheduleDrawable(Drawable who, IRunnable what) { }
private class ImageGetterViewTarget : ViewTarget
{
private UrlDrawable mDrawable;
public ImageGetterViewTarget(TextView view, UrlDrawable drawable, HashSet<ImageGetterViewTarget> mTargets) : base(view)
{
mTargets.Add(this);
mDrawable = drawable;
}
public void OnResourceReady(Java.Lang.Object resource, IGlideAnimation glideAnimation)
{
Rect rect;
TextView view = (TextView)View;
GlideDrawable drawable = (GlideDrawable)resource;
if (drawable.IntrinsicWidth > 100)
{
float width;
float height;
if (drawable.IntrinsicWidth >= view.Width)
{
float downScale = (float)drawable.IntrinsicWidth / view.Width;
width = drawable.IntrinsicWidth / downScale;
height = drawable.IntrinsicHeight / downScale;
}
else
{
float multiplier = (float)view.Width / drawable.IntrinsicWidth;
width = drawable.IntrinsicWidth * multiplier;
height = drawable.IntrinsicHeight * multiplier;
}
rect = new Rect(0, 0, Java.Lang.Math.Round(width), Java.Lang.Math.Round(height));
}
else
{
rect = new Rect(0, 0, drawable.IntrinsicWidth * 2, drawable.IntrinsicHeight * 2);
}
drawable.Bounds = rect;
mDrawable.Bounds = rect;
mDrawable.SetDrawable(drawable);
if (drawable.IsAnimated)
{
mDrawable.SetCallback(Get(view));
drawable.SetLoopCount(GlideDrawable.LoopForever);
drawable.Start();
}
view.Text = view.Text;
view.Invalidate();
}
}
}
When I build the project, this error pops up
GlideImageGetter_ImageGetterViewTarget is not abstract and does not override abstract method onResourceReady(Object,GlideAnimation) in Target
I looked into binding interface Com.Bumptech.Glide.Request.Target.ITarget and couldn't find that abstract method but it does exist in java code. I guess the generic type Transition<? super R> transition
is the cause. If so, is there any solution to this?
Similar problem. Trying to extend SimpleTarget so I can save the image to disk, but can't override OnResourceReady and get the same error as OP when compiling.
Thanks, I will look into that and will notify you.
Same here... Would be great to derive from BasicTarget and override onResourceReady
Unless you tell me there's a better way to use Glide to set the background of a Layout
Thanks in advance!
It seems that SimpleTarget and BaseTarget are abstract classes. The Xamarin binding has problems with abstract classes and methods with abstract input types. In theory it should generate something with a Java.Lang.Object as type but appearantly it doesn't. Not sure how to fix. Any suggestions?
As @Speedrockracer said, I had to disable a few methods in Transforms file. Glide is quite complicated library compared to Picasso so I will ask to someone from Xamarin team and maybe they will recommend an intuitive idea.
I tried to fix the binding but didn't have any success there. It is indeed very complicated. Also tried the following workaround. Very hacky and it didn't work. Wont even go into the SetResource method.. but crashes with a ClassCastException. Maybe someone here gets inspired and can make it work?
I'm trying to load the resulting bitmap in a SubsampelingScaleImageView for zooming. If someone knows a better way without using glide feel free to drop me a line.
void LoadImage() {
Glide.With(this).Load(url).Into(new ImageLoadTarget(_postImageView, _dummyImageView));
}
private class ImageLoadTarget: BitmapImageViewTarget {
SubsamplingScaleImageView _imageView;
public ImageLoadTarget(SubsamplingScaleImageView imageView, ImageView realImageView) : base(realImageView) {
_imageView = imageView;
}
protected override void SetResource(Bitmap bitmap)
{
_imageView.SetImage(ImageSource.InvokeBitmap(bitmap));
}
}
I've updated to 3.8.0 and haven't tested yet. Could you give a chance to see that helps ?