Products > Test Equipment

Help with getting print screen from a tektronix 7104 O-Scope over GPIB in python

(1/1)

smallhill:
Here is my code, I need help with my def capture_and_save_screen function for capturing the screenshot and saving it to the controlling pc but I keep getting my "Error", "Invalid or incomplete image data received." comment I can't seem to find where I'm going wrong. I have a connect to scope function that already connect to the scope at GPIB address 5 and IDN's the scope successfully. Just can't get the screen capture. I've looked at all the tek forums but the SCIPI commands differ because their different scopes. This is for a TDS 7104 or a TDS 6604.

import tkinter as tk
from tkinter import messagebox, scrolledtext, filedialog
import pyvisa
import time
import warnings

class OscilloscopeAppEnhanced:
    def __init__(self, master):
        self.master = master
        self.master.title("TDS 7704 Screen Capture Enhanced")
        self.master.geometry("600x300")
       
        # Label for GPIB address input
        self.label_gpib_address = tk.Label(master, text="GPIB Address:")
        self.label_gpib_address.pack()
       
        # Input for GPIB address
        self.entry_gpib_address = tk.Entry(master)
        self.entry_gpib_address.pack()
       
        # Create a button to initiate connection
        self.connect_button = tk.Button(master, text="Connect", command=self.connect_to_scope)
        self.connect_button.pack(pady=10)
       
        # Create a button to initiate screen capture, now directly opens file dialog to save
        self.capture_button = tk.Button(master, text="Capture and Save Screen", command=self.capture_and_save_screen, state=tk.DISABLED)
        self.capture_button.pack(pady=10)
       
        # Status/Command text area
        self.text_status = scrolledtext.ScrolledText(master, height=5)
        self.text_status.pack(pady=10)
       
        # Initialize VISA resource manager
        self.rm = pyvisa.ResourceManager()
        self.scope = None

    def connect_to_scope(self):
        gpib_address_num = self.entry_gpib_address.get().strip()
        try:
            gpib_address = f"GPIB0::{gpib_address_num}::INSTR"
            if not gpib_address_num.isdigit():
                raise ValueError("Please enter a valid GPIB address number.")
            self.scope = self.rm.open_resource(gpib_address)
            self.scope.write("*CLS")  # Clear any errors in the error queue.
            self.scope.timeout = 5000  # Set timeout to 5000 ms (5 seconds) to allow time for response.
            idn_response = self.scope.query("*IDN?").strip()  # Query the instrument identity
            if len(idn_response) == 0:
                raise Exception("No response from instrument. Please check the connection and GPIB address.")
            self.text_status.insert(tk.END, f"Successfully connected to the oscilloscope at {gpib_address}.\n")
            self.text_status.insert(tk.END, f"Instrument IDN: {idn_response}\n")
            self.capture_button["state"] = tk.NORMAL
        except ValueError as ve:
            self.text_status.insert(tk.END, f"Error: {str(ve)}\n")
        except Exception as e:
            self.text_status.insert(tk.END, f"Failed to connect to the oscilloscope: {str(e)}\n")
            self.scope = None

    def capture_and_save_screen(self):
        fileSaveLocation = filedialog.asksaveasfilename(defaultextension=".png", filetypes=[("PNG files", "*.png"), ("All files", "*.*")])
        if not fileSaveLocation:
            messagebox.showerror("Error", "Operation cancelled or no file selected.")
            return

        if self.scope:
            try:
                # Assuming your oscilloscope is already configured to communicate over GPIB
                self.scope.write('EXPort:IMAGe NORMal')  # Set the export image to NORMAL
                self.scope.write('EXPort:FORMat PNG')  # Set the export format to PNG
                self.scope.write('EXPort:VIEW FULLSCREEN')  # Sets the exported view area to Full Screen
                self.scope.write('HARDCopy:LAYout LANDscape')  # Sets the hard copy page orientation to Landscape
                self.scope.write('HARDCOPY:PORT GPIB')  # Set the hardcopy port to GPIB
                self.scope.write('HARDCOPY START')  # Start the hardcopy process
                time.sleep(10)  # Adjust based on your oscilloscope's response time

                # Read the image data from the oscilloscope
                imgBytes = b""
                while True:
                    try:
                        chunk = self.scope.read_raw()
                        if not chunk:
                            break  # Break the loop if no more data is received
                        imgBytes += chunk
                    except pyvisa.errors.VisaIOError as e:
                        if e.error_code == pyvisa.constants.VI_ERROR_TMO:  # Timeout error
                            break  # Assume end of data on timeout
                        else:
                            raise  # Re-raise the exception if it's not a timeout error

                # Check if the received data is valid for a PNG image
                if len(imgBytes) < 100:  # Arbitrary minimum size check for a PNG file
                    messagebox.showerror("Error", "Invalid or incomplete image data received.")
                    return

                with open(fileSaveLocation, "wb") as imgFile:
                    imgFile.write(imgBytes)

                messagebox.showinfo("Success", f"Screen capture saved to {fileSaveLocation}.")
            except Exception as e:
                messagebox.showerror("Error", f"Failed to capture and save screen: {str(e)}")



# Run the application
def run_app_enhanced():
    root = tk.Tk()
    app = OscilloscopeAppEnhanced(root)
    root.mainloop()

run_app_enhanced()

abeyer:
Are you sure you can mix and match export and hardcopy commands like that? My understanding is they're kind of distinct functions, one for waveform capture and the other for full "screenshot."

smallhill:
Good question, you see the export commands weren't in their originally only the HARDCopy commands. When they didn't work I assumed why not take a crack at throwing those in their just to see what happens. Same outcome, still didn't get the screen capture from the TDS 6604 or 7104 O-Scope. Easy to remove if need be. Worked on figuring it out a little more. Still looking into it. 

Navigation

[0] Message Index

There was an error while thanking
Thanking...
Go to full version
Powered by SMFPacks Advanced Attachments Uploader Mod