Hi,
ich arbeite zur Zeit viel mit Apples GameplayKit und sehe da stets in jedem Beispiel und in jedem öffentlichen Code folgende Herangehensweise:
Alles anzeigen
Der Code ist zwar zwecks Veranschaulichung ein wenig reduziert, die wesentlichen Punkte sind aber erhalten geblieben.
Apple selbst und auch alle anderen, öffentlichen Beispiele oder Tutorials gehen so, wie im Snippet oben vor:
1. Initialisieren der Components während Initialisierung der Klasse.
2. Hinzufügen der Components via addComponent.
3. Bei Zugriff auf die Component, diese via Computed Property herausgeben.
Meine Bedenken hierbei sind, dass eine Computed Property eben jedesmal diese "Berechnung" durchführen muss, wenn auf ihr zugegriffen wird. Für mich bedeutet dies aber, dass wohlmöglich die Performance darunter leiden kann. Speziell die Instanz der RPRenderComponent-Klasse, welche einen nicht gerade unerheblichen Teil der Grafik-Darstellung in sich trägt, wird sehr oft Frame-weise aufgerufen.
Diesen "per-Frame"-Code versuche ich aber - Verständnis halber - so gering wie möglich zu halten und arbeite hier lieber mit direkten Referenzen, eben so wie folgt:
Alles anzeigen
Hier sind die Components nun als "Ownership" an die Klasse gebunden, muss dies also auch später berücksichtigen. Für mich aber ist dies rein vom Gefühl her der richtigere Weg, da ich nicht jedesmal und "per-Frame" die Computed Property auflösen muss, was meiner Meinung (oder meinem Empfinden nach) die Performance beeinträchtigen kann.
Jetzt kann es natürlich sein, das Apple selbst in den Beispielen das nur so gemacht hat, da es der Stil desjenigen Entwicklers ist und es alle anderen ebenso nachmachen. Es kann aber auch sein, dass meine Bedenken über Computed Properties eben nicht stimmen. Habt ihr eine Antwort?
ich arbeite zur Zeit viel mit Apples GameplayKit und sehe da stets in jedem Beispiel und in jedem öffentlichen Code folgende Herangehensweise:
Quellcode
- class PlayerEntity: GKEntity {
- // MARK: Components
- /* Für den Zugriff auf Components diese über Computed Properties holen */
- var renderComponent: RPRenderComponent {
- guard let renderComponent = componentForClass(RPRenderComponent.self) else {
- fatalError()
- }
- return renderComponent
- }
- var stateMachineComponent: RPStateMachineComponent {
- guard let stateMachineComponent = componentForClass(RPStateMachineComponent.self) else {
- fatalError()
- }
- return stateMachineComponent
- }
- // MARK: Initialisation
- override init() {
- super.init()
- /* Erstellung der Components während Initialisierung */
- let renderComponent = RPRenderComponent()
- renderComponent.node.entity = self;
- let stateMachineComponent = RPStateMachineComponent(states: [
- RPPlayerStandingState(entity: self),
- RPPlayerFallingState(entity: self),
- RPPlayerBouncingDownState(entity: self),
- RPPlayerBouncingUpState(entity: self),
- RPPlayerJumpingState(entity: self),
- RPPlayerBoostState(entity: self)
- ])
- addComponent(renderComponent)
- addComponent(stateMachineComponent)
- }
- }
Der Code ist zwar zwecks Veranschaulichung ein wenig reduziert, die wesentlichen Punkte sind aber erhalten geblieben.
Apple selbst und auch alle anderen, öffentlichen Beispiele oder Tutorials gehen so, wie im Snippet oben vor:
1. Initialisieren der Components während Initialisierung der Klasse.
2. Hinzufügen der Components via addComponent.
3. Bei Zugriff auf die Component, diese via Computed Property herausgeben.
Meine Bedenken hierbei sind, dass eine Computed Property eben jedesmal diese "Berechnung" durchführen muss, wenn auf ihr zugegriffen wird. Für mich bedeutet dies aber, dass wohlmöglich die Performance darunter leiden kann. Speziell die Instanz der RPRenderComponent-Klasse, welche einen nicht gerade unerheblichen Teil der Grafik-Darstellung in sich trägt, wird sehr oft Frame-weise aufgerufen.
Diesen "per-Frame"-Code versuche ich aber - Verständnis halber - so gering wie möglich zu halten und arbeite hier lieber mit direkten Referenzen, eben so wie folgt:
Quellcode
- class PlayerEntity: GKEntity {
- // MARK: Components
- /* Zugriff auf Components über eigene Variablen */
- let renderComponent: RPRenderComponent
- var stateMachineComponent: RPStateMachineComponent!
- // MARK: Initialisation
- override init() {
- renderComponent = RPRenderComponent()
- super.init()
- renderComponent.node.entity = self
- /* Initialisierung der Statemachine nach super.init() weil Zugriff auf self benötigt wird. */
- stateMachineComponent = RPStateMachineComponent(states: [
- RPPlayerStandingState(entity: self),
- RPPlayerFallingState(entity: self),
- RPPlayerBouncingDownState(entity: self),
- RPPlayerBouncingUpState(entity: self),
- RPPlayerJumpingState(entity: self),
- RPPlayerBoostState(entity: self)
- ])
- addComponent(renderComponent)
- addComponent(stateMachineComponent)
- }
- }
Jetzt kann es natürlich sein, das Apple selbst in den Beispielen das nur so gemacht hat, da es der Stil desjenigen Entwicklers ist und es alle anderen ebenso nachmachen. Es kann aber auch sein, dass meine Bedenken über Computed Properties eben nicht stimmen. Habt ihr eine Antwort?