Cacau: plug-in não pode abrir App Janela
-
18-09-2019 - |
Pergunta
Estou desenvolvendo um plugin para OsiriX .
Nesse aplicativo eu tenho 3-4 arquivos nib. Também em para Plugin existem arquivos (.h & .m) chamou PluginFilter onde método chamado - (longo) filterImage: (NSString) menuname está presente a partir do qual a execução do plugin início. Agora o meu problema é que, tenho retornar o código para abrir a janela principal está em algum outro arquivo .m e eu tenho que chamar esse arquivo usando o método mencionado acima.
O aplicativo tem vários arquivos nib. Eu tenho um PluginFilter nome plugin chamado por:
- (long) filterImage:(NSString*) menuName
O plugin deve abrir uma janela quando chamado por este método. O código que define o controlador de janela está em outra ponta. Quando eu chamar o método filterimage
no plugin, a janela nunca aparece.
Aqui é o meu método filterImage:
.
#import "XGridInOsiriXFilter.h"
#import "MainWindowController.h"
@implementation XGridInOsiriXFilter
- (void) initPlugin
{
}
- (long) filterImage:(NSString*) menuName
{
MainWindowController *mainWindowController = [[GridSampleMainWindowController alloc] init];
[mainWindowController showWindow:self ];
[mainWindowController release];
return 0;
}
@end
Chamar o método não produz avisos ou erros, a janela simplesmente não aparece.
Solução
Você normalmente não abrir a janela principal do aplicativo a partir de um plugin. Plugins, por definição, a minha não estar sempre presente para que você não deve colocar o código crítico neles. Nem que você quer vários plugins de abertura da mesma janela lógica.
Em vez disso, a janela principal deve ser apresentado pelo delegado aplicativo como normal, mas o conteúdo da janela pode ser processado por um plugin se o plugin está disponível.
A aplicação principal deve carregar e configurar a janela principal e só chamar o plugin para processar o conteúdo da janela.
Mesmo por isso é tecnicamente possível abrir uma janela de um plug-in para que quer (1) o plug-in não está a ser carregado e o método não está a ser chamado (inserção ponto de interrupção / log para confirmar a) ou (2) o controlador de janela é mal configurado de forma que ele não abrir a janela. Testar o controlador de fora do plugin para confirmar que funciona. Melhor ainda, mover o código de abertura da janela fora do plugin.
Edit01:
De comentário:
Eu fiz algumas mudanças na acima código da seguinte forma
- (long) filterImage:(NSString*) menuName {
MainWindowController *mainWindowController = [[GridSampleMainWindowController alloc] init:self];
[mainWindowController showWindow:self ];
[mainWindowController release];
return 0;
}
mas ele está mostrando wanring que nenhuma método -init encontrado. Por que ele está mostrando como esta porque o método -init é der no arquivo MainWindowController.m
Bem, você tem dois problemas aqui.
(1) Você define definir mainWindowController
partir de MainWindowController
classe, mas você inicializa-lo com GridSampleMainWindowController
classe. Se MainWindowController
é uma subclasse de GridSampleMainWindowController
isso vai funcionar, mas vai gerar avisos. em vez disso você deve inicializar-lo como
GridSampleMainWindowController *mainWindowController = [[GridSampleMainWindowController alloc] init:self];
ou
MainWindowController *mainWindowController = [[MainWindowController alloc] init:self];
(2) Você liberar o controlador sem qualquer outro objeto retê-lo que irá matá-lo. Quando um controlador de janela morre, desaloca as janelas que ele controla. Isso é mais provável porque você não vê nada.
Você deve resolver o que classe que você quer que o controlador ser e, em seguida, defini-lo como uma propriedade retidos da classe plug-in para que possa manter-se uma sua janela ao redor.
Qual o método init
é que reclamando? Seu initPlugin
não faz nada e retorna um void
se isso é método de inicialização real do plug-in, em seguida, o plugin não irá carregar. Ele deve pelo menos olhar como esta:
- (id) initPlugin
{
self=[super init];
return self;
}
Parece que você vem de um fundo puro C que é ótimo para este ambiente, mas você precisa aprender sobre as partes orientadas a objeto da linguagem Objective-C. Você ainda está escrevendo métodos como se fossem funções velha escola C e há importantes e oft vezes sutis diferenças.
Desculpe eu perdi tudo isso ontem. Eu vi "plug-in" e focada no aspecto errado do problema.
Edit02:
Não, eu estou não falar sobre minha initPlugin método. Eu estou falando sobre a minha Init método que existe em arquivo MainWindowController.m
- (id)init {
self = [super initWithWindowNibName:@"MainWindow"];
return self;
}
Isso irá retornar uma instância da classe super do MainWindowController
. Se você não está fazendo qualquer personalização que você não tem necessidade de substituir o método init em você subclasse. Basta usar a versão herdada assim:
MainWindowController *mainWindowController = [[MainWindowController alloc] initWithWindowNibName:@"MainWindow"];
Outras dicas
Eu reconheço isso pode estar chegando um pouco tarde demais, mas eu estava procurando uma maneira de fazer a mesma coisa que você está pedindo e encontrou. Você pode usar NSBundle
para carregar a ponta desejado e apontá-lo para um controlador instanciado. Como:
@implementation YourPluginFilter
- (void) initPlugin
{
yourWindowController = [[YourWindowController alloc] init];
NSLog(@"Initialized YourWindowController");
}
- (long) filterImage:(NSString*) menuName
{
if (yourWindowController && [NSBundle loadNibNamed:@"YourNibName" owner:yourWindowController]) {
NSLog(@"Activated yourWindowController");
return 0;
} else {
return -1;
}
}
@end