Change iPhone UISlider bar image

48,369

Solution 1

You were right to use -setMinimumTrackImage:forState: and -setMaximumTrackImage:forState: methods. What you missed is that you should provide stretchable UIImage to them, the rest is taken care of automagically:

UIImage *sliderLeftTrackImage = [[UIImage imageNamed: @"SliderMin.png"] stretchableImageWithLeftCapWidth: 9 topCapHeight: 0];
UIImage *sliderRightTrackImage = [[UIImage imageNamed: @"SliderMax.png"] stretchableImageWithLeftCapWidth: 9 topCapHeight: 0];
[mySlider setMinimumTrackImage: sliderLeftTrackImage forState: UIControlStateNormal];
[mySlider setMaximumTrackImage: sliderRightTrackImage forState: UIControlStateNormal];

You can use the same image for both the min and max parts.

Solution 2

The simplest solution would be to render a UIImage behind the control to represent the track. The thumbknob can be changed with:

[mySlider setThumbImage:[UIImage imageNamed:@"thumb_image.png"] forState:UIControlStateNormal];

A side-effect of this is that the track isn't rendered unless you provide your own. This, combined with the UIImage, provide you with a custom UISlider without you having to subclass anything.

Solution 3

enter image description here

Here is a way to add a track image that is not stretched so you can have e.g. a wedge shape in the background just as the OP asked:

Swift 3.0:

let trackImg = image.resizableImage(withCapInsets: .zero, resizingMode: .tile)
slider.setMinimumTrackImage(trackImg, for: .normal)
slider.setMaximumTrackImage(trackImg, for: .normal)

Important: make sure that the width of your slider is exactly the same as the width of the image!

Solution 4

Putting it all together in a modern way

If you define the UISlider in a Storyboard the best place to style the Slider is in the View's subclass. In awakeFromNib you can change the button, left and right track.

This call is deprecated in iOS 5 stretchableImageWithLeftCapWidth:topCapHeight:

- (void)awakeFromNib
{
    [super awakeFromNib];

    UIImage *thumbImage = [UIImage imageNamed:@"slider-button"];
    [self.slider setThumbImage:thumbImage forState:UIControlStateNormal];

    UIImage *sliderLeftTrackImage = [UIImage imageNamed: @"slider-fill"];
    sliderLeftTrackImage = [sliderLeftTrackImage resizableImageWithCapInsets:UIEdgeInsetsZero resizingMode:UIImageResizingModeStretch];
    UIImage *sliderRightTrackImage = [UIImage imageNamed: @"slider-track"];
    sliderRightTrackImage = [sliderRightTrackImage resizableImageWithCapInsets:UIEdgeInsetsZero resizingMode:UIImageResizingModeStretch];
    [self.slider setMinimumTrackImage:sliderLeftTrackImage forState:UIControlStateNormal];
    [self.slider setMaximumTrackImage:sliderRightTrackImage forState:UIControlStateNormal];
}

Solution 5

stretchableImageWithLeftCapWidth: has been deprecated since iOS 5.0. The docs say to use 'capInsets' property instead. Here's an easy way to do that:

Create three images, the min (left) track, the max (right) track, and the thumb. For this example, assume the min and max track images are 34p H x 18p W, something like this: min track and this: enter image description here.

Create the images as usual:

UIImage *thumbImage = [UIImage imageNamed:@"sliderThumb.png"];

UIImage *sliderMinTrackImage = [UIImage imageNamed: @"sliderMin.png"];

UIImage *sliderMaxTrackImage = [UIImage imageNamed: @"sliderMax.png"];

For my 18 point wide image examples, the inner point on the left and the right can be stretched to fit the track, but the ends should have unstretchable cap sizes 17 points wide (hence the capInsets):

sliderMinTrackImage = [sliderMinTrackImage resizableImageWithCapInsets:UIEdgeInsetsMake(0, 17, 0, 0)];

sliderMaxTrackImage = [sliderMaxTrackImage resizableImageWithCapInsets:UIEdgeInsetsMake(0, 0, 0, 17)];

Then set the images on your UISlider as always:

[slider setThumbImage:thumbImage forState:UIControlStateNormal];
[slider setMinimumTrackImage:sliderMinTrackImage forState:UIControlStateNormal];
[slider setMaximumTrackImage:sliderMaxTrackImage forState:UIControlStateNormal];
Share:
48,369
Fogmeister
Author by

Fogmeister

iOS Developer in Leeds.

Updated on February 18, 2020

Comments

  • Fogmeister
    Fogmeister about 4 years

    I'm using a UISlider in my app but I'd like to use a custom "look-and-feel" for it. I have changed the thumb to my own image but is there a way to change the bar also? I have a bar image I would like to use but can't see how to do this.

    I have found how to change the max and min image but not the bar itself.