Skip to content

Instantly share code, notes, and snippets.

@ellieLitwack
Created February 7, 2023 03:44
Show Gist options
  • Save ellieLitwack/7fe9a0ccf083d4a6d4e64fb2945d2f7c to your computer and use it in GitHub Desktop.
Save ellieLitwack/7fe9a0ccf083d4a6d4e64fb2945d2f7c to your computer and use it in GitHub Desktop.
A tool for visualize keypress data from ZipChord's debug log files.
import re
import matplotlib.pyplot as plt
from matplotlib.widgets import Slider
# open the chords file and read the lines
print('Scroll through the diagram using the "Pos" slider.')
print('Click on the chart to draw a vertical line (useful for seeing when keypresses overlap.')
file = open(input('Enter the path to the debug.txt file: '), 'r')
lines = file.readlines()
file.close()
# if the line starts with a number with one or more digits followed by a tab, keep it
lines = [line for line in lines if re.match(r'\d+\t', line)]
# ignore lines with the string "*Interrupt*" in them
lines = [line for line in lines if '*Interrupt*' not in line]
# the format of the lines is <number><tab>~<keypress><newline> or
# <number><tab>~<keypress> Up<newline>
# create list of [keypress, [down_time, up_time]]
key_presses = []
# iterate through the lines
for line in lines:
# split the line into the number and the key info
number, keyinfo = line.split('\t')
# split the key info into the keypress and is_up
if len(keyinfo.split(' ')) == 1:
keypress = keyinfo[1:-1] # remove the ~ and the newline
is_up = False
else:
keypress, is_up = keyinfo.split(' ')
keypress = keypress[1:] # remove the ~
is_up = True
if not is_up:
key_presses.append([keypress, [int(number), None]])
else:
for (i, key_press) in enumerate(key_presses):
if key_press[0] == keypress and key_press[1][1] is None:
key_presses[i][1][1] = int(number)
break
# create a chart showing a timeline of keypresses
fig, ax = plt.subplots()
for key_press in key_presses:
ax.plot(key_press[1], [key_press[0], key_press[0]], linewidth=5, solid_capstyle='round')
# large y axis labels
ax.tick_params(axis='y', which='major')
# x and y axis labels
ax.set_xlabel('Time (ms)')
ax.set_ylabel('Keypress')
# set xlim to first second
ax.set_xlim(key_presses[0][1][0]-10, key_presses[0][1][0]+990)
# make an interactive, scrollable chart
# Choose the Slider color
slider_color = 'White'
# Set the axis and slider position in the plot
axis_position = plt.axes([0.2, 0.0, 0.65, 0.03],
facecolor=slider_color)
slider_position = Slider(axis_position,
'Pos', key_presses[0][1][0], key_presses[-1][1][1],)
# update() function to change the graph when the
# slider is in use
def update(val):
pos = slider_position.val
ax.axis([pos, pos + 1000, ax.get_ylim()[0], ax.get_ylim()[1]])
fig.canvas.draw_idle()
# update function called using on_changed() function
slider_position.on_changed(update)
# create a vertical line at the mouse position when the mouse is clicked
def onMouseClick(event):
if event.inaxes == ax:
ax.axvline(x=event.xdata, color='r', linewidth=1)
fig.canvas.draw_idle()
# connect the mouse move event to the function
fig.canvas.mpl_connect('button_press_event', onMouseClick)
plt.show()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment