• トップ
  • ブログ一覧
  • Pythonを使ってオシロスコープを遠隔操作したり、画面キャプチャをしてみよう
  • Pythonを使ってオシロスコープを遠隔操作したり、画面キャプチャをしてみよう

    広告メディア事業部広告メディア事業部
    2021.02.08

    IT技術

    python でオシロスコープを操作しよう!

    オシロスコープなどの計測器は「NI-VISA」という通信規格に対応しています。

    NI-VISA を使えば、PC から簡単にオシロスコープを制御したり、データ転送することができます。

    今回は「PyVISA」モジュールを使い、オシロスコープを操作する Python プログラムを作ってみましょう!

    準備

    PyVISA とは?

    「PyVISA」は、NI-VISA を通して、Python コード上で計測器を制御するモジュールです。

    【PyVISA 公式サイト】
    https://pyvisa.readthedocs.io/en/latest/index.html

    おなじみの pip を使えば、簡単にインストールできます。

    1pip install -U pyvisa

    インストールが必要なもの

    1. Python の開発環境
    2. PyVISA モジュール
    3. NI-VISA

    この中で、NI-VISA のインストールには注意が必要です。

    公式サイトの最新バージョンでは Full 版しかダウンロードできませんが、バージョンを17.5まで落とせば Runtime 版をダウンロードできます。

    最低限 NI-VISA のドライバが使えればいいので、他の機能はインストール不要ということです。

    筆者の実行環境

    1. Python(3.6)
    2. Spyder(3.2.6)
    3. PyVISA(1.9.1)
    4. オシロスコープ(Tektronix 社 MSO58 シリーズ)

    ①PyVISA でオシロスコープのアドレスを取得する

    それではさっそく、Python でコードを書いていきましょう!

    PC とオシロスコープを接続

    まずは、Python を通して PC とオシロスコープを接続する処理を行います。

    1import pyvisa
    2
    3rm = pyvisa.ResourceManager()
    4print(rm.list_resources())

    ResourceManager が、PC と計測器をつなぐクラスです。

    このスクリプトを実行する前に、オシロスコープと PC が USB ケーブルで接続されているか確認してください。

    オシロスコープのアドレスを取得

    実行すると…

    1('USB0::0x___::____::INSTR', 'ASRL1::INSTR', 'ASRL2::INSTR')

    このような表示がされます。

    この 'USB0::~' がオシロスコープのアドレスで、この値を使うことで通信の確立を行います。

    ※接続した USB の端子の箇所によっては、USB1 や USB2 となったりもします。

    ②オシロスコープと接続し、遠隔操作する

    オシロスコープのアドレスが分かったら、次は接続です。

    さっき取得したアドレスを、括弧内に入力することを忘れずに!

    1import pyvisa
    2import time
    3from datetime import datetime
    4
    5inst = rm.open_resource('USB0::0x___::____::INSTR')
    6print(inst.query('*IDN?'))

    実行し、下記のようなコードが表示されれば接続成功です。

    1<'USBInstrument'('USB0::0x___::____::INSTR')>
    2TEKTRONIX,MSO58,_____,______

    接続されているオシロスコープの情報が表示されていますね(__はシリアル番号の略です)。

    この.query は、オシロスコープに NI-VISA コマンドを送信し、戻り値を要求しています。

    NI-VISA のコマンドに「?」が付いているのも、戻り値を要求するコマンドだからです。

    接続に失敗した場合

    1VI_ERROR_RSRC_NFOUND (-1073807343): Insufficient location information or the requested device or resource is not present in the system.

    万が一接続に失敗すると、このような表示がされます。

    こんな時には、下記の方法を試してみてください。

    1. rm.close()で ResourceManager のクローズ処理を実行
    2. USB ケーブルを再接続
    3. オシロスコープを再起動

    オシロスコープを遠隔操作してみよう

    接続に成功したら、下記のコマンドを実行してみましょう。

    1inst.write('ACQuire:STATE STOP')

    オシロスコープの測定が停止したことが分かります。

    次は、下記のコマンドです。

    1inst.write('ACQuire:STATE RUN')

    今度は逆に、オシロスコープの測定が再開します。

    これで、PC 上からオシロスコープの測定開始・停止ができるようになりました。

    PyVISA は命令するだけ

    PyVISA で行っていることは、.write のコマンドで()内の NI-VISA コマンドをオシロスコープに命令するだけです。

    .query と異なり、戻り値を要求せず、命令を実行するだけなので、NI-VISA のコマンドにも「?」は付いていません。

    ③オシロスコープの画面をキャプチャして、PC に送信

    次に、測定停止中のオシロスコープの画面をキャプチャして、PC に送信するコードを書いてみましょう。

    1#オシロスコープの内蔵HDにテンポラリのキャプチャ画像を保存
    2inst.write('SAVE:IMAGe \"C:/Temp.png\"')
    3
    4#画像のキャプチャ処理が終了するまで待つ
    5while inst.query('*OPC?')[0]!="1":
    6    print("Waiting")
    7    time.sleep(1)
    8
    9#保存された画像ファイルをPC側へ読み出す
    10inst.write('FILESystem:READFile \"C:/Temp.png\"')
    11img_data = inst.read_raw()
    12
    13#PC側に保存する際にdatetimeモジュールを使い、日付+時間のファイル名で保存する
    14dt=datetime.now()
    15filename = dt.strftime("IMG_%Y%m%d_%H%M%S,png")
    16file = open(filename,"wb")
    17file.write(img_data)
    18file.close()
    19
    20#測定終了後にオシロスコープとの通信を切断する
    21inst.close()
    22rm.close()

    上記コードの原理を説明すると、こんな感じです。

    1. 画面キャプチャをしたら、オシロスコープの内蔵ハードディスクに「Temp.png」として保存するよう命令
    2. コマンドOPC?.queryで送信し続け、1が返ってくるまで Wait
    3. オシロスコープの内蔵ハードディスクから、PC へ画像ファイルを転送

    処理が全て終わったら、オシロスコープとの接続をクローズすることを忘れずに!

    応用例:タイマー制御の自動キャプチャ

    最後に、ひとつ応用例をご紹介します!

    「Python のタイマー制御により、自動でオシロスコープの RUN/STOP と画面キャプチャを行う」というものです。

    オシロスコープに一切触れることなく、数秒単位で波形画面を次々に取得できますよ。

    1import pyvisa
    2import time
    3from datetime import datetime
    4
    5
    6VISAAddr = "USB0::___::____::INSTR" #rm.list_resources()にて得られる接続先のアドレス
    7GET_INT_SEC = 3     #画像をキャプチャするまでの待ち時間[sec]
    8GET_COUNT = 3       #タイマーによる画像キャプチャを繰り返す回数
    9
    10#リソースマネージャを実体化し、オシロスコープと接続を行う
    11rm = pyvisa.ResourceManager()
    12inst = rm.open_resource(VISAAddr)
    13
    14#接続先のオシロスコープの情報を表示(表示できない場合はエラーで終了)
    15print(inst.query('*IDN?'))
    16
    17#タイマーカウントによる画像キャプチャ処理の開始
    18for i in range(GET_COUNT):
    19    
    20    #timeモジュールを使い、待ち時間が0になるまでカウントを繰り返す
    21    cnt_sec = GET_INT_SEC
    22    while cnt_sec!=0:
    23        print("Timer Count:" + str(cnt_sec))
    24        time.sleep(1)
    25        cnt_sec = cnt_sec-1
    26        
    27    print("Image Capture Start")
    28    
    29    #オシロスコープの画面を停止させる
    30    inst.write('ACQuire:STATE STOP')
    31    time.sleep(1)
    32    
    33    #オシロスコープの内蔵HDにテンポラリのキャプチャ画像を保存
    34    inst.write('SAVE:IMAGe \"C:/Temp.png\"')
    35    
    36    #画像のキャプチャ処理が終了するまで待つ
    37    while inst.query('*OPC?')[0]!="1":
    38        print("Waiting")
    39        time.sleep(1)
    40        
    41    #保存された画像ファイルをPC側へ読み出す
    42    inst.write('FILESystem:READFile \"C:/Temp.png\"')
    43    img_data = inst.read_raw()
    44    
    45    #PC側に保存する際にdatetimeモジュールを使い、日付+時間のファイル名で保存する
    46    dt=datetime.now()
    47    filename = dt.strftime("IMG_%Y%m%d_%H%M%S,png")
    48    file = open(filename,"wb")
    49    file.write(img_data)
    50    file.close()
    51    
    52    #オシロスコープ側のテンポラリ画像ファイルを削除
    53    inst.write('FILESystem:DELEte \"C:/Temp.png\"')
    54    
    55    #オシロスコープの画面の停止を解除する
    56    inst.write('ACQuire:STATE RUN')
    57
    58#測定終了後にオシロスコープとの通信を切断する
    59inst.close()
    60rm.close()

    繰り返しの回数や時間間隔は、使いやすいようにカスタマイズしてください。

    さいごに

    Python の良いところは、デバッガなしでも、コードの途中で処理が実行できるところだと思います。

    特に NI-VISA コマンドは使ってみないとわからないものも多いので、Python との相性は良さそうですね。

    次回は「オシロスコープの波形データを自動転送」する方法をご紹介します。

    お楽しみに!

    次回の記事はこちら!

    Pythonでオシロスコープの波形データを自動転送してみた!2021.02.16Pythonでオシロスコープの波形データを自動転送してみた!Python + PyVISA でオシロスコープの波形データを自動転送してみよう!前回は、PyVISA でオシロスコー...

    こちらの記事もオススメ!

    featureImg2020.07.17ライトコード的「やってみた!」シリーズ「やってみた!」を集めました!(株)ライトコードが今まで作ってきた「やってみた!」記事を集めてみました!※作成日が新し...
    featureImg2020.07.30Python 特集実装編※最新記事順Responder + Firestore でモダンかつサーバーレスなブログシステムを作ってみた!P...

    広告メディア事業部

    広告メディア事業部

    おすすめ記事

    GitHubActionsのランナーに触れてみた

    こやまん(エンジニア)

    こやまん(エンジニア)

    2024.03.28

    IT技術

    Azure Data FactoryでSlackへ通知をしてみる

    たかやん(エンジニア)

    たかやん(エンジニア)

    2024.03.28

    IT技術

    GCP Secret Managerを使ってみた

    たなゆー(エンジニア)

    たなゆー(エンジニア)

    2024.03.21

    IT技術

    Bitriseのパイプラインと環境変数

    加納(エンジニア)

    加納(エンジニア)

    2024.03.11

    IT技術