Hi, I'm trying to make my first (successful) GUI here, and I'm getting close. I have all my callbacks working, functions do what they are supposed to, but I'm having a heck of a time getting MATLAB to load the input data correctly. What I'm trying to load is a 5000x4 table with columns Datestr/Number/Number/Number. However, I am having terrible luck.
When I used load, it read my Datestr as a number and only gave me the first digit.
When I use open it gives me a struct, which I can work with, but it's a tedious work around.
When I use uiopen, I don't know how to get the file to work with the rest of my GUI.
If I can make it work, using uiopen is ideal because it lets enduser just choose the file they want. However, if they don't choose the text string in my GUI, I dont' know how to read the file. Included below is my most recent attempts at coding it in, but I keep getting invalid file errors.
% --- Executes on button press in loadbutton.
function loadbutton_Callback(hObject, eventdata, handles)
[pathstr,name,ext] = fileparts(handles.filename);
uiopen(strcat(name,ext));
file=name; |<---- THIS LINE IS GIVING ME PROBLEMS! How do I fix it?|
if iscell(file)
handles.file=cell2table(file);
elseif istable(file)
handles.file=file;%This is good!
else
handles.file=array2table(file);
end
Basically, what I'm running into is rather than saving the variable named 'Name' as something, it's just saving the string as it. so I get file = 'March2011' not file = March2011 Table 5000x4
Also, When I am trying to callback this later, I might be having problems there, but I don't think I am. That bit of code is
function calculatebutton_Callback(hObject, eventdata, handles)
% hObject handle to calculatebutton (see GCBO)
% eventdata reserved - to be defined in a future version of MATLAB
% handles structure with handles and user data (see GUIDATA)
if isempty(handles.file)
error('File to load?')
else
handles.file=file;
end
guidata(hObject,handles);

5 commentaires

For errors, I'm getting
Undefined function or variable 'file'.
Error in Userfriendly>calculatebutton_Callback (line 380)
handles.file=file;
Geoff Hayes
Geoff Hayes le 24 Juil 2014
The above error makes sense given that there is no local variable file to assign to handles.file. What should file be in this case?
As for uiopen it opens and loads data from a file given the handles.filename. But since "filter* is based on the name and the extension of handles.filename (which is different from handles.file??) then there doesn't seem to be any reason to use this function - since the user has no choice.
If you want the user to choose a file, then perhaps try uigetfile instead.
Mike Beacham
Mike Beacham le 24 Juil 2014
Changed file to handle.file and now I have a new problem which is related to data entry I think.
I would like to use uiopen so that it doesn't require a specifically typed out filename to be entered. I just don't know how to access something that has been opened with uiopen because it's entirely up to user choice, and therefore hard to pre-program. How can I use uigetfile and uiopen together to get the variable name of what is opened? I'm assuming idiots are going to be using this GUI, and won't know to click on the same file twice (i.e. uiopen(File A) then uigetfile(File B), and then crash the program.
Geoff Hayes
Geoff Hayes le 25 Juil 2014
Mike - I don't understand how changing file to handle.file makes a difference. What is handle? But then what does the calculate button callback actually do, since there doesn't appear to be any calculations?
Mike Beacham
Mike Beacham le 25 Juil 2014
I didn't see this here, file ---> handles.file actually reads the file from the other callback function I had set. When it was looking for just file, it was searching inside of the calculate button. I have about 100 lines of code after what I copied in, but I didn't think it was necessary to include here. At the end, I run a function [output] = calcuation(handles.file, ... ) and then export the result as a CSV file.

Connectez-vous pour commenter.

 Réponse acceptée

Geoff Hayes
Geoff Hayes le 25 Juil 2014
Modifié(e) : Geoff Hayes le 25 Juil 2014

0 votes

If you want to allow the user to choose the file that you are to open, then you could use uigetfile which will return the selected filename (and not try to automatically load the file like uiopen). You can then "look into" the file to see what is there.
Let's assume that you only allow the user to open files with a mat extension. Then
[filename,pathname,filterindex] = uigetfile('*.mat');
% if the user presses CANCEL then zero is returned so ensure character
% filename
% if the user selects a filter other than the one we set (index==1) then
% ignore the selected file
if ischar(filename) && filterindex==1
% so a *.mat file has been selected
end
The above code allows us to get the user to choose a file that matches our extension (mat). We ignore the case where the user cancels the dialog OR the user selects another filter (All Files, say) by using the appropriate conditions.
Now that we have a file, we can "look into" it with whos. In the body of the above if statement, we do the following
% so a *.mat file has been selected
datInMat = whos('-file',fullfile(pathname,filename));
Now datInMat will be an array of one or more structures for each variable that is in the mat file. For example, if a mat file has a single variable T (table) then
datInMat =
name: 'T'
size: []
bytes: 2010
class: 'table'
global: 0
sparse: 0
complex: 0
nesting: [1x1 struct]
persistent: 0
Given the class attribute, you can then decide what to do with the data - ignore it, or load it
if strcmpi(datInMat(1).class,'table')
varStruct = load(fullfile(pathname,filename),datInMat(1).name);
handles.file = varStruct.(datInMat(1).name);
end
In the above, since the first variable is a table, we load it into the varStruct variable (a structure). But we don't want the structure, just the field that corresponds to the table. So we use the field name (which is the variable name of the table) to access that table from the varStruct and copy it to the handles.file.
It may be useful to put a breakpoint somewhere in the above code and step through and observe what is happening.
The above can now be expanded to handle multiple variables in a mat file, variables of different type/classes (cell, double, etc.), and whether the variables are scalars, arrays, or matrices (using the size field).
Though since this uses load, this may cause a problem given your statement When I used load, it read my Datestr as a number and only gave me the first digit.
Try the above and see what happens!

Plus de réponses (0)

Catégories

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by