2009-07-11 9 views
21

Je voudrais créer un objet UIImage à partir du contexte graphique actuel. Plus spécifiquement, mon cas d'utilisation est une vue sur laquelle l'utilisateur peut dessiner des lignes. Ils peuvent tirer progressivement. Après avoir terminé, je voudrais créer un UIImage pour représenter leur dessin.Comment créer un UIImage à partir du contexte graphique actuel?

Voici ce que drawRect: me ressemble pour l'instant:

- (void)drawRect:(CGRect)rect 
{ 
CGContextRef c = UIGraphicsGetCurrentContext(); 

CGContextSaveGState(c); 
CGContextSetStrokeColorWithColor(c, [UIColor blackColor].CGColor); 
CGContextSetLineWidth(c,1.5f); 

for(CFIndex i = 0; i < CFArrayGetCount(_pathArray); i++) 
{ 
    CGPathRef path = CFArrayGetValueAtIndex(_pathArray, i); 
    CGContextAddPath(c, path); 
} 

CGContextStrokePath(c); 

CGContextRestoreGState(c); 
} 

... où _pathArray est de type CFArrayRef, et est peuplé chaque fois touchesEnded: est invoquée. Notez également que drawRect: peut être appelé plusieurs fois, au fur et à mesure que l'utilisateur dessine.

Lorsque l'utilisateur a terminé, j'aimerais créer un objet UIImage qui représente le contexte graphique. Des suggestions sur la façon de faire cela?

+0

Les deux réponses ci-dessous fonctionnent. Notez qu'il existe une différence fonctionnelle entre les deux, à savoir que le rendu du calque dans le contexte de l'image rendra également l'arrière-plan du calque; appeler drawRect: ne le fait pas directement (dans mon cas, cela n'a pas d'importance). Je vais avec l'approche CALayer renderInContext en raison des complexités avec l'appel drawRect: directement (Voir http://lists.apple.com/archives/Cocoa-dev/2002/Apr/msg01846.html pour plus de détails). Merci! – figelwump

Répondre

42

Vous devez configurer le contexte graphique d'abord:

UIGraphicsBeginImageContext(myView.bounds.size); 
[myView.layer renderInContext:UIGraphicsGetCurrentContext()]; 
viewImage = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 
7

UIImage * image = UIGraphicsGetImageFromCurrentImageContext();

Si vous devez conserver image, assurez-vous de le conserver!

EDIT: Si vous souhaitez enregistrer la sortie de drawRect dans une image, créez simplement un contexte bitmap en utilisant UIGraphicsBeginImageContext et appelez votre fonction drawRect avec le nouveau contexte lié. C'est plus facile à faire que de sauvegarder le CGContextRef avec lequel vous travaillez dans drawRect - parce que ce contexte n'a peut-être pas d'informations bitmap qui lui sont associées.

UIGraphicsBeginImageContext(view.bounds.size); 
[view drawRect: [myView bounds]]; 
UIImage * image = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 

Vous pouvez également utiliser l'approche mentionnée par Kelvin. Si vous souhaitez créer une image à partir d'une vue plus complexe comme UIWebView, sa méthode est plus rapide. Dessiner la couche de la vue ne nécessite pas d'actualiser la couche, il suffit de déplacer les données d'image d'un tampon à l'autre!

+0

Merci pour la réponse, mais ne semble pas fonctionner. J'ai ajouté la ligne: \t _signatureImage = UIGraphicsGetImageFromCurrentImageContext(); ... où _signatureImage est une propriété conservée. L'objet retourné est nul. Selon les documents, UIGraphicsGetImageFromCurrentImageContext() est destiné à être utilisé uniquement si le contexte actuel est un contexte bitmap. Dans ma mise en œuvre actuelle de drawRect: Je ne crois pas que ce soit le cas. Les docs mentionnent l'utilisation de UIGraphicsBeginImageContext(), mais je ne sais pas comment cela s'applique dans mon cas car drawRect peut être invoqué plusieurs fois. – figelwump

2

Version Swift

func createImage(from view: UIView) -> UIImage { 
     UIGraphicsBeginImageContext(view.bounds.size) 
     view.layer.renderInContext(UIGraphicsGetCurrentContext()!) 
     let viewImage = UIGraphicsGetImageFromCurrentImageContext() 
     UIGraphicsEndImageContext() 

     return viewImage 
    } 
Questions connexes