% Gui: A GUI for accessing the functions of the Velleman K8055
%
% guiobject = VellboardGui()
% Creates a graphical user interface (GUI) for accessing the Velleman
% K8055 board. Inputs are updated in real time and outputs can be changed
% on user input. Uses EasyGUI to build the GUI and the velleman package
% to interface with the board. Requires that EasyGUI is somewhere on the
% search path in addition to vellboard.
% Copyright 2011 The MathWorks, Inc.
classdef VellboardGui < handle
properties (Access = private) %properties
Board % ExperimentBoard
VGui % GUI objects
Devices
DevicesRefresh
DigitalO
AnalogO
DigitalI
AnalogI
Counter
CounterReset
CounterDebounce
RefreshTimer % timer
end
methods
function obj = VellboardGui()
obj.Board = vellboard.ExperimentBoard(); % connect
obj.drawGUI; %create initial gui
% setup input monitor
obj.VGui.monitor([{obj.Devices obj.DevicesRefresh} obj.CounterReset obj.CounterDebounce...
obj.DigitalO obj.AnalogO]);
obj.VGui.ValueChangedFcn = @obj.changeOutputs;
% setup window delete function and window title
set(obj.VGui.UiHandle,'DeleteFcn',@(x,y)obj.deletedWindow);
set(obj.VGui.UiHandle,'Name','Velleman K8055 GUI');
% set initial input values
obj.DevicesRefresh.Value = true;
% setup timer
refreshrate = .001;
obj.RefreshTimer = timer('Period',refreshrate,'ExecutionMode','fixedSpacing',...
'TimerFcn',@(x,y)obj.refreshInputs);
start(obj.RefreshTimer);
end
function delete(obj)
if isvalid(obj.RefreshTimer)
stop(obj.RefreshTimer);
delete(obj.RefreshTimer);
end
if isvalid(obj.VGui)
delete(obj.VGui);
end
if isvalid(obj.Board)
delete(obj.Board);
end
end
end
methods (Access = private)
function drawGUI(obj)
% Sets up the EasyGUI window and adds a lot of widgits
% Is a bit complex but otherwise self-explainatory
obj.VGui = gui.autogui('Location','float','Resizeable',false);
obj.Devices = gui.listbox('Active Devices',{'No Devices Found'});
obj.Devices.Position.height = 100;
obj.DevicesRefresh = gui.pushbutton('Refresh');
spacer1 = gui.space;
spacer1.Position.height = 201;
version = gui.edittext('DLL Version');
version.Value = '4.0.0.0';
version.Enable = 0;
obj.VGui.addPanel;
gui.label('Outputs:');
obj.DigitalO = cell(1,8); %loops automatically create n IO widgits
for i = 1:8;
obj.DigitalO{i} = gui.checkbox(['Digital ' num2str(i)]);
end
spacer2 = gui.space;
spacer2.Position.height = 20;
obj.AnalogO = cell(1,2);
for i = 1:2;
obj.AnalogO{i} = gui.slider(['Analog ' num2str(i)],[0 255]);
obj.AnalogO{i}.Value = 0;
end
obj.VGui.addPanel;
gui.label('Inputs:');
obj.DigitalI = cell(1,5);
for i = 1:5;
obj.DigitalI{i} = gui.checkbox(['Digital ' num2str(i)]);
obj.DigitalI{i}.Enable = 0;
end
spacer2 = gui.space;
spacer2.Position.height = 104;
obj.AnalogI = cell(1,2);
for i = 1:2;
obj.AnalogI{i} = gui.slider(['Analog ' num2str(i)],[0 255]);
obj.AnalogI{i}.Enable = 0;
end
obj.VGui.addPanel;
gui.label('Counters:');
obj.Counter = cell(1,2);
for i = 1:2;
obj.Counter{i} = gui.editnumber(['Counter ' num2str(i)]);
obj.Counter{i}.Enable = 0;
obj.CounterReset{i} = gui.pushbutton(['Reset Counter ' num2str(i)]);
cspacer = gui.space;
cspacer.Position.height = 5;
obj.CounterDebounce{i}= gui.editnumber(['Counter ' num2str(i) ' Debounce']);
if i == 1
spacer3 = gui.space;
spacer3.Position.height = 40;
end
end
end
function changeOutputs(obj,widgit)
label = widgit.Label;
switch label(1) %cheating because there are a limited number of values
case 'R' %Refresh devices or reset counter
if label(3) == 'f' %is it refresh devices?
devicesarray = obj.Board.getActiveDevices;
devicescell = cell(size(devicesarray));
for i = 1:size(devicesarray,2)
devicescell{i} = num2str(devicesarray(i));
end
obj.Devices.MenuItems = devicescell;
else
counter = str2double(label(15)); %extract counter number
obj.Board.resetCounter(counter);
end
case 'D' %Digital Output
output = str2double(label(9)); %Extracts output number from label
obj.Board.writeDigital(output,int8(widgit.Value))
case 'A' %Analog Output or Active Devices
if label(2) == 'c' %is it active devices?
if iscell(widgit.Value) %check for multiple selections and disallow
widgit.Value = widgit.Value{1};
end
obj.Board.setCurrentDevice(str2double(widgit.Value));
else
output = str2double(label(8));
widgit.Value = round(widgit.Value);
obj.Board.writeAnalog(output,widgit.Value);
end
case 'C' %Counter debounce
counter = str2double(label(9));
widgit.Value = round(widgit.Value);
if widgit.Value < 0 % change to in range if necessary
widgit.Value = 0;
elseif widgit.Value > 5000
widgit.Value = 5000;
end
obj.Board.setCounterDebounceTime(counter,widgit.Value);
end
end
function refreshInputs(obj)
% obtains data from K8055 and outputs to input widgets
digi = obj.Board.readDigitalAll();
for i = 1:5
obj.DigitalI{i}.Enable = 1;
obj.DigitalI{i}.Value = logical(digi(i));
obj.DigitalI{i}.Enable = 0;
end
anai = obj.Board.readAnalogAll();
for i = 1:2
obj.AnalogI{i}.Enable = 1;
obj.AnalogI{i}.Value = anai(i);
obj.AnalogI{i}.Enable = 0;
end
count = obj.Board.readCounterAll();
for i = 1:2
obj.Counter{i}.Enable = 1;
obj.Counter{i}.Value = count(i);
obj.Counter{i}.Enable = 0;
end
end
function deletedWindow(obj)
%deletes object if window is closed
if isvalid(obj)
delete(obj);
end
end
end
end