Layer — är en abstraktion av grafiskt innehåll som hanterar den visuella presentationen av gränssnittselement i mobilapplikationer. Till skillnad från UIView bearbetar layer inte tryckhändelser och deltar inte i Auto Layout — dess uppgift är uteslutande rendering, animering och pixelkomposition. Enligt Apple QuartzCore Documentation, 2025 har varje UIView i iOS en associerad CALayer som faktiskt hanterar ritning och animering. Att förstå lagrens struktur gör att utvecklaren kan kontrollera renderingens prestanda på nivån av enskilda pixlar.
Huvudsakligt
Layer — är ett lågnivåobjekt i grafiksystemet som lagrar rasterbilden av en skärmfragment och hanterar dess visuella attribut: position, storlek, rotation, transparens, skugga och färg. I iOS har varje UIView en inbyggd CALayer, tillgänglig via egenskapen layer. Utvecklaren kan arbeta direkt med layer, förbi UIView, för finjustering av renderingen.
Lagerarkitekturen följer mönstret Model-View-Controller, där CALayer fungerar som Model — den lagrar tillståndet för visuella egenskaper. Core Animation är Controller som hanterar animationen av övergångar mellan tillstånd. View (UIView) — ett valfritt omslag som lägger till tryckhantering och deltagande i Auto Layout.
Enligt Apple WWDC 2024 använder den moderna renderingspipelinjen i iOS Metal för lagerkomposition. Varje CALayer ritas i en separat buffer, varefter Core Animation slår samman alla buffertar till den slutgiltiga bilden med hänsyn till transparens och blandningslägen.
I Android är motsvarigheten till lager View och bakgrunds-Drawable, men direkt arbete med grafiska lager är tillgängligt via Canvas och RenderNode i Android 10+. Att förstå begreppet layer är viktigt för att optimera rendering på båda plattformarna.
Huvudskillnaden ligger i ansvarsområdet. View ansvarar för användarinmatning (tryckning, gester), positionering (Auto Layout, frame) och livscykel. Layer ansvarar uteslutande för visuell presentation: rendering av innehåll, animering av egenskaper och komposition med andra lager.
Denna separation gör det möjligt att cachelagra lagrets rasterrepresentation oberoende av View. Om lagret inte ändras använder Core Animation den cachelagrade bildrutan utan att anropa drawRect. För statiska element ger detta en betydande prestandaökning utan kodändringar.
iOS erbjuder en rik klasshierarki som ärver från CALayer. Varje underklass är optimerad för ett specifikt scenario: visning av text, vektorgrafik, gradienter eller 3D-transformationer. Valet av rätt lagertyp påverkar direkt renderingsprestandan.
I Android är konceptet med lager implementerat via RenderNode, ViewLayer och HardwareRenderer. Från och med Android 5.0 (API 21) renderas varje View i sitt eget hårdvaruaccelerationslager, vilket gör det möjligt att utföra animationer utan att anropa onDraw.
Extra flexibilitet i iOS tillhandahålls av CAReplicatorLayer och CAEmitterLayer. Den första används för att skapa repetitiva mönster, den andra — för partikelsystem. Båda arbetar uteslutande på GPU, vilket gör det möjligt att skapa komplexa visuella effekter utan prestandaförlust.
Lagerhierarkin i iOS är uppbyggd enligt trädprincipen: varje CALayer kan innehålla flera underordnade sublayers. Alla transformationer som tillämpas på det överordnade lagret — skalning, rotation, förskjutning — tillämpas automatiskt på underordnade element. Detta säkerställer konsistens i den visuella presentationen under animationer.
Scenkomposition utförs av Core Animation i följande ordning: först renderas bakgrunden, sedan varje underordnat lager i den ordning de läggs till från botten till toppen. För varje lager kontrollerar Core Animation egenskaperna för transparens, masker och blandningslägen, varefter den utför sammanslagning (compositing) till den slutgiltiga bildrutan.
Enligt Apple Documentation utförs kompositionen av ett lager med opaque = true och utan alfakanal utan extra passager — GPU kopierar helt enkelt pixlar över det föregående lagret. Om lagret innehåller transparens utför GPU alfa-blandning, vilket kräver ytterligare beräkningsresurser.
I Android utförs lagerkomposition via SurfaceFlinger — systemtjänsten som tar emot buffertar från varje applikation och slår samman dem med hänsyn till z-ordningen. Varje Window i Android är en separat Surface som kan innehålla flera grafiska lager.
CALayer.mask — egenskapen som gör det möjligt att applicera en mask av godtycklig form på ett lager. Masken kan vara vilken annan CALayer som helst — till exempel CAShapeLayer med en cirkulär bana eller CAGradientLayer för att skapa en mjuk transparensövergång. Användning av masker ökar GPU-belastningen eftersom det kräver en extra renderingspassage för att beräkna alfavärdena för varje pixel.
För enkel beskärning längs rektangulära gränser rekommenderas att använda cornerRadius och masksToBounds. Till skillnad från masker via mask-egenskapen bearbetas cornerRadius hårdvarumässigt i rasteriseringsfasen och kräver ingen extra passage.
shouldRasterize — den viktigaste CALayer-egenskapen för prestandaoptimering. När shouldRasterize är inställd på true renderar Core Animation lagret och alla dess sublayers till en separat rasterbuffer (offscreen buffer). Vid efterföljande bildrutor används den cachelagrade rasterbilden istället för att rendera om.
Cachelagring är effektivt för statiska eller sällan föränderliga lager: skuggor, gradienter, text med rundade hörn. För ofta uppdaterade lager (animation, video, scroll) kan rasterisering dock försämra prestandan eftersom varje bildruta kräver att cachen återskapas.
Enligt forskning från Objc.io minskar korrekt användning av shouldRasterize på iPad Pro renderingstiden för en komplex skärm från 25 ms till 8 ms — mer än tre gånger. Nyckelvillkor: lagret bör inte ändras oftare än en gång var 3-5 bildruta.
Det första exemplet visar konfiguration av grundläggande visuella egenskaper för CALayer i Swift — avrundning av hörn, skugga och kant:
import UIKit
class StyledView: UIView {
override func awakeFromNib() {
super.awakeFromNib()
layer.cornerRadius = 12
layer.masksToBounds = false
layer.shadowColor = UIColor.darkGray.cgColor
layer.shadowOpacity = 0.3
layer.shadowOffset = CGSize(width: 0, height: 4)
layer.shadowRadius = 8
}
}
Det andra exemplet — skapa lageranimation i Swift med CABasicAnimation. Egenskapen position animeras utan UIViews deltagande:
let animation = CABasicAnimation(keyPath: "position")
animation.fromValue = NSValue(cgPoint: CGPoint(x: 0, y: 0))
animation.toValue = NSValue(cgPoint: CGPoint(x: 150, y: 300))
animation.duration = 1.0
animation.timingFunction = CAMediaTimingFunction(name: .easeInEaseOut)
targetLayer.add(animation, forKey: "moveAnimation")
Det tredje exemplet — arbete med RenderNode i Kotlin på Android. RenderNode — den direkta motsvarigheten till CALayer, som möjliggör hantering av grafiska lager på Canvas-nivå:
import android.graphics.renderer.RenderNode
fun createLayer(): RenderNode {
val node = RenderNode("customLayer")
node.setPosition(0, 0, 300, 200)
node.setScaleX(1.5f)
node.setScaleY(1.5f)
val canvas = node.beginRecording()
canvas.drawColor(android.graphics.Color.BLUE)
node.endRecording()
return node
}
Vanliga frågor
UIView — är ett omslag runt CALayer som lägger till tryckhantering och deltagande i Auto Layout. Layer hanterar endast rendering och animering. Direkt arbete med CALayer är möjligt, men för bearbetning av inmatningshändelser krävs UIView.
shouldRasterize aktiverar cachelagring av lagret i en separat offscreen buffer. Använd för statiska eller sällan föränderliga element med skuggor eller komplex komposition. Använd inte för ofta animerade lager — återskapande av cachen blir dyrare än direkt rendering.
Ställ in egenskapen cornerRadius för avrundning av hörn och masksToBounds = true för att beskära innehållet till lagrets gränser. För skugga måste masksToBounds vara false, annars kommer skuggan att beskäras — använd i så fall ett separat lager för skuggan.
Ja, RenderNode i Android 10+ tillhandahåller liknande funktionalitet: hantering av position, skala, rotation och transparens på nivån av grafiskt lager. Canvas och HardwareRenderer säkerställer rendering via GPU. Arkitekturellt sett separerar dock Android inte View och lager lika strikt som iOS.
Skugga i CALayer beräknas via shadowPath eller automatiskt baserat på alfakanalen. Automatisk beräkning kräver genomgång av alla pixlar i lagret, vilket är dyrt. Ange en explicit shadowPath — en rektangel eller UIBezierPath — detta gör det möjligt för GPU att beräkna skuggan utan att inspektera innehållet.
Sammanfattning
Vi utvecklar en mobil applikation nyckelfärdigt
IT Sectr skapar iOS- och Android-applikationer för startups och företag sedan 2017. Vi ger dig råd och föreslår den bästa lösningen.
Läs också