データファイルのオープンと共に、データファイル中の情報をframe上部に表示する

 "selecfile"関数を用いて数値データをビジュアルに選択し、単一の数値データをカレントframeにロードした後、Partsオブジェクトを作成し数値ファイル中の情報をframe上部に表示します。ここではファイルをオープンする方法及び正規表現を用いたパターンマッチングの方法に付いて学びます。

 この例では、数値データファイルは以下のような形式になっており、1行目が測定日時、2行目が試料番号、3行目が数値データ内容、4行目以降が数値データを表し、常にこの形式の数値ファイルを扱うものとします。ここで2行目の中の試料番号を抜きだし、frame上部に表示させることを考えます。

# date: May 6 1999
# sample No.: 3454
# V        I
  0        3.5654
  1        5.6765
  2        7.5643

  # initオブジェクトには数値データファイルのデフォルト拡張子が格納
  # されています。この拡張子は、ラベル'dataext'の値で参照されます。
  # まずラベル'dataext'が存在するか確認します。'dataext'は通常初期化
  # スクリプトinitparamsでTopaz起動時に設定されますので、通常は存在
  # するはずです。デフォルトの拡張子を取得後、変数$extにコピーします。

  if ($graph->init->search(dataext) == -1)
  {
     $ext = '';
  }
  else
  {
     $ext = $graph->init->get(dataext);
  }
  
  # CUI関数'selectfile'を起動し、ユーザに数値データファイルを選択させ
  # ます。'selectfile'関数の第1引数は0ですので、単一ファイル選択モード
  # になります。また第2引数には$extが指定され、この引数を正規表現とし
  # ファイルリストのフィルタリングを行います。ユーザが単一のファイルを
  # 選択し、リターンキーを押してselectfile関数を終了すればselectfile関数は
  # 1を返します。またこの場合選択されたファイル名は@_RETに格納されます。
  # キャンセルによりselectfile関数が終了すると0が返され、最終行ににジャンプ
  # しスクリプトは終了します。

  if (selectfile(0, $ext))
  {

      # @_RETに値を返す関数は多く存在するので、@_RET中の必要な値は他の変数
      # に早めに格納した方がよいでしょう。

      $file = $_RET[0];
     # データプロットを行うための、detaオブジェクトの新たなインスタンスを
      # 生成します。関数の返り値-1は新たに生成されたインスタンスのインスタ
      # ンスidです。この値を変数$dnoに格納します。

      $dno = $graph->frame[$_CUR]->new('data') - 1;

      # 新しく作成したインスタンスの初期化を行います。
      # 初期化スクリプト'initdata'の第1引数はframeオブジェクトの配列
      # idであり、第2引数はdataオブジェクトの配列idです。

      if (execfile('initdata', $graph->currentframe, $dno) == 0)
      {
         print ("Error!: cannot initialize data.\n");
      }

      # 新たなdataオブジェクトインスタンスを選択状態にし、ファイル名の設定を
      # 行います。CUI関数'loaddatamenu()'は選択状態にあるdataオブジェクト
      # インスタンスの、ファイル読み込み条件設定を行うためのユーザインター
      # フェイスです。

      $graph->frame[$_CUR]->data[$dno]->selected = 1;
      $graph->frame[$_CUR]->data[$dno]->filename = $file;
      loaddatamenu();

      # ここまでに行われたdataオブジェクトインスタンスの設定内容に従い、
      # 数値データを実際にロードします。

      print 'reading data .....   ';
      $graph->frame[$_CUR]->data[$dno]->loaddata();
      print "done\n";

      # 読み込まれた数値データに合わせ、座標軸のオートスケーリングを
      # 行います。第1引数はスケーリングを行う軸のインスタンスidです。
      # $_ALLと指定すると、全ての軸がオートスケーリングされます。
      # 第2引数はスケーリングマージン(余白)です。ここでは10%としています。

      $graph->frame[$_CUR]->autoscale($_ALL, 10);

      # 数値データファイル名を表示するために、partsオブジェクトインス
      # タンスを新たに生成します。Partsオブジェクトインスタンスを作成
      # する際は、Partsの種類も同時に指定する必要があります。ここでは
      # その種類として、textを与えています。新たに作られたインスタンス
      # の配列番号を変数$pnoに格納します。

      $pno =  $graph->frame[$_CUR]->new('parts', 'text') - 1;

      # インスタンスの初期化を行います。
      if (execfile('initparts', $graph->currentframe, $pno) == 0)
      {
         print ("Error!: cannot initialize parts.\n");
      }

      # ここで数値データファイルをオープンし、ファイルハンドル'F'に対応
      # 付けます。
      open(F, $file);

      # まず1行目を読み込みます。

      $line = <F>;

      # 2行目を読み込みます。

      $line = <F>;

      # ファイルをクローズします。

      close (F);

      # 正規表現を用いてパターンマッチングを行います。マッチングした
      # 結果は$1に格納されます。

      $line =~ 'sample No\.: ([0-9]+)';
      
      $graph->frame[$_CUR]->parts[pno]->text = $1;

      # テキストを表示する位置を計算し、インスタンスに位置情報を代入します。
      $framecenter = ($graph->frame[$_CUR]->x2 - $graph->frame[$_CUR]->x1) / 2;
      @bbox = @graph->frame[$_CUR]->parts[$pno]->bbox();
      $textwidth   = $bbox[2] - $bbox[0];
      $textheight  = $bbox[3] - $bbox[1];
      $graph->frame[$_CUR]->parts[pno]->x1 = $framecenter - $textwidth / 2;
      $graph->frame[$_CUR]->parts[pno]->y1 = -2 * $textheight;

      $graph->paintall(V0);
  }