Domanda

I'm working with the C4 framework on a project and I'm having a bit of trouble with using the gesture controls and calling methods from C4WorkSpace.

I found this link that had to do with this problem but it didn't seem to stop my program from throwing an error.

A little background: I'm creating a custom button class that has 4 properties: UIColor, C4Shape and 2 floats (x/y position). I'm storing the custom button objects in an array and have this bit of code going to add a gesture to each button and add it to the canvas.

C4WorkSpace.m

        for (button in buttonArray){
        [button.shape addGesture:TAP name:@"tapGesture" action:@"tapped"];
        [self.canvas addShape:button.shape];
        [self listenFor:@"tapped" fromObject:button andRunMethod:@"doThis:"];
}

And I also have a function outside my '-(void)setup' that just prints a log message:

-(void)doThis:(NSNotification *)notification{
NSLog(@"notification test");
}

I have extended my C4Shape class with a category and when I call this method it works fine:

#import "C4Shape+myC4Shape.h"

@implementation C4Shape (myC4Shape)

-(void)printTest{
    NSLog(@"this is a print test");
}
@end

The error I'm getting gets thrown when I try and tap on a button, it says: Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[C4Shape tapped]: unrecognized selector sent to instance 0x931e9c0'

I have my "action" set to 'tapped', but that's just something I made up. I know this usually calls a method inside the shape class, but I'm trying to call a method that isn't in the C4Shape class but on the main WorkSpace. I'm not sure what's causing this or what I'm doing wrong? Is there something specific I need to be writing in the 'action' part of the method?

È stato utile?

Soluzione

this Obj-C stuff can be confusing at first. Hopefully this will help.

I notice two things for you to change.

The first is in regards to your TAP gesture. When you add this to your code you're actually telling the gesture to recognize a TAP and then run the tapped method. However, this method doesn't exist (hence the -[C4Shape tapped]: unrecognized selector sent to instance 0x931e9c0). You should have a method in your code called -(void)tapped{}; for this message to go away.

The following code illustrates this:

@implementation C4WorkSpace

-(void)setup {
    [self addGesture:TAP name:@"tap" action:@"tapped"];
}

-(void)tapped {
    C4Log(@"tapped!");
}

@end

Putting that into a shape is quite similar.

Second, for the subclassing, C4Shape (and all other visual objects) inherit from C4Control so I would suggest that subclassing C4Control isn't the best approach. For creating your own custom button with a C4Shape I would subclass C4Shape directly.

The above code would look exactly the same for a subclassed C4Shape except that if you created a MyShape subclass would have @implementation MyShape instead.

Finally, you want to add a little broadcast message to your tap method so that the canvas can listen for it... All in all your .h and .m files for your subclass should look like this:

.h

#import "C4Shape.h"

@interface MyShape : C4Shape

@end

.m

#import "MyShape.h"

@implementation MyShape

-(void)setup {
    [self addGesture:TAP name:@"tap" action:@"tapped"];
}

-(void)tapped {
    [self postNotification:@"tapNotification"];
}

@end

Finally, with those two files in your project you can add the following to your workspace:

#import "C4WorkSpace.h"
#import "MyShape.h"

@implementation C4WorkSpace

-(void)setup {
    MyShape *m = [[MyShape alloc] init];
    [m rect:CGRectMake(0, 0, 100, 100)];
    m.center = self.canvas.center;
    [self.canvas addShape:m];

    [self listenFor:@"tapNotification" fromObject:m andRunMethod:@"heardTap:"];
}

-(void)heardTap:(NSNotification *)aNotification {
    MyShape *notificationShape = (MyShape *)[aNotification object];
    C4Log(@"%4.2f,%4.2f",notificationShape.center.x,notificationShape.center.y);
    C4Log(@"%@",notificationShape.strokeColor);
}

@end

Here's a link to a gist with the 3 files you'll need for this to run.

Button Subclass with Canvas Listener

PS thanks for giving C4 a try!


Oh, and this is the output I get in Xcode's console when I tap on the square:

[C4Log] 384.00,512.00
[C4Log] UIDeviceRGBColorSpace 1 0.1 0.1 1

This gives me the x and y coordinates, as well as the strokeColor of the "button" without having to add these as objects to the MyShape class (because they already exist in C4Shape).

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top