Ffimageloading: AddBackgroundColor transformation

Created on 31 Mar 2017  路  28Comments  路  Source: luberda-molinet/FFImageLoading

colorimage
161l

How can I set the background color on a image that uses CircleTransformation?

The image is transparent, I want to change backgroundcolor and tint.

Here is my code:

var taskImage = ImageService.Instance.LoadFile(filename)
.ErrorPlaceholder("161L.png", ImageSource.ApplicationBundle)
.LoadingPlaceholder("161L.png", ImageSource.ApplicationBundle);

taskImage.Transform(new TintTransformation(255, 95, 28, 128) { EnableSolidColor = true });
taskImage.Transform(new CircleTransformation(10, "#b0e0e6"));
taskImage.Into(imageView);

I want it to be like screenshot attached,

enhancement up-for-grabs

Most helpful comment

I can add a new BackgroundColorTransformation which could be used in combination with other transformations.

Eg:

<ffimageloading:CachedImage HorizontalOptions="Center" VerticalOptions="Center"
    LoadingPlaceholder="loading.png" ErrorPlaceholder="error.png" DownsampleToViewSize="true"
    Aspect="AspectFit" HeightRequest="400" WidthRequest="400" Source="{Binding ImageUrl}">
    <ffimageloading:CachedImage.Transformations>
        <fftransformations:BackgroundColorTransformation Color="#FFFFFF"/>
        <fftransformations:CircleTransformation/>
    </ffimageloading:CachedImage.Transformations>
</ffimageloading:CachedImage>

What do you think?

All 28 comments

Have you tried setting the background on the imageView?

Yes, image is coloured, but it not circled.

I try to make the image colored and circled

so you set the background color, imageView.BackgroundColor, before you use it? If the image is transparent, it should just show the background color of the imageView.

It have background color but not circled.

Maybe I need to make a new Transformation
like this
CircledWithFillTransformation
https://github.com/luberda-molinet/FFImageLoading/issues/307
?

imageView.BackgroundColor = UIColor.Yellow;
taskImage.Transform(new CircleTransformation(10, "#b0e0e6"));

simulator screen shot 31 mar 2017 21 03 03

You need to make the actual imageView into a circle. For Xamarin.iOS this seems to work.

OK
I can do this

One more question, is it possible to do a Transformation only on the placeholder image, not the downloaded image?

I saw your other question. I am not sure however you can just change the transformation on the Success event.

I can try that,
Do you have a sample showing how to do this?

Nah I don't happen to have a sample.

No success

I want to TintTransformation only on ErrorPlaceholder and LoadingPlaceholder
What is wrong?

            var taskImage2 = ImageService.Instance.LoadUrl(imageURL)

.ErrorPlaceholder("161L.png", ImageSource.ApplicationBundle)
.LoadingPlaceholder("161L.png", ImageSource.CompiledResource)
;

            taskImage2.Success((size, loadingResult) =>
            {
                aSuccess = true;

                //taskImage2.Transform(new TintTransformation(100, 12, 28, 12) { EnableSolidColor = true });

            });


                if (aSuccess != true)
                    taskImage2.Transform(new TintTransformation(255, 95, 28, 128) { EnableSolidColor = true });


            taskImage2.Transform(new CircleTransformation(10, "#b0e0e6"));

            taskImage2.Into(imageView);

well you need to change the transformation inside the Success Command. That code is ran when the images is loaded. Anything outside that runs before that so that if (aSuccess != true) statement runs when you create the image not when the success is evaluated. You can also use the other Callbacks: Error or Finish.

I tried but did not figure out how

How can I remove a TintTransformation inside this?
taskImage2.Success((size, loadingResult) =>
{
aSuccess = true;

            });

you can't do taskImage2.Transform.Clear() inside of Success?

I added this:

    taskImage2.Success((size, loadingResult) =>
            {
                aSuccess = true;
            taskImage2.Transformations.Clear();// .Transform.Clear();
            });

the image is still transformed

Try taskImage2.Transformations = new List(). Sometimes Clear() doesn't raise the onPropetyChanged event to trigger updating the UI.

taskImage2.Transformations = new List();
Thus does not compile

I also add this
taskImage2.Transform(new CircleTransformation(10, "#b0e0e6"));
but it does not have any effect

            taskImage2.Success((size, loadingResult) =>
            {
                aSuccess = true;
        //      taskImage2.Transformations = new List();
     taskImage2.Transformations.Clear();// .Transform.Clear();
                taskImage2.Transform(new CircleTransformation(10, "#b0e0e6"));
            });

I meant = new List<ITransformation>();

taskImage2.Transformations = new List();

does not compile:

Property or indexer `FFImageLoading.Work.TaskParameter.Transformations' cannot be assigned to (it is read-only) (CS0200) (Simple.iOS.Sample)

Hmm yeah I am out of ideas.

Seems to be difficult to only add TintTransformation on placeholders

an easy solution is just to skip
TintTransformation
and add this before loading on the placeholder images

I have one strange idea.
For implementing this you can create a custom control.
Something like this:

var control = new AbsoluteLayout(); control.Children.Add(imageBackground, new Rectangle(0,0,1,1), Flags.All); control.Children.Add(mainImage, new Rectangle(0,0,1,1), Flags.All);

I have now just one issue
On android the tint color is not saved in the bitmap I create

Do you see any reason?

    public override void OnBindViewHolder(RecyclerView.ViewHolder viewHolder, int position)
    {
        var item = Items[position];

        var vh = viewHolder as ViewHolder;

        vh.Title.Text = position.ToString();
        vh.ItemView.Tag = position;


        Android.Graphics.Drawables.Drawable drawable = context.Resources.GetDrawable(Resource.Drawable.ic_365);
        drawable.SetTint(Color.Red);

        drawable.SetFilterBitmap(true);


        //      drawable.SetColorFilter(Color.RoyalBlue);


        //  Bitmap bitmap = BitmapFactory.DecodeResource(context.Resources, Resource.Drawable.ic_365);
        //  bitmap. .SetTint(Color.Red);



        Bitmap bitmap = ((BitmapDrawable)drawable).Bitmap;

    //  ((BitmapDrawable)drawable).SetTint(Color.Pink);
        //      bitmap.co .SetColorFilter(ImageColor);

        string folder = Environment.GetFolderPath(Environment.SpecialFolder.Personal);
        string localFilename = "ic_365.png";
        string localPath = Path.Combine(folder, localFilename);


//      File.Delete(localPath);

        if (File.Exists(localPath) == false)
        {
            using (var os = new FileStream(localPath, FileMode.CreateNew))
            {
                bitmap.Compress(Bitmap.CompressFormat.Png, 100, os);
            }
        }


        //  vh.Image.SetBackgroundColor(Color.Green);
        //      vh.Image.SetImageDrawable(drawable);


        GradientDrawable shape2 = new GradientDrawable();

        shape2.SetSize(vh.Image.Width, vh.Image.Width);
        shape2.SetShape(ShapeType.Oval);

        shape2.SetColor(Color.Blue);
        vh.Image.SetBackgroundDrawable(shape2);


        /*
            ImageService.Instance.LoadFile(localPath)
              .Retry(3, 200)
              .DownSample(100, 100)
        .Transform(new CircleTransformation(10, "#b0e0e6"))
                        .LoadingPlaceholder(localPath, FFImageLoading.Work.ImageSource.Filepath)
              .ErrorPlaceholder(localPath, FFImageLoading.Work.ImageSource.Filepath)
              .Into(vh.Image);

    */
        ImageService.Instance.LoadUrl(item)
           .Retry(3, 200)
           .DownSample(100, 100)
                        .Transform(new CircleTransformation(10, "#b0e0e6"))
           .LoadingPlaceholder(localPath, FFImageLoading.Work.ImageSource.Filepath)
           .ErrorPlaceholder(localPath, FFImageLoading.Work.ImageSource.Filepath)
           .Into(vh.Image);

    }

the drawable has correct tint
the bitmap is not tinted

do you see any reason?

this worked:

Bitmap bitmap = Bitmap.CreateBitmap(40, 40, Android.Graphics.Bitmap.Config.Argb8888);

        Canvas canvas = new Canvas(bitmap);
        drawable.SetBounds(0, 0, canvas.Width, canvas.Height);
        drawable.Draw(canvas);

Do you have a better solution?

I can add a new BackgroundColorTransformation which could be used in combination with other transformations.

Eg:

<ffimageloading:CachedImage HorizontalOptions="Center" VerticalOptions="Center"
    LoadingPlaceholder="loading.png" ErrorPlaceholder="error.png" DownsampleToViewSize="true"
    Aspect="AspectFit" HeightRequest="400" WidthRequest="400" Source="{Binding ImageUrl}">
    <ffimageloading:CachedImage.Transformations>
        <fftransformations:BackgroundColorTransformation Color="#FFFFFF"/>
        <fftransformations:CircleTransformation/>
    </ffimageloading:CachedImage.Transformations>
</ffimageloading:CachedImage>

What do you think?

And the other enhancement (transformation selector on placeholders / normal images and many other scenarios) is already implemented. Take a look at this: https://github.com/luberda-molinet/FFImageLoading/issues/556

I'll close this one as it's easier to use SVG for such cases (and it's already working).

Was this page helpful?
0 / 5 - 0 ratings