J'ai remarqué que lorsque je place une UIImage
blanche ou noire dans une UISegmentedControl
, la couleur la masque automatiquement pour qu'elle corresponde à la teinte du contrôle segmenté. Je pensais que c'était vraiment cool et je me demandais si je pouvais le faire ailleurs. Par exemple, j'ai un tas de boutons qui ont une forme uniforme mais des couleurs variées. Au lieu de créer un fichier PNG pour chaque bouton, puis-je utiliser ce masquage de couleur pour utiliser la même image pour tous, mais définir ensuite une couleur ou une couleur pour modifier leur couleur réelle?
Depuis iOS 7, il existe une nouvelle méthode sur UIImage
pour spécifier le mode de rendu. L'utilisation du mode de rendu UIImageRenderingModeAlwaysTemplate
permettra à la couleur de l'image d'être contrôlée par la couleur de teinte du bouton.
Objectif c
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
UIImage *image = [[UIImage imageNamed:@"image_name"] imageWithRenderingMode:UIImageRenderingModeAlwaysTemplate];
[button setImage:image forState:UIControlStateNormal];
button.tintColor = [UIColor redColor];
Rapide
let button = UIButton(type: .custom)
let image = UIImage(named: "image_name")?.withRenderingMode(.alwaysTemplate)
button.setImage(image, for: .normal)
button.tintColor = UIColor.red
Comme Ric l'a déjà mentionné dans son post , vous pouvez définir le mode de rendu en code, vous pouvez également le faire directement dans le catalogue d'images, voir l'image ci-jointe ci-dessous. Il suffit de définir le Render As
à Template Image
Avertissement J'ai eu des problèmes avec iOS 7 et cette approche. Donc, si vous utilisez également iOS 7, vous pouvez également le faire en code pour en être sûr, comme décrit ici .
Vous devez définir le mode de rendu de l'image sur UIImageRenderingModeAlwaysTemplate
pour que tintColor
affecte le paramètre UIImage. Voici la solution dans Swift:
let image = UIImage(named: "image-name")
let button = UIButton()
button.setImage(image?.imageWithRenderingMode(UIImageRenderingMode.AlwaysTemplate), forState: .Normal)
button.tintColor = UIColor.whiteColor()
Si vous avez un bouton personnalisé avec une image d’arrière-plan. Vous pouvez définir la couleur de teinte de votre bouton et remplacer l’image par ce qui suit.
Dans les ressources, sélectionnez l’arrière-plan du bouton pour lequel vous souhaitez définir la couleur de teinte.
Dans l'inspecteur d'attributs de l'image, définissez la valeur du rendu sous "Modèle".
Maintenant, chaque fois que vous définissezbutton.tintColor = UIColor.red
, votre bouton apparaît en rouge.
Dans Swift, vous pouvez le faire comme suit:
var exampleImage = UIImage(named: "ExampleImage.png")?.imageWithRenderingMode(.AlwaysTemplate)
Puis dans votre viewDidLoad
exampleButtonOutlet.setImage(exampleImage, forState: UIControlState.Normal)
Et pour modifier la couleur
exampleButtonOutlet.tintColor = UIColor(red: 1, green: 0, blue: 0, alpha: 1) //your color
EDIT Xcode 8 Maintenant, vous pouvez aussi choisir le mode de rendu de l’image dans votre .xcassets vers un modèle d’image sans avoir à le déclarer spécifiquement dans le var exampleImage
Vous ne savez pas exactement ce que vous voulez, mais cette méthode de catégorie masquera une UIImage avec une couleur spécifiée afin que vous puissiez avoir une seule image et changer sa couleur comme vous voulez.
ImageUtils.h
- (UIImage *) maskWithColor:(UIColor *)color;
ImageUtils.m
-(UIImage *) maskWithColor:(UIColor *)color
{
CGImageRef maskImage = self.CGImage;
CGFloat width = self.size.width;
CGFloat height = self.size.height;
CGRect bounds = CGRectMake(0,0,width,height);
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef bitmapContext = CGBitmapContextCreate(NULL, width, height, 8, 0, colorSpace, kCGImageAlphaPremultipliedLast);
CGContextClipToMask(bitmapContext, bounds, maskImage);
CGContextSetFillColorWithColor(bitmapContext, color.CGColor);
CGContextFillRect(bitmapContext, bounds);
CGImageRef cImage = CGBitmapContextCreateImage(bitmapContext);
UIImage *coloredImage = [UIImage imageWithCGImage:cImage];
CGContextRelease(bitmapContext);
CGColorSpaceRelease(colorSpace);
CGImageRelease(cImage);
return coloredImage;
}
Importez la catégorie ImageUtils et faites quelque chose comme ça ...
#import "ImageUtils.h"
...
UIImage *icon = [UIImage imageNamed:ICON_IMAGE];
UIImage *redIcon = [icon maskWithColor:UIColor.redColor];
UIImage *blueIcon = [icon maskWithColor:UIColor.blueColor];
Swift 4 avec customType:
let button = UIButton(frame: aRectHere)
let buttonImage = UIImage(named: "imageName")
button.setImage(buttonImage?.withRenderingMode(.alwaysTemplate), for: .normal)
button.tintColor = .white
Swift 3:
Cette solution pourrait être confortable si vous avez déjà défini votre image via le constructeur d'interface xCode. En gros, vous avez une extension pour coloriser une image:
extension UIImage {
public func image(withTintColor color: UIColor) -> UIImage{
UIGraphicsBeginImageContextWithOptions(self.size, false, self.scale)
let context: CGContext = UIGraphicsGetCurrentContext()!
context.translateBy(x: 0, y: self.size.height)
context.scaleBy(x: 1.0, y: -1.0)
context.setBlendMode(CGBlendMode.normal)
let rect: CGRect = CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height)
context.clip(to: rect, mask: self.cgImage!)
color.setFill()
context.fill(rect)
let newImage: UIImage = UIGraphicsGetImageFromCurrentImageContext()!
UIGraphicsEndImageContext()
return newImage
}
}
Ensuite, vous pouvez préparer cette extension UIButton pour coloriser l’image dans un état particulier:
extension UIButton {
func imageWith(color:UIColor, for: UIControlState) {
if let imageForState = self.image(for: state) {
self.image(for: .normal)?.withRenderingMode(.alwaysTemplate)
let colorizedImage = imageForState.image(withTintColor: color)
self.setImage(colorizedImage, for: state)
}
}
}
Utilisation:
myButton.imageWith(.red, for: .normal)
P.S. (fonctionne bien aussi dans les cellules de tableau, vous n'avez pas besoin d'appeler la méthode setNeedDisplay()
, le changement de couleur est immédiat en raison de l'extension UIImage ..
Pour Xamarin.iOS (C #):
UIButton messagesButton = new UIButton(UIButtonType.Custom);
UIImage icon = UIImage.FromBundle("Images/icon.png");
messagesButton.SetImage(icon.ImageWithRenderingMode(UIImageRenderingMode.AlwaysTemplate), UIControlState.Normal);
messagesButton.TintColor = UIColor.White;
messagesButton.Frame = new RectangleF(0, 0, 25, 25);
Si vous souhaitez masquer manuellement votre image, voici le code mis à jour qui fonctionne avec les écrans de rétine
- (UIImage *)maskWithColor:(UIColor *)color
{
CGImageRef maskImage = self.CGImage;
CGFloat width = self.size.width * self.scale;
CGFloat height = self.size.height * self.scale;
CGRect bounds = CGRectMake(0,0,width,height);
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef bitmapContext = CGBitmapContextCreate(NULL, width, height, 8, 0, colorSpace, kCGBitmapAlphaInfoMask & kCGImageAlphaPremultipliedLast);
CGContextClipToMask(bitmapContext, bounds, maskImage);
CGContextSetFillColorWithColor(bitmapContext, color.CGColor);
CGContextFillRect(bitmapContext, bounds);
CGImageRef cImage = CGBitmapContextCreateImage(bitmapContext);
UIImage *coloredImage = [UIImage imageWithCGImage:cImage scale:self.scale orientation:self.imageOrientation];
CGContextRelease(bitmapContext);
CGColorSpaceRelease(colorSpace);
CGImageRelease(cImage);
return coloredImage;
}
Tu devrais essayer
Après avoir défini le cadre
NSArray *arr10 =[NSArray arrayWithObjects:btn1,btn2,nil];
for(UIButton *btn10 in arr10)
{
CAGradientLayer *btnGradient2 = [CAGradientLayer layer];
btnGradient2.frame = btn10.bounds;
btnGradient2.colors = [NSArray arrayWithObjects:
(id)[[UIColor colorWithRed:151.0/255.0f green:206.0/255.5 blue:99.0/255.0 alpha:1] CGColor],
(id)[[UIColor colorWithRed:126.0/255.0f green:192.0/255.5 blue:65.0/255.0 alpha:1]CGColor],
nil];
[btn10.layer insertSublayer:btnGradient2 atIndex:0];
}
Swift 3.0
let image = UIImage(named:"NoConnection")!
warningButton = UIButton(type: .system)
warningButton.setImage(image, for: .normal)
warningButton.tintColor = UIColor.lightText
warningButton.frame = CGRect(Origin: CGPoint(x:-100,y:0), size: CGSize(width: 59, height: 56))
self.addSubview(warningButton)
Changer l'image du bouton ou la couleur de la teinte de l'image, Swift:
btn.imageView?.image = btn.imageView?.image?.withRenderingMode(.alwaysTemplate)
btn.imageView?.tintColor = #colorLiteral(red: 0, green: 0, blue: 0, alpha: 1)
Aucune de ces solutions ne fonctionnait pour moi, car la teinte était effacée après un clic. Je devais utiliser
button.setImageTintColor(Palette.darkGray(), for: UIControlState())