1

私のプロジェクト(ゲーム)には、タッチで操作される複数のオブジェクトがあるので、すべてのタッチ可能なオブジェクトを「タッチ可能な」抽象クラスのサブクラスとして持つことは、次のような良い考えだと思いました。

TouchableはCCSpriteのサブクラスです

BoxはTouchableのサブクラスです

モーターはTouchableのサブクラスです

したがって、BoxとMotorはCCSpriteであり、Touchableの一般的なメソッドを継承し、それらをオーバーライドできます。

これはこれを回避する正しい方法ですか、それともこの階層に取り組む他の方法がありますか?

4

2 に答える 2

3

CCSpriteのサブクラス化がほとんどの場合悪い考えである理由を以前に説明しました。

名前が示すように「タッチ可能」はオブジェクトの能力です。ノードに触れることも、触れないこともできます。さらに、これはスプライトに限定されてはなりません。後でタッチ可能なラベル、タッチ可能なパーティクルエフェクト、またはその他のタッチ可能なノードクラスが必要になった場合はどうなりますか?

明らかに、CCNodeをサブクラス化してタッチ可能にし、そのタッチ可能ノードクラスのサブクラスをスプライトやラベルなどに戻すことはできません。これは、cocos2dがすでにクラス階層を確立しているためです。これは、このような階層システムの柔軟性の欠如が表面化し、開始する場所です。本当の痛みになります。

このようなタッチ可能な(またはキル可能、フライング、ジャンプ、ドライブ可能、スワイプ可能など)機能をいつでも任意のオブジェクトに追加でき、いつでもそれを取り除くことができます。これにより、プラグインクラス(コンポーネント)の候補になります。すべての能力、特に一時的な能力は、スーパークラスの一部ではなく、既存のオブジェクトに追加できる追加のオブジェクトであり、必要に応じて有効/無効にする必要があります。

これを実行する1つの方法は、ノードのuserObjectプロパティを使用することです。Abilitiesコンテナクラスを記述し、それをノードのuserObjectに割り当てます。次に、必要な能力クラスをノードのコンテナに追加します。次に、ノードはupdateメソッドを転送することにより、userObjectコンテナクラスを更新します。このメソッドは、更新をすべての機能に転送します。または、Abilityコンテナー自体がCCSchedulerに登録して、更新を受信します。コンテナクラスと能力クラスに必要なのは、所有ノードへの(弱い)参照だけです。

于 2012-10-11T08:05:20.530 に答える
2

「Touchable」が、サポートするために各クラスが明示的に実装する必要のある動作のランダムなセットを表すかどうか、または継承で「正しく機能する」単一の実装が存在する可能性があるかどうかによって異なります(おそらく少しカスタマイズして)。

前者の場合、あなたの考えはほとんど正しいです。後者の場合、@protocol(Javaのインターフェイスによく似た)を使用するというJackの提案は理にかなっています。

個人的には、とてもシンプルにしています。SPAbstractSpriteのサブクラスであるクラスから始めCCSpriteます。次に、それをとにサブクラス化SPBoxSPMotorます。

SPBoxおよび/またはで実装を開始しSPMotor、一般的なことが起こったら、それらをにリファクタリングしますSPAbstractSprite

「タッチ可能」の概念については、今のところ、それを名前付きのものにしようとすることを心配する必要はありません。上記と同じ方法でアプローチします。モーターまたはボックスにタッチ可能なサポートを実装し、後で抽象親クラスまでリファクタリングします。

しかし、私は非常に確かに、非常にデザインとコードがインターリーブされた人物であり、コードの行を書く前に、座ってボックス/行/階層の素晴らしいセットを引き出すのが本当に好きな人がいることを完全に認めています。

いずれにせよ、Appleが提供するクラスと例全体のクラス階層は非常に浅い傾向があり、抽象化は依然として頻繁に使用されますが、この抽象化を大量に行う傾向はないことに注意してください(UIViewすべての抽象コンテナです)たとえば、これらすべてのサブクラスに必要なグープのようなビュー)。

于 2012-10-10T23:56:12.417 に答える