# -*- coding: utf-8 -*-

"""
このプログラムは、計測器に接続してコマンドの送受信を行います。
コマンドの欄に送信したいコマンドを入力し、[送受信]ボタンを押すと送信されます。
応答があるコマンド（?が含まれるコマンド）の場合は、テキストボックスに応答が表示されます。

動作確認環境(ソフトウェア):
    Python 3.7 Windows

必要なパッケージ:
    PyVISA
"""

import tkinter
import gpib


class SampleWindow(tkinter.Frame):

    TIMEOUT_DEFAULT = 1000                                                              # VISA I/O 操作のタイムアウト(1秒)

    def __init__(self, window):
        """ コンストラクタ """
        super().__init__(window)
        window.title("Sample")
        window.geometry("497x309")
        self.__Label1 = None
        self.__Label2 = None
        self.__Label4 = None
        self.__Label5 = None
        self.__Label6 = None
        self.__TextBox1 = None
        self.__TextBox2 = None
        self.__TextBox3 = None
        self.__TextBox4 = None
        self.__TextBox5 = None
        self.__Scrollbar1 = None
        self.__Scrollbar2 = None
        self.__Button1 = None
        self.__Button2 = None
        self.__Button3 = None
        self.__Button4 = None
        self.__Communication = None
        self.__CreateWidgets()
        self.__TextBox1.insert(tkinter.END, "0")
        self.__TextBox2.insert(tkinter.END, "1")
        self.__TextBox3.insert(tkinter.END, "*IDN?")
        self.__TextBox4.insert(tkinter.END, "1")
        # ボタンとテキストボックスの有効/無効の処理
        self.__Button1.configure(state=tkinter.NORMAL)
        self.__Button2.configure(state=tkinter.DISABLED)
        self.__Button3.configure(state=tkinter.DISABLED)
        self.__TextBox1.configure(state=tkinter.NORMAL)
        self.__TextBox2.configure(state=tkinter.NORMAL)
        self.__TextBox3.configure(state=tkinter.DISABLED)
        self.__TextBox4.configure(state=tkinter.DISABLED)
        self.__TextBox5.configure(state=tkinter.DISABLED)

    def __CreateWidgets(self):
        """ ウィジェットの作成 """
        self.__Label1 = tkinter.Label(text="ボードID")
        self.__Label1.place(anchor=tkinter.NE, x=84, y=18)
        self.__TextBox1 = tkinter.Entry(justify=tkinter.RIGHT)
        self.__TextBox1.place(x=87, y=18, width=51, height=19)
        self.__Label2 = tkinter.Label(text="機器アドレス")
        self.__Label2.place(anchor=tkinter.NE, x=241, y=18)
        self.__TextBox2 = tkinter.Entry(justify=tkinter.RIGHT)
        self.__TextBox2.place(x=244, y=18, width=51, height=19)
        self.__Label4 = tkinter.Label(text="コマンド")
        self.__Label4.place(anchor=tkinter.NE, x=84, y=58)
        self.__TextBox3 = tkinter.Entry()
        self.__TextBox3.place(x=87, y=58, width=229, height=19)
        self.__Label5 = tkinter.Label(text="タイムアウト")
        self.__Label5.place(anchor=tkinter.NE, x=84, y=83)
        self.__TextBox4 = tkinter.Entry(justify=tkinter.RIGHT)
        self.__TextBox4.place(x=87, y=83, width=51, height=19)
        self.__Label6 = tkinter.Label(text="秒")
        self.__Label6.place(x=141, y=83)
        self.__TextBox5 = tkinter.Text(wrap=tkinter.NONE)
        self.__TextBox5.place(x=11, y=119, width=298, height=168)
        self.__Scrollbar1 = tkinter.Scrollbar(orient=tkinter.VERTICAL, command=self.__TextBox5.yview)
        self.__Scrollbar1.place(x=310, y=119, width=16, height=160)
        self.__TextBox5["yscrollcommand"] = self.__Scrollbar1.set
        self.__Scrollbar2 = tkinter.Scrollbar(orient=tkinter.HORIZONTAL, command=self.__TextBox5.xview)
        self.__Scrollbar2.place(x=11, y=280, width=298, height=16)
        self.__TextBox5["xscrollcommand"] = self.__Scrollbar2.set
        self.__Button1 = tkinter.Button(text="接続", command=self.__Button1_Click)
        self.__Button1.place(x=331, y=12, width=73, height=30)
        self.__Button2 = tkinter.Button(text="切断", command=self.__Button2_Click)
        self.__Button2.place(x=410, y=12, width=73, height=30)
        self.__Button3 = tkinter.Button(text="送受信", command=self.__Button3_Click)
        self.__Button3.place(x=331, y=52, width=152, height=50)
        self.__Button4 = tkinter.Button(text="クリア", command=self.__Button4_Click)
        self.__Button4.place(x=331, y=119, width=73, height=30)

    def __Button1_Click(self):
        """ 「接続」ボタンを押したときの処理 """
        boardID = int(self.__TextBox1.get())
        deviceAddress = int(self.__TextBox2.get())
        # Gpibオブジェクトを作成
        self.__Communication = gpib.Gpib(True)
        # 接続
        if not self.__Communication.open(str(boardID), str(deviceAddress), self.TIMEOUT_DEFAULT):
            return
        # ボタンとテキストボックスの有効/無効の処理
        self.__Button1.configure(state=tkinter.DISABLED)
        self.__Button2.configure(state=tkinter.NORMAL)
        self.__Button3.configure(state=tkinter.NORMAL)
        self.__TextBox1.configure(state=tkinter.DISABLED)
        self.__TextBox2.configure(state=tkinter.DISABLED)
        self.__TextBox3.configure(state=tkinter.NORMAL)
        self.__TextBox4.configure(state=tkinter.NORMAL)

    def __Button2_Click(self):
        """ 「切断」ボタンを押したときの処理 """
        # 切断
        self.__Communication.close()
        # ボタンとテキストボックスの有効/無効の処理
        self.__Button1.configure(state=tkinter.NORMAL)
        self.__Button2.configure(state=tkinter.DISABLED)
        self.__Button3.configure(state=tkinter.DISABLED)
        self.__TextBox1.configure(state=tkinter.NORMAL)
        self.__TextBox2.configure(state=tkinter.NORMAL)
        self.__TextBox3.configure(state=tkinter.DISABLED)
        self.__TextBox4.configure(state=tkinter.DISABLED)

    def __Button3_Click(self):
        """ 「送受信」ボタンを押したときの処理 """
        self.__Button3.configure(state=tkinter.DISABLED)
        command = self.__TextBox3.get()
        timeout = int(self.__TextBox4.get())
        self.__TextBox5.configure(state=tkinter.NORMAL)
        self.__TextBox5.insert(tkinter.END, "<< " + command + "\n")                     # ログ出力
        self.__TextBox5.see(tkinter.END)
        self.__TextBox5.configure(state=tkinter.DISABLED)
        if "?" in command:                                                              # コマンドに?が含まれている場合は、
            msgBuf = self.__Communication.SendQueryMsg(command, timeout)                # コマンド送信と応答受信
            self.__TextBox5.configure(state=tkinter.NORMAL)
            self.__TextBox5.insert(tkinter.END, ">> " + msgBuf + "\n")                  # ログ出力
            self.__TextBox5.see(tkinter.END)
            self.__TextBox5.configure(state=tkinter.DISABLED)
        else:
            self.__Communication.sendMsg(command)                                       # コマンド送信
        self.__Button3.configure(state=tkinter.NORMAL)

    def __Button4_Click(self):
        """ 「クリア」ボタンを押したときの処理 """
        # テキストボックスのクリア
        self.__TextBox5.configure(state=tkinter.NORMAL)
        self.__TextBox5.delete(1.0, tkinter.END)
        self.__TextBox5.configure(state=tkinter.DISABLED)


if __name__ == "__main__":
    root = tkinter.Tk()
    window = SampleWindow(root)
    window.mainloop()
