拼字拖动技术

时间:2012-11-19 03:58:41

标签: objective-c ios touch puzzle

我创造了一个类似拼字游戏的益智游戏。

这是布局:

1 2 3 4

5 6 7 8

9 10 11 12

13 14 15 16

我的问题是什么?

我的问题是当我从1开始触摸并向12方向触摸时,如果触摸和拖动速度慢,那么没有问题但是当快速拖动时,我只能设置为1,6,12或1,7,12。缺少一个数字。

如何确保选择路径编号?

我正在使用touch begantouch movedtouch ended并使用坐标来确定要触摸的号码。

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
[super touchesBegan:touches withEvent:event];

UITouch *touch = [touches anyObject];
CGPoint currentTouchLocation = [touch locationInView:self.numberview];
if(!ispause && [time.text intValue] > 0){
    if(!isbegan && !isended){
        for(int i = 1; i <= 16; i++)
        {
            UIView *imageview = [self.numberview viewWithTag:i];
            if (CGRectContainsPoint(imageview.frame, currentTouchLocation))
            {
                isbegan = YES;
                isreverse = NO;
                if([[ischose objectAtIndex:i-1] boolValue] == 0)
                {
                    currentposition = imageview.tag;
                    positionvalue += pow(i, 3);
                    currentanswer += [self converter:[NSString stringWithFormat:@"%@", [allimagenumbers substringWithRange:NSMakeRange(i-1, 1)]]];
                    [ischose replaceObjectAtIndex:i-1 withObject:[NSNumber numberWithBool:YES]];
                    [self changeimage:@"selected"];
                }
                break;
            }
        }
    }
}
}

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{
[super touchesMoved:touches withEvent:event];

UITouch *touch = [touches anyObject];
CGPoint currentTouchLocation = [touch locationInView:self.numberview];

float gapX = image1.frame.size.width / 8;
float gapY = image1.frame.size.height / 8;

if(isbegan && !isended)
{
    if(currentTouchLocation.x >= 0 && currentTouchLocation.x <= self.numberview.frame.size.width && currentTouchLocation.y >= 0 && currentTouchLocation.y <= self.numberview.frame.size.height)
    {
        for(int i = 1; i <= 16; i++)
        {
            UIView *imageview = [self.numberview viewWithTag:i];
            if (CGRectContainsPoint(imageview.frame, currentTouchLocation))
            {
                if((currentTouchLocation.x >= imageview.frame.origin.x + gapX && currentTouchLocation.x < imageview.frame.origin.x + imageview.frame.size.width  - gapX) && (currentTouchLocation.y >= imageview.frame.origin.y  + gapY && currentTouchLocation.y < imageview.frame.origin.y + imageview.frame.size.height - gapY ))
                {
                    if([[ischose objectAtIndex:i-1] boolValue] == 0 && !isreverse)
                    {
                        currentposition = imageview.tag;
                        positionvalue += pow(i, 3);
                        currentanswer += [self converter:[NSString stringWithFormat:@"%@", [allimagenumbers substringWithRange:NSMakeRange(i-1, 1)]]];
                        [ischose replaceObjectAtIndex:i-1 withObject:[NSNumber numberWithBool:YES]];
                        [self changeimage:@"selected"];
                    }
                    else
                    {
                        if(currentposition != imageview.tag)
                        {
                            isreverse = YES;
                        }
                        else
                        {
                            isreverse = NO;
                        }
                    }
                    break;
                }
            }
        }
    }
    else
    {
        isended = YES;
        isoutofbound = YES;
        if(isbegan && isoutofbound)
            [self countinganswer];
    }
}
}

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
[super touchesEnded:touches withEvent:event];
if(!isoutofbound)
{
    isended = YES;
    [self countinganswer];
}
else
    isoutofbound = NO;
}

-(void)changeimage:(NSString *)status{
if([status isEqualToString:@"default"])
{
    for(int i = 1; i <=16;i++)
    {
        UIImageView *imageview = (UIImageView*)[self.numberview viewWithTag:i];
        imageview.image = [UIImage imageNamed:[NSString stringWithFormat:@"stone%@", [allimagenumbers substringWithRange:NSMakeRange(i-1, 1)]]];
        [image1 setUserInteractionEnabled:YES];
    }
}
else if([status isEqualToString:@"correct"] || [status isEqualToString:@"selected"])
{
    for(int i = 1; i<= ischose.count; i++)
    {
        if([[ischose objectAtIndex:i-1] boolValue] == 1)
        {
            UIImageView *imageview = (UIImageView*)[self.numberview viewWithTag:i];
            imageview.image = [UIImage imageNamed:[NSString stringWithFormat:@"stone%@_correct", [allimagenumbers substringWithRange:NSMakeRange(i-1, 1)]]];
        }
    }
}
else if([status isEqualToString:@"wrong"] || [status isEqualToString:@"repeat"])
{
    for(int i = 1; i<= ischose.count; i++)
    {
        if([[ischose objectAtIndex:i-1] boolValue] == 1)
        {
            UIImageView *imageview = (UIImageView*)[self.numberview viewWithTag:i];
            imageview.image = [UIImage imageNamed:[NSString stringWithFormat:@"stone%@_wrong_repeat", [allimagenumbers substringWithRange:NSMakeRange(i-1, 1)]]];
        }
    }
}
}

2 个答案:

答案 0 :(得分:0)

<强>更新

与您聊天,您似乎已经解决了问题(未检测到某个UIImageView对象的滑动)。看起来该解决方案是与您的代码相关联的唯一问题(即,在Stack Overflow语言中高度“本地化”),以创建使用gap变量构建的缩小“命中区域”。看起来解决方案与touchesMoved,iOS API或iOS系统性能无关。无论如何,我很高兴你解决了这个问题。

我在下面的原始答案取决于发布的原始源代码,它对16个UIImageView对象中的每一个都重复了相同的逻辑。我只是在演示如何使用UIArray来大大简化逻辑。我也使用UIPanGestureRecognizer,我认为统一代码,并且<UIKit/UIGestureRecognizerSubclass.h>你可以取消手势,以防用户的手势“超出界限”。


原始回答:

我假设您只是想构建一个图像数字数组,因为用户将手指拖过数字。所以ARC代码可能看起来像:

//  NumberGameViewController.m

#import "NumberGameViewController.h"
#import <UIKit/UIGestureRecognizerSubclass.h>

@interface NumberGameViewController ()
{
    NSArray *images;
    NSMutableArray *results;
}
@end

@implementation NumberGameViewController

- (void)viewDidLoad
{
    [super viewDidLoad];

    // if you build an array of your images, the logic to determine which image you're over is much easier

    images = @[self.image1, self.image2, self.image3, self.image4, self.image5, self.image6, self.image7, self.image8, self.image9, self.image10, self.image11, self.image12, self.image13, self.image14, self.image15, self.image16];

    // I know you used `touchesMoved` and the like, but I think gesture recognizers are a little easier

    UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
    [self.numberview addGestureRecognizer:pan];
}

- (NSInteger)determineImageNumber:(CGPoint)point
{
    for (NSInteger i = 0; i < [images count]; i++)
    {
        UIImageView *imageview = images[i];

        // I'm just going to see if the user's finger was over the number in question.
        // If you wanted more restrictive logic (e.g. 3/4ths of the frame), just adjust
        // adjust the frame variable here. 

        CGRect frame = imageview.frame;
        if (CGRectContainsPoint(frame, point))
            return i;
    }

    return -1;
}

- (void)handlePan:(UIGestureRecognizer *)gesture
{
    CGPoint location = [gesture locationInView:self.numberview];
    NSInteger imageNumber = [self determineImageNumber:location];
    static NSInteger lastImageNumber;

    if (gesture.state == UIGestureRecognizerStateBegan)
    {
        results = [[NSMutableArray alloc] init];
        if (imageNumber >= 0)
        {
            [results addObject:@(imageNumber)];
        }
    }
    else if (gesture.state == UIGestureRecognizerStateChanged)
    {
        if (imageNumber >= 0)
        {
            if (imageNumber != lastImageNumber)
            {
                // If you want to do some visual adjustment of the image you're over, do it
                // here.

                // add the image to our array of results

                [results addObject:@(imageNumber)];

                // if you want to do some additional validation (e.g. do you have 16 points,
                // has the user hit the same number twice, etc.), do that here
            }
        }

        // by the way, let's check to see if we're still within the numberview subview, and if
        // not, let's cancel the gesture

        if (!CGRectContainsPoint(self.numberview.bounds, location))
        {
            gesture.state = UIGestureRecognizerStateCancelled;
            return;
        }
    }
    else if ((gesture.state == UIGestureRecognizerStateEnded) || (gesture.state == UIGestureRecognizerStateCancelled) || (gesture.state == UIGestureRecognizerStateFailed))
    {
        // At this point you'd do any final validation of the user's response, to see if they
        // succeeded or not. I'm just displaying the results in the console

        NSLog(@"%@", results);
    }

    if (imageNumber >= 0)
        lastImageNumber = imageNumber;
}

@end

答案 1 :(得分:0)

float gapX = image1.frame.size.width / 8;
float gapY = image1.frame.size.height / 8;

问题是,所有图像中都有间隙,因此快速拖动时它将是图像的外部部分