2012-06-18 13 views
9

Ich habe eine Ansicht mit einem CATiledLayer Hintergrund. Ich möchte die sichtbaren Kacheln aus dieser CATiledLayer-UIView übernehmen und sie einer anderen Ansicht als CALayer-Hintergrund hinzufügen, wodurch das sichtbare Bild in einer anderen UIView, die CATiledLayer nicht verwendet, erneut erstellt wird.CATiledLayer zu CALayer

Der Grund, warum ich dies tun möchte, ist, dass ich diese zweite UIView verwenden werde, um den Effekt der Aktualisierung der CATiledLayer-gestützten UIView zu maskieren - dies erzeugt derzeit ein Flimmern, wenn alle Kacheln neu geladen werden.

Das Problem ist, ich bin mir nicht ganz sicher, wie ich das tun würde. Irgendwelche Ideen?

+1

Sie will also eine bewusst gekachelte Ansicht nehmen und eine normale Ansicht macht die gefliesten zu verbergen ...? Vielleicht eine verrückte Frage, aber warum war es zu Beginn gefliest? –

+0

@PauldeLange - Wenn meine gekachelte Ansicht neu geladen wird, flackert sie, wenn die Kacheln neu gezeichnet werden. Es wird eine UIView unter der gekachelten Ansicht geben, die eine direkte Kopie der darüber liegenden Kacheln sein wird. Wenn die Kacheln neu geladen werden, wird die Ansicht von unten für einen Bruchteil einer Sekunde angezeigt, wenn die Kacheln erneut geladen werden, wodurch der Flickeffekt gestoppt wird. Von dem, was ich sagen kann, ist dies eine ziemlich übliche Praxis für Grafikprogramme - Verwenden eines Grafikpuffers, um die Auswirkungen des Renderns von neuem Inhalt oben zu glätten. –

+0

Wenn Sie die Hintergrundansicht schneller als die Kacheln rendern können, warum haben Sie Kacheln? beeinflussen -> Effekt übrigens. –

Antwort

3

CATiledLayer ist eine Unterklasse von CALayer einen Weg zu asynchron bieten Kacheln des Ebenen Inhalte, potenziell auf mehreren Detailebenen zwischengespeichert.

Sie können die sichtbaren Dinge in der Schicht in eine CGContextRef mit Render:

- (void)renderInContext:(CGContextRef)ctx 

Und dann so Ihre andere Schicht durch Einstellungen seines Beauftragten zu aktualisieren und die Umsetzung der

- (void)drawLayer:(CALayer *)layer inContext:(CGContextRef)context 

ss hier gezeigt http://www.raywenderlich.com/2502/introduction-to-calayers-tutorial

Aber ehrlich gesagt glaube ich nicht, dass dies effizient ist.

+0

Danke für die Antwort. Du sagst es ist nicht effizient. Haben Sie noch andere Ideen, die mir helfen könnten, mein Flimmerproblem zu lösen? –

+0

@Luis 'renderInContext' scheint nicht auf' CATiledLayer' zu funktionieren, wie 'CALayer' das für mich tut. Die Fliesen werden überhaupt nicht gerendert. Irgendwelche Ideen? – Tim

0

Ihr echtes Problem ist hier das Flackern. Ich hatte ein ähnliches Problem auf eine Ansicht mit einem benutzerdefinierten CALayer es sichern, ist dieser Teil der Lösung war: eine benutzerdefinierte Unterklasse Ihrer CALayer Erstellen und implementieren Sie die folgende Methode:

- (void) display { 
    self.contents = nil; 
    [super display]; 
} 

Das eine Reihe von Problemen festgelegt für ich, aber vielleicht nicht für Sie reparieren. Die Alternative für Sie können Transaktionen zu deaktivieren, während Sie aktualisieren: Von CATransaction Class Reference

setDisableActions: Legt fest, ob Aktionen als Folge der Eigenschaftsänderungen ausgelöst innerhalb dieser Transaktion Gruppe gemacht werden unterdrückt.

Also diese verwenden:

[CATransaction begin]; 
[CATransaction setDisableActions:YES]; 
// do updating/flickering stuff 
[self doFlickeringThing]; 
[CATransaction commit];