Como manter as ligações de cacau funcionando depois de substituir a instância do objeto de destino por outra instância do mesmo tipo?
-
12-09-2019 - |
Pergunta
Eu gostaria de poder usar ligações para manter minha GUI sincronizada com um objeto carregado dinamicamente, mas assim que substituo o objeto em questão por outro do mesmo tipo que as ligações quebram e a GUI para de atualizar. Aqui está algum código para ajudá -lo a entender o que quero dizer:
Na minha interface, tenho uma variável de instância para manter o objeto em questão:
@interface AppDelegate : NSObject {
CustomObject *anObject; // This object has a "NSString *textValue" property
}
Então, na minha implementação, instancie o objeto:
- (id) init {
self = [super init];
if (self != nil) {
anObject = [[CustomObject alloc] init];
}
return self;
}
No construtor de interface, tenho o "valor" de um campo de texto ligado a "anobject.textValue".
Quando eu chamo este método:
[anObject setValue:@"Changed anObject.textValue!" forKey:@"textValue"];
Em seguida, o campo de texto atualiza para refletir o novo valor.
Mas o que eu quero fazer é exibir os valores de um objeto que é dado depois de fazer algum trabalho em outras partes do aplicativo. Então, o que eu fiz foi o seguinte:
- (void)setCustomObject:(CustomObject *)newObject {
anObject = newObject;
}
Agora, o resultado desta operação parece quebrar as ligações da GUI à instância do CustomObject (anobject), que parece lógica, considerando que o objeto ligado foi substituído por outra instância.
O que eu quero saber é se existe uma maneira de manter as ligações funcionais com a instância criada dinamicamente do CustomObject sem ter que fazer novamente todos os controle programaticamente através bind:toObject:forKeyPath:options:
ou similar, o que exigiria (a meu conhecimento) o uso de iboutlets para se apossar dos controles para poder ligá -los aos valores em meu novo objeto (IMO isso tornaria as ligações inúteis na minha situação). Esta é a única solução ou existe uma maneira melhor e mais limpa de lidar com isso?
Eu li um bom monte de documentos no desenvolvimento.apple.com e em outros lugares em relação às ligações, mas não encontrei nada que parece falar sobre esse caso em particular.
Agradeço antecipadamente pelo seu tempo!
Solução
Para ser específico, acho que o problema era que seu método de setter foi chamado -setCustomObject:
ao invés de -setAnObject:
. Se você fez exatamente essa alteração, acho que o KVO seria invocado e seus campos de texto vinculados serão atualizados.
A nota de Abizern sobre o vazamento (se você não está usando o GC) ainda se aplica. Seu setter deve parecer algo como:
- (void)setAnObject:(CustomObject *)newObject {
if (anObject != newObject) {
[anObject release];
anObject = [newObject retain];
}
}
Outras dicas
Dê uma olhada nesses documentos Observação do valor da chave. Isso deve mostrar como alterar as propriedades de uma maneira compatível com o KVO.
Como alternativa, configure o AnoBject como uma propriedade:
@interface AppDelegate : NSObject {
CustomObject *anObject; // This object has a "NSString *textValue" property
}
@property (retain) CustomObject *anObject;
...
@end
@interface AppDelegate
@synthesize anObject;
...
@end
Em seguida, ao alterar a instância do AnoBject, use a sintaxe da propriedade.
self.anObject = newObject;
Isso cuidará das coisas do KVO para você.
Nota: a menos que você tenha gc ligado ao seu setCustomObject:
vazamentos de método.