What you're looking for is an SKEffectNode
. It applies a CoreImage filter to itself (and thus all subnodes). Just make it the root view of your scene, give it one of CoreImage's blur filters, and you're set.
For example, I set up an SKScene
with an SKEffectNode
as it's first child node and a property, root
that holds a weak reference to it:
-(void)createLayers{
SKEffectNode *node = [SKEffectNode node];
[node setShouldEnableEffects:NO];
CIFilter *blur = [CIFilter filterWithName:@"CIGaussianBlur" keysAndValues:@"inputRadius", @1.0f, nil];
[node setFilter:blur];
[self setRoot:node];
}
And here's the method I use to (animate!) the blur of my scene:
-(void)blurWithCompletion:(void (^)())handler{
CGFloat duration = 0.5f;
[[self root] setShouldRasterize:YES];
[[self root] setShouldEnableEffects:YES];
[[self root] runAction:[SKAction customActionWithDuration:duration actionBlock:^(SKNode *node, CGFloat elapsedTime){
NSNumber *radius = [NSNumber numberWithFloat:(elapsedTime/duration) * 10.0];
[[(SKEffectNode *)node filter] setValue:radius forKey:@"inputRadius"];
}] completion:handler];
}
Note that, like you, I'm using this as a pause screen, so I rasterize the scene. If you want your scene to animate while blurred, you should probably setShouldResterize:
to NO
.
And if you're not interested in animating the transition to the blur, you could always just set the filter to an initial radius of 10.0f
or so and do a simple setShouldEnableEffects:YES
when you want to switch it on.
See also: SKEffectNode class reference
UPDATE:
See Markus's comment below. He points out that SKScene
is, in fact, a subclass of SKEffectNode
, so you really ought to be able to call all of this on the scene itself rather than arbitrarily inserting an effect node in your node tree.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…