Skip to content

Commit

Permalink
Fix the rendering issues that were causing #2095. (#2117)
Browse files Browse the repository at this point in the history
* `-[CALayer renderInContext:]` has the ability to render a cached version of itself; it was doing so upside-down because it was using a Cairo implementation detail.
* `-[UIImage drawAtPoint:]` squashed every image it rendered because it switched width & height.

The bug in UIImage dates back to the Cairo implementation as well; the invalid size was passed to a function that ignored it. When our refactor made use of that parameter, things rapidly went south.
We did not catch the second regression because all the images we drew with it were square.

Fixes #2095.
  • Loading branch information
DHowett authored and Raj Seshasankaran committed Mar 1, 2017
1 parent 2eaddf0 commit ff8784c
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 10 deletions.
22 changes: 14 additions & 8 deletions Frameworks/QuartzCore/CALayer.mm
Original file line number Diff line number Diff line change
Expand Up @@ -427,14 +427,20 @@ - (void)renderInContext:(CGContextRef)ctx {
[priv->delegate drawLayer:self inContext:ctx];
}
} else {
CGRect rect;

rect.origin.x = 0;
rect.origin.y = priv->bounds.size.height * priv->contentsScale;
rect.size.width = priv->bounds.size.width * priv->contentsScale;
rect.size.height = -priv->bounds.size.height * priv->contentsScale;

_CGContextDrawImageRect(ctx, priv->contents, rect, destRect);
// If the layer has cached contents, blit them directly.

// Since the layer was rendered in Quartz referential (ULO) AND the current context
// is assumed to be Quartz referential (ULO), BUT the layer's cached contents
// were captured in a CGImage (CGImage referential, LLO), we have to flip
// the context again before we render it.

// |1 0 0| is the transformation matrix for flipping a rect anchored at 0,0 about its Y midpoint.
// |0 -1 0|
// |0 h 1|
CGContextSaveGState(ctx);
CGContextConcatCTM(ctx, CGAffineTransformMake(1, 0, 0, -1, 0, destRect.size.height));
CGContextDrawImage(ctx, destRect, priv->contents);
CGContextRestoreGState(ctx);
}

// Draw sublayers
Expand Down
4 changes: 2 additions & 2 deletions Frameworks/UIKit/UIImage.mm
Original file line number Diff line number Diff line change
Expand Up @@ -491,8 +491,8 @@ - (void)drawAtPoint:(CGPoint)point blendMode:(CGBlendMode)mode alpha:(float)alph

CGRect pos;
pos.origin = point;
pos.size.width = (img_height / _scale);
pos.size.height = (img_width / _scale);
pos.size.height = (img_height / _scale);
pos.size.width = (img_width / _scale);

// |1 0 0| is the transformation matrix for flipping a rect about its Y midpoint m. (m = (y + h/2))
// |0 -1 0|
Expand Down

0 comments on commit ff8784c

Please sign in to comment.