编辑:有足够的重写和评论,我已经运行,将在下面发布最终其他人. 编辑2:我一直在更新我自己的版本,而且我已经了解到原来的编码器对C不是很好,你可能想在使用它之前查看其中的所
编辑2:我一直在更新我自己的版本,而且我已经了解到原来的编码器对C不是很好,你可能想在使用它之前查看其中的所有内容,请查看下面的评论
目前可用的CCScrollView for cocos2d-x存在一个主要缺陷:它搞砸了.
具体来说,cpp函数头与.h文件不匹配.
cpp文件引用UIEvent和NSMutableArray,而不是X-Platform.
滚动视图本身必须添加一个数组,这限制了您使用for循环创建菜单项(如果创建菜单项)的能力,因为您不能使用可变的,并且它们不会像iOS所以你不能只使用一个mutable然后说CCArray * array = mutable-> getMutableArray()或类似的.
此外,定义已过时(虽然通过cocos2d-x网站上的转换规则添加CCX_SAFE_DELETE可以修复),以及各种随机模板试图创建甚至不在项目中的NS和UI对象我也没有线索为什么.
基本的想法是,除了使用可变数组之外,这个类太乱了,无法转换为C语言.我不相信作者编译了他的版本,因为标题不匹配.我以为我下载了两个(每个都有2个)cpp和.h文件,并且都有UIEvent而不是CC以及其他问题.
注意:我已经修复了上面的各种内容,并在各个地方将SelectorProtocol更改为CCObject,但它只是变得势不可挡.
也许我应该使用Parallax节点?
这太荒谬了,也许它对Cocos2d来说很棒,但它不适用于c2d-X.无论如何,我会记录和搜索,感谢任何建议!
编辑:这是我现在正在使用的课程.没有完成编辑,但这些将让任何人开始,并编译不仅仅是iPhone
标题:
#ifndef __CCSCROLLLAYER__ #define __CCSCROLLLAYER__ // CCScrollLayer.h // // Copyright 2010 DK101 // http://dk101.net/2010/11/30/implementing-page-scrolling-in-cocos2d/ // // Copyright 2010 Giv Parvaneh. // http://www.givp.org/blog/2010/12/30/scrolling-menus-in-cocos2d/ // // Copyright 2011 Stepan Generalov // // Copyright 2011 Eli Yukelzon // // Permission is hereby granted, free of charge, to any person obtaining a copy // of this software and associated documentation files (the "Software"), to deal // in the Software without restriction, including without limitation the rights // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell // copies of the Software, and to permit persons to whom the Software is // furnished to do so, subject to the following conditions: // // The above copyright notice and this permission notice shall be included in // all copies or substantial portions of the Software. // // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN // THE SOFTWARE. // Original source: https://github.com/cocos2d/cocos2d-iphone-extensions/tree/master/Extensions/CCScrollLayer // Last updated: October 1, 2011 #include "cocos2d.h" namespace cocos2d { class CCScrollLayer; class CCScrollLayerDelegate { public: /** Called when scroll layer begins scrolling. * Usefull to cancel CCTouchDispatcher standardDelegates. */ virtual void scrollLayerScrollingStarted(CCScrollLayer* sender) {} /** Called at the end of moveToPage: * Doesn't get called in selectPage: */ virtual void scrollLayerScrolledToPageNumber(CCScrollLayer* sender, unsigned int page) {} }; /* It is a very clean and elegant subclass of CCLayer that lets you pass-in an array of layers and it will then create a smooth scroller. Complete with the "snapping" effect. You can create screens with anything that can be added to a CCLayer. */ class CCScrollLayer : public CCLayer { int currentScreen; //added int totalScreens; float scrollWidth; float scrollHeight; float startWidth; float startHeight; int startSwipe; public: //CCScrollLayer(); ~CCScrollLayer(); static CCScrollLayer* nodeWithLayers(CCArray* layers, int widthOffset); bool initWithLayers(CCArray* layers, int widthOffset); /** Updates all pages positions & adds them as children if needed. * Can be used to update position of pages after screen reshape, or * for update after dynamic page add/remove. */ void updatePages(); /** Adds new page and reorders pages trying to set given number for newly added page. * If number > pages count - adds new page to the right end of the scroll layer. * If number <= 0 - adds new page to the left end of the scroll layer. * @attention Designated addPage method. */ void addPage(CCLayer* aPage, unsigned int pageNumber); /** Adds new page to the right end of the scroll layer. */ void addPage(CCLayer* aPage); /** Removes page if it's one of scroll layers pages (not children) * Does nothing if page not found. */ void removePage(CCLayer* aPage); /** Removes page with given number. Doesn nothing if there's no page for such number. */ void removePageWithNumber(unsigned int pageNumber); /* Moves scrollLayer to page with given number & invokes delegate * method scrollLayer:scrolledToPageNumber: at the end of CCMoveTo action. * Does nothing if number >= totalScreens or < 0. */ void moveToPage(unsigned int pageNumber); /* Immedeatly moves scrollLayer to page with given number without running CCMoveTo. * Does nothing if number >= totalScreens or < 0. */ void selectPage(unsigned int pageNumber); CC_SYNTHESIZE(CCScrollLayerDelegate*, m_pDelegate, Delegate); /** Calibration property. Minimum moving touch length that is enough * to cancel menu items and start scrolling a layer. */ CC_SYNTHESIZE(CGFloat, m_fMinimumTouchLengthToSlide, MinimumTouchLengthToSlide); /** Calibration property. Minimum moving touch length that is enough to change * the page, without snapping back to the previous selected page. */ CC_SYNTHESIZE(CGFloat, m_fMinimumTouchLengthToChangePage, MinimumTouchLengthToChangePage); /** If YES - when starting scrolling CCScrollLayer will claim touches, that are * already claimed by others targetedTouchDelegates by calling CCTouchDispatcher#touchesCancelled * Usefull to have ability to scroll with touch above menus in pages. * If NO - scrolling will start, but no touches will be cancelled. * Default is YES. */ CC_SYNTHESIZE(bool, m_bStealTouches, StealTouches); /** Whenever show or not white/grey dots under the scroll layer. * If yes - dots will be rendered in parents transform (rendered after scroller visit). */ CC_SYNTHESIZE(bool, m_bShowPagesIndicator, ShowPagesIndicator); /** Position of dots center in parent coordinates. * (Default value is screenWidth/2, screenHeight/4) */ CC_SYNTHESIZE_PASS_BY_REF(CCPoint, m_tPagesIndicatorPosition, PagesIndicatorPosition); /** Total pages available in scrollLayer. */ unsigned int getTotalScreens() const; /** Current page number, that is shown. Belongs to the [0, totalScreen] interval. */ CC_SYNTHESIZE_READONLY(unsigned int, m_uCurrentScreen, CurrentScreen); /** Offset, that can be used to let user see next/previous page. */ CC_SYNTHESIZE(CGFloat, m_fPagesWidthOffset, PagesWidthOffset); /** Offset that can be used to let user see empty space over first or last page. */ CC_SYNTHESIZE(CGFloat, m_fMarginOffset, MarginOffset); /** Array of pages CCLayer's */ CC_SYNTHESIZE_READONLY(CCArray*, m_pLayers, Pages); protected: // The x coord of initial point the user starts their swipe. CGFloat m_fStartSwipe; // Internal state of scrollLayer (scrolling or idle). int m_iState; bool m_bStealingTouchInProgress; // Holds the touch that started the scroll CCTouch* m_pScrollTouch; //void visit(); //void moveToPageEnded(); unsigned int pageNumberForPosition(const CCPoint& position); CCPoint positionForPageWithNumber(unsigned int pageNumber); void claimTouch(CCTouch* pTouch); void cancelAndStoleTouch(CCTouch* pTouch, CCEvent* pEvent); //void registerWithTouchDispatcher(); bool ccTouchBegan(CCTouch* pTouch, CCEvent* pEvent); void ccTouchMoved(CCTouch* pTouch, CCEvent* pEvent); void ccTouchEnded(CCTouch* pTouch, CCEvent* pEvent); //void ccTouchCancelled(CCTouch* pTouch, CCEvent* pEvent); }; } //end namespace #endif
CPP
// CCScrollLayer.cpp // Museum // // Created by GParvaneh on 29/12/2010. // Copyright 2010. All rights reserved. // Ported to C++ by Lior Tamam on 03/04/2011 #include "CCScrollLayer.h" using namespace cocos2d; CCScrollLayer* CCScrollLayer::nodeWithLayers(CCArray* layers, int widthOffset) { CCScrollLayer *pRet = new CCScrollLayer(); if (pRet && pRet->initWithLayers(layers, widthOffset)) { pRet->autorelease(); return pRet; } CCX_SAFE_DELETE(pRet); return NULL; } bool CCScrollLayer::initWithLayers(CCArray* layers, int widthOffset) { if (CCLayer::init()) { // Make sure the layer accepts touches CCTouchDispatcher::sharedDispatcher()->addTargetedDelegate(this,0,true); // Set up the starting variables //if(!widthOffset) { // widthOffset = 0; } currentScreen = 1; // offset added to show preview of next/previous screens scrollWidth = (int)CCDirector::sharedDirector()->getWinSize().width - widthOffset; scrollHeight = (int)CCDirector::sharedDirector()->getWinSize().height; startWidth = scrollWidth; startHeight = scrollHeight; // Loop through the array and add the screens unsigned int i; for (i=0; i<layers->count(); i++) { CCLayer* l = (CCLayer*)layers->objectAtIndex(i); //l->setAnchorPoint(ccp(0,0)); //l->setPosition(ccp((i*scrollWidth),0)); addChild(l); } // Setup a count of the available screens totalScreens = layers->count(); return true; } else { return false; } } void CCScrollLayer::setMaximumScrollHeight(float maxHeight) { //Make the offset match expected pixels (include the current screen if at ccp(0,0) maxHeight -= CCDirector::sharedDirector()->getWinSize().height; maximumScrollHeight = maxHeight; } CCScrollLayer::~CCScrollLayer() { CCTouchDispatcher::sharedDispatcher()->removeDelegate(this); CCLayer::onExit(); } bool CCScrollLayer::ccTouchBegan(CCTouch *touch, CCEvent *withEvent) { // // CCPoint touchPoint = touch->locationInView(); // touchPoint = CCDirector::sharedDirector()->convertToGL(touchPoint); // // startSwipe = (int)touchPoint.y; return true; } void CCScrollLayer::ccTouchMoved(CCTouch *touch, CCEvent *withEvent) { CCPoint touchPoint = touch->locationInView(); CCPoint prevPoint = touch->previousLocationInView(); touchPoint = CCDirector::sharedDirector()->convertToGL(touchPoint); prevPoint = CCDirector::sharedDirector()->convertToGL(prevPoint); CCPoint difference = ccp( touchPoint.x - prevPoint.x , touchPoint.y - prevPoint.y); CCPoint currentPos = this->getPosition(); currentPos = ccp( currentPos.x, currentPos.y+difference.y); if (currentPos.y > maximumScrollHeight) { currentPos.y = maximumScrollHeight; //this->setPositionY(maximumScrollHeight); } else if (currentPos.y < 0) { currentPos.y = 0; // this->setPositionY(0); } this->setPosition(currentPos); } /* void CCScrollLayer::ccTouchEnded(CCTouch *touch, CCEvent *withEvent) { //CCPoint touchPoint = touch->locationInView(); //touchPoint = CCDirector::sharedDirector()->convertToGL(touchPoint); int newX = (int)touchPoint.x; if ( (newX - startSwipe) < -scrollWidth / 3 && (currentScreen+1) <= totalScreens ) { // this->moveToNextPage(); } else if ( (newX - startSwipe) > scrollWidth / 3 && (currentScreen-1) > 0 ) { // this->moveToPreviousPage(); } else { // this->moveToPage(currentScreen); } } */对于通过搜索引擎找到此内容的任何人来说,恢复旧线程以添加新信息:
CCScrollView
现在是GUI扩展的一部分,并且似乎运行得相当好.不再需要上面提到的实现.