0

从这里下载了 CCScrollLayer Cocos2D 扩展: https ://github.com/cocos2d/cocos2d-iphone-extensions/tree/master/Extensions/CCScrollLayer

不确定它有多重要,因为我认为这更像是一个 OpenGL 问题,但该层的目的是向 CCLayer 对象添加惯性滚动功能。

我不明白为什么——如果我没有以任何方式修改代码并且很多其他人说它工作正常——我在 Xcode 4.5 中遇到“使用未声明的变量”错误。它抱怨的行在 .m 文件中:

glEnable(GL_POINT_SMOOTH);

GL_POINT_SMOOTH 是无法识别的常量。我不知道我可以用什么作为替代品,也不知道如何为它#define 一个值。任何具有 Cocos2D 或 OpenGL 知识的人都知道我可以做些什么来解决这个问题?这里分别是 .h 和 .m 文件,供任何感兴趣的人使用。我没有在我的项目中包含我正在使用的任何 OpenGL 文件。让我知道你是否需要他们。

。H

/*
 * CCScrollLayer
 *
 * Cocos2D-iPhone-Extensions v0.2.1
 * https://github.com/cocos2d/cocos2d-iphone-extensions
 *
 * 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-2012 Stepan Generalov
 * Copyright 2011 Brian Feller
 *
 * 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.
 *
 */

#import <Foundation/Foundation.h>
#import "cocos2d.h"

@class CCScrollLayer;
@protocol CCScrollLayerDelegate

@optional

/** Called when scroll layer begins scrolling.
 * Usefull to cancel CCTouchDispatcher standardDelegates.
 */
- (void) scrollLayerScrollingStarted:(CCScrollLayer *) sender;

/** Called at the end of moveToPage:
 * Doesn't get called in selectPage:
 */
- (void) scrollLayer: (CCScrollLayer *) sender scrolledToPageNumber: (int) page;

@end

/** Scrolling layer for Menus, like iOS Springboard Screen.
 *
 * 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.
 *
 * @version 0.2.1
 */
@interface CCScrollLayer : CCLayer 
{   
    NSObject <CCScrollLayerDelegate> *delegate_;

    // Holds the current page being displayed.
    int currentScreen_;

    // Number of previous page being displayed.
    int prevScreen_;

    // The x coord of initial point the user starts their swipe.
    CGFloat startSwipe_;

    // For what distance user must slide finger to start scrolling menu.
    CGFloat minimumTouchLengthToSlide_; 

    // For what distance user must slide finger to change the page.
    CGFloat minimumTouchLengthToChangePage_; 

    // Whenever show or not gray/white dots under scrolling content.
    BOOL showPagesIndicator_;
    CGPoint pagesIndicatorPosition_;
    ccColor4B pagesIndicatorSelectedColor_;
    ccColor4B pagesIndicatorNormalColor_;

    // Internal state of scrollLayer (scrolling or idle).
    int state_;

    BOOL stealTouches_;

#ifdef __IPHONE_OS_VERSION_MAX_ALLOWED
    // Holds the touch that started the scroll
    UITouch *scrollTouch_;
#endif

    // Holds pages.
    NSMutableArray *layers_;

    // Holds current pages width offset.
    CGFloat pagesWidthOffset_;

    // Holds current margin offset
    CGFloat marginOffset_;
}

@property (readwrite, assign) NSObject <CCScrollLayerDelegate> *delegate;

#pragma mark Scroll Config Properties

/** Calibration property. Minimum moving touch length that is enough
 * to cancel menu items and start scrolling a layer. 
 */
@property(readwrite, assign) CGFloat minimumTouchLengthToSlide;

/** Calibration property. Minimum moving touch length that is enough to change
 * the page, without snapping back to the previous selected page.
 */
@property(readwrite, assign) CGFloat minimumTouchLengthToChangePage;

/** Offset that can be used to let user see empty space over first or last page. */
@property(readwrite, assign) CGFloat  marginOffset;

/** 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.
 */
@property(readwrite) BOOL stealTouches;

#pragma mark Pages Indicator Properties

/** Whenever show or not white/grey dots under the scroll layer.
 * If yes - dots will be rendered in parents transform (rendered after scroller visit).
 */
@property(readwrite, assign) BOOL showPagesIndicator;

/** Position of dots center in parent coordinates. 
 * (Default value is screenWidth/2, screenHeight/4)
 */
@property(readwrite, assign) CGPoint pagesIndicatorPosition;

/** Color of dot, that represents current selected page(only one dot). */
@property(readwrite, assign) ccColor4B pagesIndicatorSelectedColor;

/** Color of dots, that represents other pages. */
@property(readwrite, assign) ccColor4B pagesIndicatorNormalColor;


#pragma mark Pages Control Properties

/** Total pages available in scrollLayer. */
@property(readonly) int totalScreens;

/** Current page number, that is shown. Belongs to the [0, totalScreen] interval. */
@property(readonly) int currentScreen;

/** Offset, that can be used to let user see next/previous page. */
@property(readwrite) CGFloat pagesWidthOffset;

/** Returns array of pages CCLayer's  */
@property(readonly) NSArray *pages;

#pragma mark Init/Creation

/** Creates new scrollLayer with given pages & width offset.
 * @param layers NSArray of CCLayers, that will be used as pages.
 * @param widthOffset Length in X-coord, that describes length of possible pages
 * intersection. */
+(id) nodeWithLayers:(NSArray *)layers widthOffset: (int) widthOffset; 
/** Inits scrollLayer with given pages & width offset.
 * @param layers NSArray of CCLayers, that will be used as pages.
 * @param widthOffset Length in X-coord, that describes length of possible pages
 * intersection. */
-(id) initWithLayers:(NSArray *)layers widthOffset: (int) widthOffset;

#pragma mark Updates 
/** 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;

#pragma mark Adding/Removing Pages

/** 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 withNumber: (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: (int) page;

#pragma mark Moving/Selecting Pages

/* 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:(int)page;

/* Immedeatly moves scrollLayer to page with given number without running CCMoveTo. 
 * Does nothing if number >= totalScreens or < 0.
 */
-(void) selectPage:(int)page;

@end

和 .m 文件:

/*
 * CCScrollLayer
 *
 * Cocos2D-iPhone-Extensions v0.2.1
 * https://github.com/cocos2d/cocos2d-iphone-extensions
 *
 * 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-2012 Stepan Generalov
 * Copyright 2011 Brian Feller
 *
 * 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.
 *
 */


#import "CCScrollLayer.h"
#import "CCGL.h"

enum 
{
    kCCScrollLayerStateIdle,
    kCCScrollLayerStateSliding,
};

#ifdef __IPHONE_OS_VERSION_MAX_ALLOWED
@interface CCTouchDispatcher (targetedHandlersGetter)

- (id<NSFastEnumeration>) targetedHandlers;

@end

@implementation CCTouchDispatcher (targetedHandlersGetter)

- (id<NSFastEnumeration>) targetedHandlers
{
    return targetedHandlers;
}

@end
#endif

@interface CCScrollLayer ()

- (int) pageNumberForPosition: (CGPoint) position;

@end

@implementation CCScrollLayer

@synthesize delegate = delegate_;
@synthesize minimumTouchLengthToSlide = minimumTouchLengthToSlide_;
@synthesize minimumTouchLengthToChangePage = minimumTouchLengthToChangePage_;
@synthesize marginOffset = marginOffset_;
@synthesize currentScreen = currentScreen_;
@synthesize showPagesIndicator = showPagesIndicator_;
@synthesize pagesIndicatorPosition = pagesIndicatorPosition_;
@synthesize pagesIndicatorNormalColor = pagesIndicatorNormalColor_;
@synthesize pagesIndicatorSelectedColor = pagesIndicatorSelectedColor_;
@synthesize pagesWidthOffset = pagesWidthOffset_;
@synthesize pages = layers_;
@synthesize stealTouches = stealTouches_;

@dynamic totalScreens;
- (int) totalScreens
{
    return [layers_ count];
}

+(id) nodeWithLayers:(NSArray *)layers widthOffset: (int) widthOffset
{
    return [[[self alloc] initWithLayers: layers widthOffset:widthOffset] autorelease];
}

-(id) initWithLayers:(NSArray *)layers widthOffset: (int) widthOffset
{
    if ( (self = [super init]) )
    {
        NSAssert([layers count], @"CCScrollLayer#initWithLayers:widthOffset: you must provide at least one layer!");

        // Enable Touches/Mouse.
#ifdef __IPHONE_OS_VERSION_MAX_ALLOWED
        self.isTouchEnabled = YES;
#elif defined(__MAC_OS_X_VERSION_MAX_ALLOWED)
        self.isMouseEnabled = YES;
#endif

        self.stealTouches = YES;

        // Set default minimum touch length to scroll.
        self.minimumTouchLengthToSlide = 30.0f;
        self.minimumTouchLengthToChangePage = 100.0f;

        self.marginOffset = [[CCDirector sharedDirector] winSize].width;

        // Show indicator by default.
        self.showPagesIndicator = YES;
        self.pagesIndicatorPosition = ccp(0.5f * self.contentSize.width, ceilf ( self.contentSize.height / 8.0f ));
        self.pagesIndicatorNormalColor = ccc4(0x96,0x96,0x96,0xFF);
        self.pagesIndicatorSelectedColor = ccc4(0xFF,0xFF,0xFF,0xFF);

        // Set up the starting variables
        currentScreen_ = 0; 

        // Save offset.
        self.pagesWidthOffset = widthOffset;            

        // Save array of layers.
        layers_ = [[NSMutableArray alloc] initWithArray:layers copyItems:NO];

        [self updatePages];         

    }
    return self;
}

- (void) dealloc
{
    self.delegate = nil;

    [layers_ release];
    layers_ = nil;

    [super dealloc];
}

- (void) updatePages
{
    // Loop through the array and add the screens if needed.
    int i = 0;
    for (CCLayer *l in layers_)
    {
        l.anchorPoint = ccp(0,0);
        l.contentSize = [CCDirector sharedDirector].winSize;
        l.position = ccp(  (i * (self.contentSize.width - self.pagesWidthOffset)), 0  );
        if (!l.parent)
            [self addChild:l];
        i++;
    }
}

#pragma mark CCLayer Methods ReImpl

- (void) visit
{
    [super visit];//< Will draw after glPopScene. 

    if (self.showPagesIndicator)
    {
        int totalScreens = [layers_ count];

        // Prepare Points Array
        CGFloat n = (CGFloat)totalScreens; //< Total points count in CGFloat.
        CGFloat pY = self.pagesIndicatorPosition.y; //< Points y-coord in parent coord sys.
        CGFloat d = 16.0f; //< Distance between points.
        CGPoint points[totalScreens];   
        for (int i=0; i < totalScreens; ++i)
        {
            CGFloat pX = self.pagesIndicatorPosition.x + d * ( (CGFloat)i - 0.5f*(n-1.0f) );
            points[i] = ccp (pX, pY);
        }

        // Set GL Values
#if COCOS2D_VERSION >= 0x00020000
        ccGLEnable(CC_GL_BLEND);
        ccPointSize( 6.0 * CC_CONTENT_SCALE_FACTOR() );
#define DRAW_4B_FUNC ccDrawColor4B

#else
        glEnable(GL_POINT_SMOOTH);
        GLboolean blendWasEnabled = glIsEnabled( GL_BLEND );
        glEnable(GL_BLEND);

        // save the old blending functions
        int blend_src = 0;
        int blend_dst = 0;
        glGetIntegerv( GL_BLEND_SRC, &blend_src );
        glGetIntegerv( GL_BLEND_DST, &blend_dst );
        glPointSize( 6.0 * CC_CONTENT_SCALE_FACTOR() );

#define DRAW_4B_FUNC glColor4ub        

#endif
        glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );

        // Draw Gray Points
        DRAW_4B_FUNC(pagesIndicatorNormalColor_.r,
                     pagesIndicatorNormalColor_.g,
                     pagesIndicatorNormalColor_.b,
                     pagesIndicatorNormalColor_.a);

        ccDrawPoints( points, totalScreens );

        // Draw White Point for Selected Page   
        DRAW_4B_FUNC(pagesIndicatorSelectedColor_.r,
                     pagesIndicatorSelectedColor_.g,
                     pagesIndicatorSelectedColor_.b,
                     pagesIndicatorSelectedColor_.a);
        ccDrawPoint(points[currentScreen_]);

        // Restore GL Values
#if COCOS2D_VERSION >= 0x00020000
        ccPointSize(1.0f);
#else
        glPointSize(1.0f);
        glDisable(GL_POINT_SMOOTH);
        if (! blendWasEnabled)
            glDisable(GL_BLEND);

        // always restore the blending functions too
        glBlendFunc( blend_src, blend_dst );
#endif      
    }
}

#pragma mark Moving To / Selecting Pages

- (void) moveToPageEnded
{
    if (prevScreen_ != currentScreen_)
    {
        if ([self.delegate respondsToSelector:@selector(scrollLayer:scrolledToPageNumber:)])
            [self.delegate scrollLayer: self scrolledToPageNumber: currentScreen_];
    }

    prevScreen_ = currentScreen_ = [self pageNumberForPosition:self.position];
}

- (int) pageNumberForPosition: (CGPoint) position
{
    CGFloat pageFloat = - self.position.x / (self.contentSize.width - self.pagesWidthOffset);
    int pageNumber = ceilf(pageFloat);
    if ( (CGFloat)pageNumber - pageFloat  >= 0.5f)
        pageNumber--;


    pageNumber = MAX(0, pageNumber);
    pageNumber = MIN([layers_ count] - 1, pageNumber);

    return pageNumber;
}


- (CGPoint) positionForPageWithNumber: (int) pageNumber
{
    return ccp( - pageNumber * (self.contentSize.width - self.pagesWidthOffset), 0.0f );
}

-(void) moveToPage:(int)page
{   
    if (page < 0 || page >= [layers_ count]) {
        CCLOGERROR(@"CCScrollLayer#moveToPage: %d - wrong page number, out of bounds. ", page);
        return;
    }

    id changePage = [CCMoveTo actionWithDuration:0.3 position: [self positionForPageWithNumber: page]];
    changePage = [CCSequence actions: changePage,[CCCallFunc actionWithTarget:self selector:@selector(moveToPageEnded)], nil];
    [self runAction:changePage];
    currentScreen_ = page;

}

-(void) selectPage:(int)page
{
    if (page < 0 || page >= [layers_ count]) {
        CCLOGERROR(@"CCScrollLayer#selectPage: %d - wrong page number, out of bounds. ", page);
        return;
    }

    self.position = [self positionForPageWithNumber: page];
    prevScreen_ = currentScreen_;
    currentScreen_ = page;

}

#pragma mark Dynamic Pages Control

- (void) addPage: (CCLayer *) aPage
{
    [self addPage: aPage withNumber: [layers_ count]];
}

- (void) addPage: (CCLayer *) aPage withNumber: (int) pageNumber
{
    pageNumber = MIN(pageNumber, [layers_ count]);
    pageNumber = MAX(pageNumber, 0);

    [layers_ insertObject: aPage atIndex: pageNumber];

    [self updatePages];

    [self moveToPage: currentScreen_];
}

- (void) removePage: (CCLayer *) aPage
{
    [layers_ removeObject: aPage];
    [self removeChild: aPage cleanup: YES];

    [self updatePages];

    prevScreen_ = currentScreen_;
    currentScreen_ = MIN(currentScreen_, [layers_ count] - 1);
    [self moveToPage: currentScreen_];
}

- (void) removePageWithNumber: (int) page
{
    if (page >= 0 && page < [layers_ count])
        [self removePage:[layers_ objectAtIndex: page]];
}

#pragma mark Touches
#ifdef __IPHONE_OS_VERSION_MAX_ALLOWED

/** Register with more priority than CCMenu's but don't swallow touches. */
-(void) registerWithTouchDispatcher
{   
#if COCOS2D_VERSION >= 0x00020000
    CCTouchDispatcher *dispatcher = [[CCDirector sharedDirector] touchDispatcher];
    int priority = kCCMenuHandlerPriority - 1;
#else
    CCTouchDispatcher *dispatcher = [CCTouchDispatcher sharedDispatcher];
    int priority = kCCMenuTouchPriority - 1;
#endif

    [dispatcher addTargetedDelegate:self priority: priority swallowsTouches:NO];    
}

/** Hackish stuff - stole touches from other CCTouchDispatcher targeted delegates. 
 Used to claim touch without receiving ccTouchBegan. */
- (void) claimTouch: (UITouch *) aTouch
{
#if COCOS2D_VERSION >= 0x00020000
    CCTouchDispatcher *dispatcher = [[CCDirector sharedDirector] touchDispatcher];
#else
    CCTouchDispatcher *dispatcher = [CCTouchDispatcher sharedDispatcher];
#endif

    // Enumerate through all targeted handlers.
    for ( CCTargetedTouchHandler *handler in [dispatcher targetedHandlers] )
    {
        // Only our handler should claim the touch.
        if (handler.delegate == self)
        {
            if (![handler.claimedTouches containsObject: aTouch])
            {
                [handler.claimedTouches addObject: aTouch];
            }
        }
        else 
        {
            // Steal touch from other targeted delegates, if they claimed it.
            if ([handler.claimedTouches containsObject: aTouch])
            {
                if ([handler.delegate respondsToSelector:@selector(ccTouchCancelled:withEvent:)])
                {
                    [handler.delegate ccTouchCancelled: aTouch withEvent: nil];
                }
                [handler.claimedTouches removeObject: aTouch];
            }
        }
    }
}

-(void)ccTouchCancelled:(UITouch *)touch withEvent:(UIEvent *)event 
{
    if( scrollTouch_ == touch ) {
        scrollTouch_ = nil;
        [self selectPage: currentScreen_];
    }
}

-(BOOL) ccTouchBegan:(UITouch *)touch withEvent:(UIEvent *)event
{
    if( scrollTouch_ == nil ) {
        scrollTouch_ = touch;
    } else {
        return NO;
    }

    CGPoint touchPoint = [touch locationInView:[touch view]];
    touchPoint = [[CCDirector sharedDirector] convertToGL:touchPoint];

    startSwipe_ = touchPoint.x;
    state_ = kCCScrollLayerStateIdle;
    return YES;
}

- (void)ccTouchMoved:(UITouch *)touch withEvent:(UIEvent *)event
{
    if( scrollTouch_ != touch ) {
        return;
    }

    CGPoint touchPoint = [touch locationInView:[touch view]];
    touchPoint = [[CCDirector sharedDirector] convertToGL:touchPoint];


    // If finger is dragged for more distance then minimum - start sliding and cancel pressed buttons.
    // Of course only if we not already in sliding mode
    if ( (state_ != kCCScrollLayerStateSliding) 
        && (fabsf(touchPoint.x-startSwipe_) >= self.minimumTouchLengthToSlide) )
    {
        state_ = kCCScrollLayerStateSliding;

        // Avoid jerk after state change.
        startSwipe_ = touchPoint.x;

        if (self.stealTouches)
        {
            [self claimTouch: touch];
        }

        if ([self.delegate respondsToSelector:@selector(scrollLayerScrollingStarted:)])
        {
            [self.delegate scrollLayerScrollingStarted: self];
        }
    }

    if (state_ == kCCScrollLayerStateSliding)
    {
        CGFloat desiredX = (- currentScreen_ * (self.contentSize.width - self.pagesWidthOffset)) + touchPoint.x - startSwipe_;
        int page = [self pageNumberForPosition:ccp(desiredX, 0)];
        CGFloat offset = desiredX - [self positionForPageWithNumber:page].x; 
        if ((page == 0 && offset > 0) || (page == [layers_ count] - 1 && offset < 0))
            offset -= marginOffset_ * offset / [[CCDirector sharedDirector] winSize].width;
        else
            offset = 0;
        self.position = ccp(desiredX - offset, 0);
    }
}

- (void)ccTouchEnded:(UITouch *)touch withEvent:(UIEvent *)event
{
    if( scrollTouch_ != touch )
        return;
    scrollTouch_ = nil;

    CGPoint touchPoint = [touch locationInView:[touch view]];
    touchPoint = [[CCDirector sharedDirector] convertToGL:touchPoint];

    int selectedPage = currentScreen_;
    CGFloat delta = touchPoint.x - startSwipe_;
    if (fabsf(delta) >= self.minimumTouchLengthToChangePage)
    {
        selectedPage = [self pageNumberForPosition:self.position];
        if (selectedPage == currentScreen_)
        {
            if (delta < 0.f && selectedPage < [layers_ count] - 1)
                selectedPage++;
            else if (delta > 0.f && selectedPage > 0)
                selectedPage--;
        }
    }
    [self moveToPage:selectedPage]; 
}

#endif

#pragma mark Mouse
#ifdef __MAC_OS_X_VERSION_MAX_ALLOWED

- (NSInteger) mouseDelegatePriority
{
#if COCOS2D_VERSION >= 0x00020000
    return kCCMenuHandlerPriority - 1;
#else
    return kCCMenuMousePriority - 1;
#endif
}

-(BOOL) ccMouseDown:(NSEvent*)event
{
    CGPoint touchPoint = [[CCDirector sharedDirector] convertEventToGL: event];

    startSwipe_ = touchPoint.x;
    state_ = kCCScrollLayerStateIdle;

    return NO;
}

-(BOOL) ccMouseDragged:(NSEvent*)event
{
    CGPoint touchPoint = [[CCDirector sharedDirector] convertEventToGL:event];

    // If mouse is dragged for more distance then minimum - start sliding.
    if ( (state_ != kCCScrollLayerStateSliding) 
        && (fabsf(touchPoint.x-startSwipe_) >= self.minimumTouchLengthToSlide) )
    {
        state_ = kCCScrollLayerStateSliding;

        // Avoid jerk after state change.
        startSwipe_ = touchPoint.x;

        if ([self.delegate respondsToSelector:@selector(scrollLayerScrollingStarted:)])
        {
            [self.delegate scrollLayerScrollingStarted: self];
        }
    }

    if (state_ == kCCScrollLayerStateSliding)
    {
        CGFloat desiredX = (- currentScreen_ * (self.contentSize.width - self.pagesWidthOffset)) + touchPoint.x - startSwipe_;
        int page = [self pageNumberForPosition:ccp(desiredX, 0)];       
        CGFloat offset = desiredX - [self positionForPageWithNumber:page].x;        
        if ((page == 0 && offset > 0) || (page == [layers_ count] - 1 && offset < 0))           
            offset -= marginOffset_ * offset / [[CCDirector sharedDirector] winSize].width;
        else        
            offset = 0;

        self.position = ccp(desiredX - offset, 0);
    }

    return NO;
}

- (BOOL)ccMouseUp:(NSEvent *)event
{
    CGPoint touchPoint = [[CCDirector sharedDirector] convertEventToGL:event];

    int selectedPage = currentScreen_;
    CGFloat delta = touchPoint.x - startSwipe_;
    if (fabsf(delta) >= self.minimumTouchLengthToChangePage)
    {
        selectedPage = [self pageNumberForPosition:self.position];
        if (selectedPage == currentScreen_)
        {
            if (delta < 0.f && selectedPage < [layers_ count] - 1)
                selectedPage++;
            else if (delta > 0.f && selectedPage > 0)
                selectedPage--;
        }
    }
    [self moveToPage:selectedPage];     

    return NO;
}

- (BOOL)ccScrollWheel:(NSEvent *)theEvent
{
    CGFloat deltaX = [theEvent deltaX];

    CGPoint newPos = ccpAdd( self.position, ccp(deltaX, 0.0f) );
    newPos.x = MIN(newPos.x, [self positionForPageWithNumber: 0].x);
    newPos.x = MAX(newPos.x, [self positionForPageWithNumber: [layers_ count] - 1].x);

    self.position = newPos;
    prevScreen_ = currentScreen_;
    currentScreen_ = [self pageNumberForPosition:self.position];

    // Inform delegate about new currentScreen.
    if (prevScreen_ != currentScreen_)
    {
        if ([self.delegate respondsToSelector:@selector(scrollLayer:scrolledToPageNumber:)])
            [self.delegate scrollLayer: self scrolledToPageNumber: currentScreen_];
    }

    prevScreen_ = currentScreen_;

    return NO;

}

#endif

@end
4

1 回答 1

0

Cocos2D 2.0 使用 OpenGLES 2.0。

嘿,请参考我在上一个问题中的回答:Stack_Cocos2D_CCScrollLayer

于 2012-11-03T03:52:26.947 回答