I often use UIimage's resizeableImageWithCapInsets method. However, I would now like to do the reverse i.e. resize the areas covered by the cap and leave the uncapped area unstretched. Is this possible?
Related
So in my scenario, I have a square that is (for understanding's sake) 100x100 and need to display an image that is 300x800 inside of it.
What I want to do is be able to have the image scale just as it would with UIViewContentMode.ScaleAspectFill so that the width scales properly to 100.
However, after that, I would like to then "move" the image up to the top of the image instead of it putting it inside the imageView right in the center, basically what UIViewContentMode.Top does. However that doesn't scale it first.
Is there anyway to do this type of behavior with the built in tools? Anyway to add multiple contentModes?
I already had a helper function that I wrote that scaled an image to a specific size passed in, so I just wrote a function that calculated the scaled image that would fit into the smaller square I had similar to the size AspectFill would do, and then I wrote code that would crop it with the rectangle size I needed at (0,0).
I'm trying to place a background image on a view, using a UIImageView or anything else that will work. I want it to fill the entire view, but maintain the aspect ratio, and allow me to control which side(s) get clipped. I'd like to use Auto Layout if possible (not code).
By setting Auto Layout constraints to keep the UIImageView the full size of the container, and setting Scale Mode to Aspect Fill, I am very close. The only problem is the image is always centered in the view, in that it is cropped on top and bottom in landscape layout and both sides in portrait. I want to be able to control that. I want to be able to "crop just the right side" (keep left edge docked to left of container), or "crop just the top". I have different images and I'll want each one to crop a different way, and possibly I'll allow users to use their own images and select from a few cropping options.
In this image, I currently get the top result, but want the option to get the bottom. The red box shows the visible area in portrait view (roughly):
My question is similar to this one: iOS Aspect Fill Image Resizing with Content Aligned to Left/Top Edge
However, I do not feel it is a duplicate because my needs are different, and I'm also including an image to help explain better. Also, I will not accept an answer of "use different images for portrait vs landscape" because that doesn't really solve the problem. If you understand my question, you would see that you would actually need a different image for every different aspect ratio, pre-cropped in each alignment I want to support. Obviously that's not really a robust solution.
Does anyone know how I could trim a UIImageView of some image with surrounding transparency down to just barely fit the content by cropping off the edges?
You can try using this category:
https://github.com/Clstroud/UIImage-Trim
Here is a usage example from their docs:
UIImage-Trim Category for trimming transparent pixels of an UIImage
object.
How to use
Add the UIImage+Trim files to your project. Include UIImage+Trim.h in
the files where you want to trim your images.
Trimming is pretty straightforward:
[yourImage imageByTrimmingTransparentPixels];
Optionally, you may want to consider any non-opaque pixels as being
transparent (for instance, cropping out a light drop shadow). This can
be achieved by using the alternate method:
[yourImage imageByTrimmingTransparentPixelsRequiringFullOpacity:YES];
Additionally, if you merely desire to know the UIEdgeInsets of the
transparency around the image, you may want to use the following:
[yourImage transparencyInsetsRequiringFullOpacity:YES];
This call works based on the same principles as the "advanced" trim
method, with the boolean dictating whether non-opaque pixels should be
considered transparent.
What is an equal value of
resizableImageWithCapInsets: for stretchableImageWithLeftCapWidth:0 topCapHeight:0?
Also, Is there any simple way to convert the values from stretchableImageWithLeftCapWidth to resizableImageWithCapInsets?
Because the stretchableImageWithLeftCapWidth method was deprecated in iOS 5.
Thanks
I guess your looking for resizableImageWithCapInsets:UIEdgeInsetsZero?
By using:
stretchableImageWithLeftCapWidth:0 topCapHeight:0
You're telling iOS that you want the entire image to be vertically stretchable and you want the entire image to also be horizontally stretchable (itals copied directly from Apple docs). In other words, no part of the image will be preserved unstretched.
In converting your code to use the new method introduced in iOS 5, though, you'll have to keep in mind that the new method works differently than the old one when it determines how to resize the image not contained in the caps (hence the move away from using "stretch" in the method name itself).
While the old method used pure (and not always efficient) scaling of every pixel not contained in the caps as a whole, the new method defaults to the more efficient tiling approach. As a consequence, the results between old and new methods will be very different if the part of the image you're stretching (the part not contained in the caps) measures more than one pixel in the direction(s) being stretched and isn't uniform.
While you have not provided screenshots of the actual image you are working with or the results you're getting, which makes it impossible to tell you exactly why you're not getting the results you want, it does sound like you specifically want your image to be resized with the UIImageResizingModeStretch resizing mode (rather than the default tiling mode). If so, it's likely that you should be using this method instead:
resizableImageWithCapInsets:(UIEdgeInsets)capInsets resizingMode:
The answer to your second question also depends on how you want the stretchable part of your image stretched.
Heuristically:
If your old caps were non-zero and the portion being stretched was either 1x1 pixel or at least uniform in the direction(s) of stretching, you'd probably be able to use UIEdgeInsetsMake(*top*, *left*, *bottom*, *right*) with your LeftCap value as left and right and your TopCap value as top and bottom, given that the old method assumed you wanted to stretch the image symmetrically.
If your old caps were 0 or the portion being stretched was larger than 1x1 pixel in any direction(s) of resized and non-uniform, you could still convert the caps in the same way but you'd want to use the method variant that allows you to control the resizingMode.
Normally I'm using CALayer shadowRadius, but now I also need to use UIImage and apply shaped shadows to it based on the content in the image.
For example when I have a layer with text in it and I set a shadow, it works automatically on the text and not just on the rectangle of the layer.
In Photoshop this is known as "layer style" and it automatically works based on the shape of the image content.
I am afraid that I need to implement some Harvard-Stanford-MIT-NASA kind of hardcore logic to apply a shadow on a "shaped image", i.e. an image of an round icon where the areas around the icon are fully transparent.
I'm able to manipulate images on a per-pixel level as I'm doing this already to draw charts, so if there was an open-sourced implementation of some fantastic algorithms this would be fantastic. And if not: How does this basically work? My guess is I would "just" try to blur a grayscaled version of my image somehow and then overlay it with the non-blurred version.
My guess is I would "just" try to blur a grayscaled version of my image somehow and then overlay it with the non-blurred version.
That's pretty much it, actually. Except instead of blurring a greyscaled version of the image, blur a solid-colored version of the image (i.e. keep the alpha channel, but make all pixels black). Although CALayer's shadowing should do this already for you.
If your images are already composited onto a background (i.e. without real transparency), you have a harder problem as you first need to "remove" the background before you can have the shape of the object in order to generate the shadow.