2012-09-06 3 views
1

Я реализую объектную C-оболочку для Box2d (написанную на C++). B2Body сохраняет ссылку на свою обертку B2Body в поле userData. GetUserData возвращает пустоту *. Теперь я внедряю быструю итерацию для того, чтобы вытащить из 2DWorld.'Назначение' id 'из несовместимого типа'

Я получаю сообщение «Присвоить идентификатор» из несовместимого типа «B2Body *» в строке, указанной ниже. Зачем?

#import "B2Body.h" 
#import "B2World.h" 
#import "Box2d.h" 

@implementation B2World 

-(id) initWithGravity:(struct B2Vec2) g 
{ 
    if (self = [super init]) 
    { 
    b2Vec2 *gPrim = (b2Vec2*)&g; 
    _world = new b2World(*gPrim); 
    } 

    return self; 
} 

- (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id __unsafe_unretained [])buffer count:(NSUInteger)len; 

{ 
    if(state->state == 0) 
    { 
    state->mutationsPtr = (unsigned long *)self; 
    state->extra[0] = (long) ((b2World*)_world)->GetBodyList(); 
    state->state = 1; 
    } 

    // pull the box2d body out of extra[0] 
    b2Body *b = (b2Body*)state->extra[0]; 

    // if it's nil then we're done enumerating, return 0 to end 
    if(b == nil) 
    { 
    return nil; 
    } 

    // otherwise, point itemsPtr at the node's value 
    state->itemsPtr = ((B2Body*)b->GetUserData()); // ERROR 
    state->extra[0] = (long)b->GetNext(); 

    // we're returning exactly one item 
    return 1; 
} 

`

B2Body.h выглядит следующим образом: #import

@interface B2Body : NSObject 
{ 
    int f; 
} 

-(id) init; 
@end 
+0

Какая строка указана ниже? – deanWombourne

+0

Тот, который отмечен // ERROR –

+0

А, извините. Я слепой :) – deanWombourne

ответ

2

NSFastEnumerationState представляет собой структуру С, а itemsPtr поле:

id __unsafe_unretained *itemsPtr; 

В начале версии, спецификатор __unsafe_unretained был явно отсутствует.

Обратите внимание, что поле itemsPtr является указателем на идентификатор. Поскольку id по существу является указателем, itemsPtr является указателем на указатель объекта. Фактически это поле содержит массив объектов, который позволяет быстро перечислять. В принципе, он троллирует через этот массив указателей объектов.

Поскольку я ничего не знаю о Box2d, это все, что я могу сказать. Предполагая, b-> GetUserData() возвращает указатель на массив объектов, вы должны быть в состоянии сделать это:

state->itemsPtr = (__unsafe_unretained id *)b->GetUserData(); 

Хотя немного устаревшей, Mike Ash's article еще большим источником для осуществления быстрого перечисления.

EDIT

Просто заметил, что вы возвращаете один объект. Итак, я полагаю, что GetUserData просто возвращает один указатель на объект. Так как вам нужно, чтобы вернуть указатель на объект указатели, вам нужно будет сделать что-то вроде этого:

id object = (__bridge id)b->GetUserData(); 
state->itemsPtr = &object; 

Однако, этот объект стек исчезнет, ​​как только вы вернетесь из этого метода, поэтому вы прошли стек буфер, который вы можете использовать. Таким образом, вы должны, вероятно, наложить этот единственный указатель на предоставленный буфер стека:

*buffer = (__bridge id)b->GetUserData() 
state->itemsPtr = buffer;