【Cocococococos 2 d-x 3.x座標系詳細

7282 ワード

//回転: http://cn.cocos2d-x.org/article/index?type=cocos2d-x&url=/doc/cococococococos-docs-master/manaual/frame ebook/native/v 3/coordinate-system/zh.md
Cococos 2 d-x座標系はOpenGL座標系と同じで、デカルト座標系が起源です。
デカルト座標系
デカルト座標系では、右手系原点は左下、xは右下、yは上、zは外側、OpenGL座標系はデカルト右手系と定義されています。
スクリーン座標系とCocos 2 d座標系
標準スクリーン座標系はOpenGLとは異なる座標系を使い、Cococos 2 dはOpenGLと同じ座標系を使います。
iOS、Android、Windows Phoneなどは、アプリケーション開発時に標準画面座標系を使い、原点は画面左上隅、xは右、yは下を向いています。
Cococos 2 d座標系はOpenGL座標系と同じで、原点は画面左下、xは右、yは上向きです。
開発において、私たちはよく二つの比較的抽象的な概念-世界座標系とローカル座標系に言及します。この2つの概念は、Cococos 2 d座標系におけるノードの位置と対応関係をより良く理解するのに役立つ。
世界座標系(World Coordinate)VSローカル座標系(Node Local)
世界座標系は絶対座標系とも言われ、ゲーム開発において確立された概念です。したがって、「世界」はゲームの世界を指す。cococococos 2 dの要素は親子関係の階層構造であり、Nodeのset Position設定要素の位置を通して使用するのは、親ノードのローカル座標系であって、世界座標系ではない。最後にスクリーンを描く時にcocococos 2 dはこれらの元素のローカル座標を世界座標系座標にマッピングします。
ローカル座標系も相対座標系と呼び、ノードに関連する座標系です。各ノードには独立した座標系があり、ノードが方向を移動または変更すると、そのノードに関連する座標系が移動または方向を変更する。
アンカーポイント(Ancher Point)
親ノードにノードを追加する場合は、親ノードの位置を設定する必要があり、基本的にはノードのアンカーポイントを親ノード座標系に設定する位置である。
アンチョーPointの2つのパラメータは0~1の間にあります。これらは画素点ではなく、乗数係数を表しています。(0.5,0.5)アンチョーPointは、ノード長が0.5と幅で0.5に乗るところ、すなわちノードの中心にあることを示す。
Cocos 2 d-xでLayerのAnchor Pointはデフォルト値(0,0)で、他のNodeのデフォルト値は(0.5,0.5)です。以下のコードを例にとって、デフォルトのアンチョーPoint値を使って、赤い層をスクリーンの左下の隅に置いて、緑の層を赤の層に追加します。
auto red = LayerColor::create(Color4B(255, 100, 100, 128), visibleSize.width/2, visibleSize.height/2);
 
auto green = LayerColor::create(Color4B(100, 255, 100, 128), visibleSize.width/4, visibleSize.height/4);
 
red->addChild(green);
 
this->addChild(red, 0);
私達は以下のコードを例にとって、赤い層のAnchor Pointをスクリーンの中央に置いて、緑色層を赤層に追加します。緑層のアンカーポイントは右上の角です。はLayerが特別なので、アンカーポイントをデフォルトで無視します。ignoreAnchorPointForPosition()インターフェースを呼び出してアンカーポイントを変更します。ignoreAnchorPointForPosition()インターフェースの使用説明については、後から詳しく説明します。
auto red = LayerColor::create(Color4B(255, 100, 100, 128), visibleSize.width/2, visibleSize.height/2);
red->ignoreAnchorPointForPosition(false);
red->setAnchorPoint(Point(0.5, 0.5));
red->setPosition(Point(visibleSize.width/2 + origin.x, visibleSize.height/2 + origin.y));
 
auto green = LayerColor::create(Color4B(100, 255, 100, 128), visibleSize.width/4, visibleSize.height/4);
green->ignoreAnchorPointForPosition(false);
green->setAnchorPoint(Point(1, 1));
red->addChild(green);
 
this->addChild(red, 0);
アンカーポイントを無視する(Ignore Ancher Point)
Ignore Anchorr Pointは全部IgnoreAnchore Pointといい、アンカーポイントを一つのところに固定する役割を果たしています。
その値がtrueである場合、画像リソースのAncher Pontは左下の角に固定されます。そうでなければ設定された位置です。
私たちは以下のコードを例にとって、2つの層のグノーレAnchorrPoint ForPositionをtrueに設定し、緑の層を赤の層に追加します。
auto red = LayerColor::create(Color4B(255, 100, 100, 128), visibleSize.width/2, visibleSize.height/2);
red->ignoreAnchorPointForPosition(true);
red->setPosition(Point(visibleSize.width/2 + origin.x, visibleSize.height/2 + origin.y));
 
auto green = LayerColor::create(Color4B(100, 255, 100, 128), visibleSize.width/4, visibleSize.height/4);
green->ignoreAnchorPointForPosition(true);
 
red->addChild(green);
 
this->addChild(red, 0);
VerstexZ,PositionZとzOrder
VersextZはOpenGL座標系のZ値です。
PositionZはCococos 2 d-x座標系のZ値です。
zOrderはCococos 2 d-xローカル座標系におけるZ値である。
実際の開発においてはzOrderだけに注目します。
PositionZはsetPositionZインターフェースで設定できます。
以下はsetPositionZインターフェースの説明である。
Sets the 'z' coordinate in the position. It is the OpenGL Z vertex value.
 PositionZ    opengl z VertexZ。     PositionZ             ,   ,   zOrder       ,PositionZ                  , zOrder        ,               , Node     。        :
auto red = LayerColor::create(Color4B(255, 100, 100, 255), visibleSize.width/2, visibleSize.height/2);
red->ignoreAnchorPointForPosition(false);
red->setPosition(Point(visibleSize.width / 2, visibleSize.height / 2));
 
auto green = LayerColor::create(Color4B(100, 255, 100, 255), visibleSize.width/4, visibleSize.height/4);
green->ignoreAnchorPointForPosition(false);
green->setPosition(Point(visibleSize.width / 2, visibleSize.height / 2 - 100));
red->setPositionZ(1);
green->setPositionZ(0);
this->addChild(red, 0);
this->addChild(green, 1);
greenのzOrderはredのzOderより大きいですが、redのPositionZは大きいので、redはやはりグリーンの上に表示されます。
タッチポイント(タッチポイント)
したがって、タッチイベントの処理には以下の4つの関数を書き換える必要があります。
virtual bool onTouchBegan(Touch *touch, Event * event);
virtual void onTouchEnded(Touch *touch, Event * event);
virtual void onTouchCancelled(Touch *touch, Event * event);
virtual void onTouchMoved(Touch *touch, Event * event);
関数でtouchを取得しました。ゲームロジックを設計する時、Cococos 2 d座標系のタッチポイントの位置を使用する必要があります。touchの座標をOpenGL座標系の点座標に変換する必要があります。
Touch positionはスクリーン座標系の点であり、OpenGL positionはCocococos 2 d-xに使用されるOpenGL座標系の点座標であり、開発においては通常、2つのインターフェースgetLocation()getLocationInView()を用いて対応する座標変換作業を行う。
開発においては、一般的にgetLocation()を用いてタッチポイントのGL座標を取得し、getLocation()内部ではDirector::getInstance()->convertToGL(_point);を呼び出してGL座標に戻すことが実現される。
また、世界座標系と局所座標系の相互変換については、Nodeで以下の4つの一般的な座標変換に関する方法が定義されている。
//                    
Point convertToNodeSpace(const Point& worldPoint) const;
 
//                           
Point convertToWorldSpace(const Point& nodePoint) const;
 
//   Anchor Point                          
Point convertToNodeSpaceAR(const Point& worldPoint) const;
 
//   Anchor Point                   
Point convertToWorldSpaceAR(const Point& nodePoint) const;
この4つの方法の理解と役割を一例で説明する。
auto *sprite1 = Sprite::create("HelloWorld.png");
sprite1->setPosition(ccp(20,40));
sprite1->setAnchorPoint(ccp(0,0));
this->addChild(sprite1);  //            ,   OpenGL   
 
auto *sprite2 = Sprite::create("HelloWorld.png");
sprite2->setPosition(ccp(-5,-20));
sprite2->setAnchorPoint(ccp(1,1));
this->addChild(sprite2); //            ,   OpenGL   
 
//  sprite2        ccp(-5,-20)     sprite1       (  )          
Point point1 = sprite1->convertToNodeSpace(sprite2->getPosition());
 
//  sprite2        ccp(-5,-20)     sprite1                 
Point point2 = sprite1->convertToWorldSpace(sprite2->getPosition());
 
log("position = (%f,%f)",point1.x,point1.y);
log("position = (%f,%f)",point2.x,point2.y);
    :
 
Cocos2d: position = (-25.000000,-60.000000)
Cocos2d: position = (15.000000,20.000000)
内訳:Point point1 = sprite1->convertToNodeSpace(sprite2->getPosition());sprite2に相当するノードが追加されている(実際には追加されていない)sprite1は、このノードのノード座標システムを使用する必要があり、このノードのノード座標システムの原点は(20,40)であり、sprite1の座標は(−5,−20)であり、変換された後、sprite1の座標は、sprite1の座標である。(-25,-60)
内訳:Point point2 = sprite1->convertToWorldSpace(sprite2->getPosition());このときの変換はsprite2の座標をsprite1の世界座標系に変換するものであり、世界座標系は変化がなく、常にOpenGLと同じであるが、sprite2は変換時にsprite1を参照としただけである。