esempio UIView multipla non funziona
-
18-09-2019 - |
Domanda
Ho sottoclasse classe UIView in una classe Bounce con accelerometro. Questa classe Bounce mostrare un'immagine e spostarla sullo schermo. Quando il dispositivo iPhone viene mosso, questa immagine Rimbalzo sullo schermo.
Quando creo multi-istanza, solo ultimo lavoro istanza properlty:
// in the MainViewController.m
Bounce *heart[100];
for(int i = 0; i < 10; i++) {
rx = (arc4random() % 300) + 10;
ry = (arc4random() % 300) + 10;
NSLog(@"random %d %d", rx, ry);
heart[i] = [[Bounce alloc] initWithPNG:@"Heart.png"
position:CGPointMake(rx, ry) size:CGSizeMake(64, 64)];
heart[i].velocity = CGPointMake(1.0, 1.0);
[self.view addSubview: heart[i]];
}
Questa è la classe Bounce:
//
// Bounce.h
// iMakeLove
//
// Created by Giovambattista Fazioli on 06/11/09.
// Copyright 2009 Saidmade srl. All rights reserved.
//
#import <UIKit/UIKit.h>
@interface Bounce : UIView <UIAccelerometerDelegate> {
CGPoint position;
CGSize size;
CGPoint velocity;
NSTimer *objTimer;
NSString *pngName;
CGFloat bounce;
CGFloat gravity;
CGPoint acceleratedGravity;
CGPoint lastTouch;
CGPoint currentTouch;
BOOL dragging;
UIAccelerometer *accelerometer;
}
@property CGPoint position;
@property CGSize size;
@property CGPoint velocity;
@property(nonatomic,retain)NSString *pngName;
@property(nonatomic,retain)NSTimer *objTimer;
@property CGFloat bounce;
@property CGFloat gravity;
@property CGPoint acceleratedGravity;
@property CGPoint lastTouch;
@property CGPoint currentTouch;
@property BOOL dragging;
- (id)initWithPNG:(NSString*)imageName position:(CGPoint)p size:(CGSize)s;
- (void)update;
- (void)onTimer;
- (void)startPrevent;
@end
Implementazione:
//
// Bounce.m
// iMakeLove
//
// Created by Giovambattista Fazioli on 06/11/09.
// Copyright 2009 Saidmade srl. All rights reserved.
//
#import "Bounce.h"
@implementation Bounce
@synthesize position, size;
@synthesize objTimer;
@synthesize velocity;
@synthesize pngName;
@synthesize bounce;
@synthesize gravity, acceleratedGravity;
@synthesize lastTouch, currentTouch;
@synthesize dragging;
- (id)initWithPNG:(NSString*)imageName position:(CGPoint)p size:(CGSize)s {
if (self = [super initWithFrame:CGRectMake(p.x, p.y, s.width, s.height)]) {
[self setPngName:imageName];
[self setPosition:p];
[self setSize:s];
[self setBackgroundColor:[UIColor clearColor]];
// Set default gravity and bounce
[self setBounce:-0.9f];
[self setGravity:0.5f];
[self setAcceleratedGravity:CGPointMake(0.0, gravity)];
[self setDragging:NO];
UIImageView *prezzie = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, s.width, s.height)];
prezzie.image = [UIImage imageNamed:imageName];
[self addSubview:prezzie];
[prezzie release];
self.accelerometer = [UIAccelerometer sharedAccelerometer];
self.accelerometer.delegate = self;
}
return self;
}
- (void)startPrevent {
if (objTimer == nil) {
objTimer = [NSTimer scheduledTimerWithTimeInterval:1.0 / 30.0 target:self selector:@selector(onTimer) userInfo:nil repeats:YES];
}
}
- (void)update {
[self setNeedsDisplay];
if(dragging) return;
velocity.x += acceleratedGravity.x;
velocity.y += acceleratedGravity.y;
position.x += velocity.x;
position.y += velocity.y;
if(position.x + size.width >= 320.0) {
position.x = 320.0 - size.width;
velocity.x *= bounce;
} else if(position.x <= 0.0) {
velocity.x *= bounce;
}
if(position.y + size.height >= 480.0) {
position.y = 480.0 - size.height;
velocity.y *= bounce;
} else if(position.y <= 0.0) {
velocity.y *= bounce;
}
self.frame = CGRectMake(position.x, position.y, size.width, size.height);
}
- (void)onTimer {
[self update];
}
- (void)drawRect:(CGRect)rect {
// Drawing code
}
/* EVENTS */
- (void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration {
acceleratedGravity.x = acceleration.x * gravity;
acceleratedGravity.y = -acceleration.y * gravity;
}
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
// First, lets check to make sure the timer has been initiated
if (objTimer == nil) {
objTimer = [NSTimer scheduledTimerWithTimeInterval:1.0 / 30.0 target:self selector:@selector(onTimer) userInfo:nil repeats:YES];
}
UITouch *touch = [touches anyObject];
[self setCurrentTouch:[touch locationInView:self]];
CGFloat dx = currentTouch.x - position.x;
CGFloat dy = currentTouch.y - position.y;
CGFloat dist = sqrt(dx * dx + dy * dy);
if(dist < size.width) {
[self setVelocity:CGPointMake(0.0, 0.0)];
[self setDragging:YES];
}
[self setLastTouch:currentTouch];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
UITouch *touch = [touches anyObject];
[self setCurrentTouch:[touch locationInView:self]];
[self setDragging:YES];
[self setVelocity:CGPointMake(currentTouch.x - lastTouch.x, currentTouch.y - lastTouch.y)];
[self setLastTouch:currentTouch];
}
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
[self setDragging:NO];
}
- (id)initWithFrame:(CGRect)frame {
if (self = [super initWithFrame:frame]) {
// Initialization code
}
return self;
}
- (void)dealloc {
[super dealloc];
}
@end
Mi potete aiutare?
Soluzione
Questo perché self.accelerometer.delegate = self;
sta cambiando delegato del sharedAccelerometer
e solo l'ultimo incarico avrà effetto.
Altri suggerimenti
Credo che solo il front-più vista otterrà i messaggi accelerometro. Si potrebbe desiderare i messaggi accelerometro da inviare al vostro viewcontroller invece.
Cosa potrei fare qui. (Esso non può essere la cosa migliore a lungo termine, ma risolvere il problema immediato) è questo:
mi piacerebbe fare la gravità accelerato una variabile statica condivisa tra tutte le istanze di rimbalzo. Questo rende sence per me, perché nel mondo reale (quella che stiamo simulando) la gravità accelerata sarebbe lo stesso per tutti i rimbalzi. (Mi piacerebbe anche rinominare rimbalzo a qualcosa come BouncingView). Mi piacerebbe accedere a tale variabile attraverso un paio di metodi di classe. Inoltre, mi piacerebbe fare l'accelerometro condiviso, e avere il suo metodo delegato, un metodo di classe. Mettete questa roba nella tua classe e dovrebbe funzionare:. (. Mi piacerebbe provarlo ma la mia macchina di sviluppo è presso l'Apple Store ottenendo fisso) Inoltre, ci sono un paio errori di sintassi nel codice di esempio che hai postato
static CGCGPoint acceleratedGravity;
static UIAccelerometer *accelerometer;
-(void) init {
/* Everything Else */
self.accelerometer = [UIAccelerometer sharedAccelerometer];
self.accelerometer.delegate = self;
/*Everything Else */
}
+(CGPoint) acceleratedGravity {
return acceleratedGravity;
}
+(void) setAcceleratedGravity:(CGPoint) _acceleratedGravity {
acceleratedGravity = _acceleratedGravity;
}
+ (void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration {
acceleratedGravity.x = acceleration.x * gravity;
acceleratedGravity.y = -acceleration.y * gravity;
}