• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:MATLABのGUIについて教えていただけないでしょうか。)

MATLABのGUIについて教えていただけないでしょうか。

このQ&Aのポイント
  • MATLABのGUIの使い方を教えていただけませんか。
  • 128x128pixelの画像が40枚でセットになっているデータをMATLABのGUIで表示したいのですがうまくいきません。
  • スライドバーの値をリアルタイムに表示された画像に反映する方法を教えてください。

質問者が選んだベストアンサー

  • ベストアンサー
  • Kules
  • ベストアンサー率47% (292/619)
回答No.2

再びKulesです。 >「set(H.image,'Cdata',H.tempA(:,:,SliceNum));」 >の部分で「??? サブスクリプトインデックスは正の実数整数, またはロジカルである必要があります」 >というエラーになるのですが… このエラーは実は回答してからすぐに気づいたのですが、まあスライダをドラッグしたりしなければ問題ないかな…と思って放置してました(笑) その1行上の SliceNum=(get(H.slider,'Value')); を SliceNum=round(get(H.slider,'Value')); に変えて下さい。このプログラム自体はこれで動くと思います。 >これ以外にどんな変数でも好きに格納できる便利なハンドルを作れる、ということなのでしょうか? 変数を格納するハンドルを作る…というよりはguidataは変数を直接figureに格納する関数です。ちょっと実験してみましょう。 figure; a=guidata(gcf); b=3; guidata(gcf,b); clear all; c=guidata(gcf); 上の6行をコマンドウィンドウから1行ずつ実行してみてください。 2行目の結果はa=[]、つまり空行列になると思います。 で、4行目で現在のfigureにbの値を格納したことになります。 5行目でワークスペース上には変数がなくなりますが、 6行目でcに先ほど格納した値が入っていることが確認できます。 また、上の例からもわかるように、変数を格納する時と取りだす時で変数名が違っていてもかまいません。なんだったら4行目をguidata(gcf,3)としてもfigureに3という値が格納されます。 今回の場合、どんな変数を保存すればいいかという話ですが、「じゃあ今回の操作をする場合何の値が必要?」を考える必要があります。 実のところを言えば、今回絶対に保存しないといけないのは画像データtempAだけです。それ以外のハンドルとかはguihandleやfindobjで探してやっても構いません。 ただ、いちいち探すのはめんどくさいということで今回は ・各種ハンドル(figure、スライダ、イメージ、軸) ・tempA(画像データ) を構造体Hとして宣言し、guidata(gcf,H)でfigureの中に格納してます。 先ほどの例でいうと、 H.○○=△△; となっているのが変数の宣言部(構造体はまだ存在しないメンバ名を宣言すれば勝手に追加されていきます)、guidata(H.figure,H);となっているのが変数を保存している部分、H=guidata(○○);が変数を取り出している部分となります。 ここからは私の勝手な感想ですが… Matlabはホントに初心者に不親切な言語だなあ…と思います。私自身Matlabに初めて触ってからまだ2年経ってませんが、始めたころは大学の研究室にあった本を読んでもさっぱりでした。 ということで、ヘルプを読んでもネットを読んでもよくわからない~という状態は気にしなくていいと思います。ネット上の情報に関しては、「わかる人にしかわからない」度合は相当高いんじゃないかと個人的には思っているので(笑) と言ってもじゃあわかんなくていいということではないので、とりあえず私が去年買って勉強に使った本を紹介します。 秀和システム「MATLABハンドブック 第三版」小林一行 ひょっとしたらもう次の版が出てるかも。 400ページぐらいある分厚い本ですが、当面必要なのはChapter 1,(2),5ぐらいです。特にhandleの扱いに関してはChapter5を読み込んでやりましょう。 この本を読んでhandleの扱い方が何となくわかったら、後はMatlabヘルプデスクの、 関数:アルファベット順 http://www.mathworks.co.jp/access/helpdesk_ja_JP/help/techdoc/ref/funcalpha.html の中に「~プロパティ」という項目があるので、それをじっくり読んでいくとそれぞれのプロパティの扱いがわかると思います。 長文失礼しました。やっぱりわからんというところがあれば補足欄にお願いします。 参考になれば幸いです。

yatz
質問者

お礼

Kulesさん 何度も教えてくださってありがとうございます。今回のご説明のおかげで、ようやくHandleと構造体の関係がわかりました。今まで何が理解できていなかったのかがようやくわかり、前進できそうです。今回書いていただいたスクリプトの中にはまだよくわからない(知らない)箇所もありますが、これをベースにもう少し勉強して理解してみたいと思います。 本当に助かりました。実はMATLABハンドブックは今回の質問にぶち当たってからWebでの評判を頼りに買ったのですが上記がわかっていなかったために、肝心の所を解決できずにいました。同じような立場の人のために今回のKulesさんの解説を書き加えたい…(^-^; また後日に別の質問スレッドを立ててしまう可能性もありますが、たまたまお時間おありでしたらまた教えてください。ありがとうございました。

その他の回答 (1)

  • Kules
  • ベストアンサー率47% (292/619)
回答No.1

CallBack中に変数を使いたい場合、 (1)引数として渡す (2)どこかに保存しておいて、そこから呼びだす の2通りが考えられると思います。私の場合、 (1)→(2)(予めmatfileとして保存し、その都度呼び出す)→(2)(guidataを使う) の順にスタイルが変わっています。 guidataはfigure内に値をストックするための関数で、figure内のハンドルであればどれを使ってもストックした変数を呼び出せるので大変便利です。 ということでそれを使える関数を書いてみました。 「 function MakeSlider(String,varargin) switch(lower(String)); case 'make'; InitSlider(varargin{1}); case 'imageslice'; MoveSlice; otherwise; error('関数MakeSliderの受け付ける動作は''Make''のみです') end; function InitSlider(Handle) H=guidata(Handle); H.slider=uicontrol(H.figure,'Style','Slider'); H.image=image(zeros(128,128)); H.axes=gca; set(gca,'PlotBoxAspectRatio',[1,1,1]); FigureSize=get(H.figure,'Position'); set(H.slider,'Position',[FigureSize(3)-30,10,25,FigureSize(4)-20]); set(H.slider,'Min',1,'Max',40,'Value',1,'SliderStep',[1,5]/39); set(H.slider,'CallBack','MakeSlider(''ImageSlice'');'); guidata(H.figure,H); return; function MoveSlice H=guidata(gcbo); SliceNum=(get(H.slider,'Value')); set(H.image,'Cdata',H.tempA(:,:,SliceNum)); return; 」 「」の間を1つのmファイル(MakeSlider.m)として保存し、 H.figure=figure(1); H.tempA=tempA; guidata(H.figure,H); MakeSlider('Make',gcf); のようにするとfigureの右端にsliderがつき、上または下矢印を押すことで1枚ずつ画像が変わります。 また、スライダのトラフを押すと一度に5枚先に飛ぶようにしてあります。 この関数自体決め打ちで値を入れているところが多いため 他の設定にするには中の値をいじるか、設定が変わっても柔軟に対応できるようにさらに改良する必要があります。 コメントをほとんどつけていないので、何をしているのかわからない部分があれば補足欄にお願いします。 以上、参考になれば幸いです。

yatz
質問者

お礼

お礼を書かないとベストアンサーがつけられない??試しに記入してみます。

yatz
質問者

補足

早速のご回答ありがとうございます。 しかし、せっかくなのですが、うまく理解できませんでした。 guihandle、guidataを用いて変数をやりとりする、という意味はなんとなくわかるのですが、どんな変数をどうやって保存するのか理解できません。本当に初歩的な問題なのだと思うのですが、ヘルプを読んでもネットを検索してもよくわからないんです。 オブジェクト(axisとかPushbuttonとか)はあらかじめデフォルトのハンドルを持っていますよね。これ以外にどんな変数でも好きに格納できる便利なハンドルを作れる、ということなのでしょうか?そのハンドル名はどうやって宣言したらいいのでしょう?? 教えていただいたスクリプトを実行してみましたが、 「set(H.image,'Cdata',H.tempA(:,:,SliceNum));」 の部分で「??? サブスクリプトインデックスは正の実数整数, またはロジカルである必要があります」 というエラーになるのですが…このような状況なのでせっかくのサンプルスクリプトをうまくかみ砕けませんでした。 おそらくかなりくだらないことを聞いているのだと思います。お忙しいようでしたら、もし、そんなこと質問する前にこの本を読むといいよ、というような本があれば教えていただけないでしょうか。門外漢な上に周囲に詳しい人もいないのでなかなか本を探すにも苦労しています。 いろいろ申し訳ありません。

関連するQ&A