2012-04-03 5 views
13

Faits sur Matlab:GUI réactif sans appeler Matlab drawnow() directement

  1. UI Java Swing est Matlab.
  2. MATLAB a une excellente interopérabilité avec Java, il est possible d'initialiser des objets Java et d'appeler leurs méthodes directement à partir du code MATLAB, il est même possible de passer en Java des listeners définis par MATLAB!

Mon problème:

Matlab ne propose pas de fils de fond, afin de rendre l'interface utilisateur Matlab répondre, nous devons appeler la fonction drawnow qui débusque la file d'attente Swing EDT, vous pouvez aussi here et here. C'est un fait connu, jusqu'ici tout va bien.

Mais maintenant j'ai un client dont le code qui effectue le calcul est un fichier p MATLAB (crypté) donc je n'ai pas accès au code pour y mettre drawnow.

Tentative infructueuse:

J'ai essayé filer une minuterie pour faire le travail d'appeler drawnow mais il ne semble pas fonctionner - même minuterie a besoin d'un précédent drawnow pour tirer ses callbacks. À la fin j'ai implémenté l'interface graphique avec .NET/WPF fonctionnant sur un autre thread, donc il reste toujours réactif et semble beaucoup mieux que MATLAB d'origine.

Répondre

2

Juste une idée. Vous pouvez créer un fichier jar à partir du fichier p en utilisant Matlab Builder pour Java. Depuis Java, vous pouvez faire le calcul maintenant dans un fil séparé.

+0

C'est une solution très laide, mais cela pourrait fonctionner. ** Je dois le tester avant de pouvoir le noter **. – Mikhail

7

Je ne sais pas si cela peut être fait correctement. Je n'ai jamais trouvé un moyen d'obtenir l'effet de drawnow au milieu d'un fichier mex, et je suppose que cette situation est similaire. Mais voici un hack incroyablement désordonné de toute façon: D. Si vous avez un fichier p, vous pouvez exécuter:

profile on; 
pfile(); 
profile viewer; 

et d'avoir une idée des fonctions que pfile() appelle. Si le code appelle des fonctions intégrées (par exemple disp) ou toute fonction dont vous avez accès au code source, vous pouvez créer votre propre version de ce fichier plus loin dans le chemin, qui sera appelée par le fichier p, par exemple Cela s'appellera drawnow au plus une fois toutes les 5 secondes, mais il ne sera pas très utile si disp n'est appelé régulièrement. Si vous ne pouvez pas trouver un composant à remplacer, vous pouvez utiliser n'importe quelle autre fonction et simplement insérer la partie drawnow en haut, comme:

function primes(N) 
    if (toc > 5) 
    drawnow; 
    tic; 
    end 
    The rest of the original primes.m here. 
+0

Très intelligent! Qu'en est-il de la visibilité/préséance lorsque je substitue (a) une fonction intégrée comme 'disp' (b) une fonction définie par l'utilisateur comme' primes', qui est peut-être p-codée elle-même? – Mikhail

+1

C'est assez salissant. Je pensais qu'il y avait toujours un moyen de se référer spécifiquement à une fonction (même si c'était prioritaire), mais je ne peux pas le trouver maintenant. Si je comprends bien, 'path' définit exactement quelles fonctions sont visibles. Toutes les autres fonctions surchargées ne semblent pas être accessibles, sauf pour les fonctions intégrées, où 'builtin (...)' vous permet d'y accéder.Je ne pense pas que p-coded-ness affecte la visibilité/précédence: s'il y a une fonction avec le même nom plus haut dans le chemin, alors elle aura la priorité. – Richante