12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387 |
- function varargout = spm_input(varargin)
- % Comprehensive graphical and command line input function
- % FORMATs (given in Programmers Help)
- %_______________________________________________________________________
- %
- % spm_input handles most forms of interactive user input for SPM.
- % (File selection is handled by spm_select.m)
- %
- % There are five types of input: String, Evaluated, Conditions, Buttons
- % and Menus: These prompt for string input; string input which is
- % evaluated to give a numerical result; selection of one item from a
- % set of buttons; selection of an item from a menu.
- %
- % - STRING, EVALUATED & CONDITION input -
- % For STRING, EVALUATED and CONDITION input types, a prompt is
- % displayed adjacent to an editable text entry widget (with a lilac
- % background!). Clicking in the entry widget allows editing, pressing
- % <RETURN> or <ENTER> enters the result. You must enter something,
- % empty answers are not accepted. A default response may be pre-specified
- % in the entry widget, which will then be outlined. Clicking the border
- % accepts the default value.
- %
- % Basic editing of the entry widget is supported *without* clicking in
- % the widget, provided no other graphics widget has the focus. (If a
- % widget has the focus, it is shown highlighted with a thin coloured
- % line. Clicking on the window background returns the focus to the
- % window, enabling keyboard accelerators.). This enables you to type
- % responses to a sequence of questions without having to repeatedly
- % click the mouse in the text widgets. Supported are BackSpace and
- % Delete, line kill (^U). Other standard ASCII characters are appended
- % to the text in the entry widget. Press <RETURN> or <ENTER> to submit
- % your response.
- %
- % A ContextMenu is provided (in the figure background) giving access to
- % relevant utilities including the facility to load input from a file
- % (see spm_load.m and examples given below): Click the right button on
- % the figure background.
- %
- % For EVALUATED input, the string submitted is evaluated in the base
- % MatLab workspace (see MatLab's `eval` command) to give a numerical
- % value. This permits the entry of numerics, matrices, expressions,
- % functions or workspace variables. I.e.:
- % i) - a number, vector or matrix e.g. "[1 2 3 4]"
- % "[1:4]"
- % "1:4"
- % ii) - an expression e.g. "pi^2"
- % "exp(-[1:36]/5.321)"
- % iii) - a function (that will be invoked) e.g. "spm_load('tmp.dat')"
- % (function must be on MATLABPATH) "input_cov(36,5.321)"
- % iv) - a variable from the base workspace
- % e.g. "tmp"
- %
- % The last three options provide a great deal of power: spm_load will
- % load a matrix from an ASCII data file and return the results. When
- % called without an argument, spm_load will pop up a file selection
- % dialog. Alternatively, this facility can be gained from the
- % ContextMenu. The second example assummes a custom funcion called
- % input_cov has been written which expects two arguments, for example
- % the following file saved as input_cov.m somewhere on the MATLABPATH
- % (~/matlab, the matlab subdirectory of your home area, and the current
- % directory, are on the MATLABPATH by default):
- %
- % function [x] = input_cov(n,decay)
- % % data input routine - mono-exponential covariate
- % % FORMAT [x] = input_cov(n,decay)
- % % n - number of time points
- % % decay - decay constant
- % x = exp(-[1:n]/decay);
- %
- % Although this example is trivial, specifying large vectors of
- % empirical data (e.g. reaction times for 72 scans) is efficient and
- % reliable using this device. In the last option, a variable called tmp
- % is picked up from the base workspace. To use this method, set the
- % variables in the MatLab base workspace before starting an SPM
- % procedure (but after starting the SPM interface). E.g.
- % >> tmp=exp(-[1:36]/5.321)
- %
- % Occasionally a vector of a specific length will be required: This
- % will be indicated in the prompt, which will start with "[#]", where
- % # is the length of vector(s) required. (If a matrix is entered then
- % at least one dimension should equal #.)
- %
- % Occasionally a specific type of number will be required. This should
- % be obvious from the context. If you enter a number of the wrong type,
- % you'll be alerted and asked to re-specify. The types are i) Real
- % numbers; ii) Integers; iii) Whole numbers [0,1,2,3,...] & iv) Natural
- % numbers [1,2,3,...]
- %
- % CONDITIONS type input is for getting indicator vectors. The features
- % of evaluated input described above are complimented as follows:
- % v) - a compressed list of digits 0-9 e.g. "12121212"
- % ii) - a list of indicator characters e.g. "abababab"
- % a-z mapped to 1-26 in alphabetical order, *except* r ("rest")
- % which is mapped to zero (case insensitive, [A:Z,a:z] only)
- % ...in addition the response is checked to ensure integer condition indices.
- % Occasionally a specific number of conditions will be required: This
- % will be indicated in the prompt, which will end with (#), where # is
- % the number of conditions required.
- %
- % CONTRAST type input is for getting contrast weight vectors. Enter
- % contrasts as row-vectors. Contrast weight vectors will be padded with
- % zeros to the correct length, and checked for validity. (Valid
- % contrasts are estimable, which are those whose weights vector is in
- % the row-space of the design matrix.)
- %
- % Errors in string evaluation for EVALUATED & CONDITION types are
- % handled gracefully, the user notified, and prompted to re-enter.
- %
- % - BUTTON input -
- % For Button input, the prompt is displayed adjacent to a small row of
- % buttons. Press the approprate button. The default button (if
- % available) has a dark outline. Keyboard accelerators are available
- % (provided no graphics widget has the focus): <RETURN> or <ENTER>
- % selects the default button (if available). Typing the first character
- % of the button label (case insensitive) "presses" that button. (If
- % these Keys are not unique, then the integer keys 1,2,... "press" the
- % appropriate button.)
- %
- % The CommandLine variant presents a simple menu of buttons and prompts
- % for a selection. Any default response is indicated, and accepted if
- % an empty line is input.
- %
- %
- % - MENU input -
- % For Menu input, the prompt is displayed in a pull down menu widget.
- % Using the mouse, a selection is made by pulling down the widget and
- % releasing the mouse on the appropriate response. The default response
- % (if set) is marked with an asterisk. Keyboard accelerators are
- % available (provided no graphic widget has the focus) as follows: 'f',
- % 'n' or 'd' move forward to next response down; 'b', 'p' or 'u' move
- % backwards to the previous response up the list; the number keys jump
- % to the appropriate response number; <RETURN> or <ENTER> slelects the
- % currently displayed response. If a default is available, then
- % pressing <RETURN> or <ENTER> when the prompt is displayed jumps to
- % the default response.
- %
- % The CommandLine variant presents a simple menu and prompts for a selection.
- % Any default response is indicated, and accepted if an empty line is
- % input.
- %
- %
- % - Combination BUTTON/EDIT input -
- % In this usage, you will be presented with a set of buttons and an
- % editable text widget. Click one of the buttons to choose that option,
- % or type your response in the edit widget. Any default response will
- % be shown in the edit widget. The edit widget behaves in the same way
- % as with the STRING/EVALUATED input, and expects a single number.
- % Keypresses edit the text widget (rather than "press" the buttons)
- % (provided no other graphics widget has the focus). A default response
- % can be selected with the mouse by clicking the thick border of the
- % edit widget.
- %
- %
- % - Command line -
- % If YPos is 0 or global CMDLINE is true, then the command line is used.
- % Negative YPos overrides CMDLINE, ensuring the GUI is used, at
- % YPos=abs(YPos). Similarly relative YPos beginning with '!'
- % (E.g.YPos='!+1') ensures the GUI is used.
- %
- % spm_input uses the SPM 'Interactive' window, which is 'Tag'ged
- % 'Interactive'. If there is no such window, then the current figure is
- % used, or an 'Interactive' window created if no windows are open.
- %
- %-----------------------------------------------------------------------
- % Programers help is contained in the main body of spm_input.m
- %-----------------------------------------------------------------------
- % See : input.m (MatLab Reference Guide)
- % See also : spm_select.m (SPM file selector dialog)
- % : spm_input.m (Input wrapper function - handles batch mode)
- %_______________________________________________________________________
- % Copyright (C) 2008 Wellcome Trust Centre for Neuroimaging
- % Andrew Holmes
- % $Id: spm_input.m 6510 2015-07-31 14:49:33Z guillaume $
- %=======================================================================
- % - FORMAT specifications for programers
- %=======================================================================
- % generic - [p,YPos] = spm_input(Prompt,YPos,Type,...)
- % string - [p,YPos] = spm_input(Prompt,YPos,'s',DefStr)
- % string+ - [p,YPos] = spm_input(Prompt,YPos,'s+',DefStr)
- % evaluated - [p,YPos] = spm_input(Prompt,YPos,'e',DefStr,n)
- % - natural - [p,YPos] = spm_input(Prompt,YPos,'n',DefStr,n,mx)
- % - whole - [p,YPos] = spm_input(Prompt,YPos,'w',DefStr,n,mx)
- % - integer - [p,YPos] = spm_input(Prompt,YPos,'i',DefStr,n)
- % - real - [p,YPos] = spm_input(Prompt,YPos,'r',DefStr,n,mm)
- % condition - [p,YPos] = spm_input(Prompt,YPos,'c',DefStr,n,m)
- % contrast - [p,YPos] = spm_input(Prompt,YPos,'x',DefStr,n,X)
- % permutation- [p,YPos] = spm_input(Prompt,YPos,'p',DefStr,P,n)
- % button - [p,YPos] = spm_input(Prompt,YPos,'b',Labels,Values,DefItem)
- % button/edit combo's (edit for string or typed scalar evaluated input)
- % [p,YPos] = spm_input(Prompt,YPos,'b?1',Labels,Values,DefStr,mx)
- % ...where ? in b?1 specifies edit widget type as with string & eval'd input
- % - [p,YPos] = spm_input(Prompt,YPos,'n1',DefStr,mx)
- % - [p,YPos] = spm_input(Prompt,YPos,'w1',DefStr,mx)
- % button dialog
- % - [p,YPos] = spm_input(Prompt,YPos,'bd',...
- % Labels,Values,DefItem,Title)
- % menu - [p,YPos] = spm_input(Prompt,YPos,'m',Labels,Values,DefItem)
- % display - spm_input(Message,YPos,'d',Label)
- % display - (GUI only) spm_input(Alert,YPos,'d!',Label)
- %
- % yes/no - [p,YPos] = spm_input(Prompt,YPos,'y/n',Values,DefItem)
- % buttons (shortcut) where Labels is a bar delimited string
- % - [p,YPos] = spm_input(Prompt,YPos,Labels,Values,DefItem)
- %
- % NB: Natural numbers are [1:Inf), Whole numbers are [0:Inf)
- %
- % -- Parameters (input) --
- %
- % Prompt - prompt string
- % - Defaults (missing or empty) to 'Enter an expression'
- %
- % YPos - (numeric) vertical position {1 - 12}
- % - overriden by global CMDLINE
- % - 0 for command line
- % - negative to force GUI
- % - (string) relative vertical position E.g. '+1'
- % - relative to last position used
- % - overriden by global CMDLINE
- % - YPos(1)=='!' forces GUI E.g. '!+1'
- % - '_' is a shortcut for the lowest GUI position
- % - Defaults (missing or empty) to '+1'
- %
- % Type - type of interrogation
- % - 's'tring
- % - 's+' multi-line string
- % - p returned as cellstr (nx1 cell array of strings)
- % - DefStr can be a cellstr or string matrix
- % - 'e'valuated string
- % - 'n'atural numbers
- % - 'w'hole numbers
- % - 'i'ntegers
- % - 'r'eals
- % - 'c'ondition indicator vector
- % - 'x' - contrast entry
- % - If n(2) or design matrix X is specified, then
- % contrast matrices are padded with zeros to have
- % correct length.
- % - if design matrix X is specified, then contrasts are
- % checked for validity (i.e. in the row-space of X)
- % (checking handled by spm_SpUtil)
- % - 'b'uttons
- % - 'bd' - button dialog: Uses MatLab's questdlg
- % - For up to three buttons
- % - Prompt can be a cellstr with a long multiline message
- % - CmdLine support as with 'b' type
- % - button/edit combo's: 'be1','bn1','bw1','bi1','br1'
- % - second letter of b?1 specifies type for edit widget
- % - 'n1' - single natural number (buttons 1,2,... & edit)
- % - 'w1' - single whole number (buttons 0,1,... & edit)
- % - 'm'enu pulldown
- % - 'y/n' : Yes or No buttons
- % (See shortcuts below)
- % - bar delimited string : buttons with these labels
- % (See shortcuts below)
- % - Defaults (missing or empty) to 'e'
- %
- % DefStr - Default string to be placed in entry widget for string and
- % evaluated types
- % - Defaults to ''
- %
- % n ('e', 'c' & 'p' types)
- % - Size of matrix requred
- % - NaN for 'e' type implies no checking - returns input as evaluated
- % - length of n(:) specifies dimension - elements specify size
- % - Inf implies no restriction
- % - Scalar n expanded to [n,1] (i.e. a column vector)
- % (except 'x' contrast type when it's [n,np] for np
- % - E.g: [n,1] & [1,n] (scalar n) prompt for an n-vector,
- % returned as column or row vector respectively
- % [1,Inf] & [Inf,1] prompt for a single vector,
- % returned as column or row vector respectively
- % [n,Inf] & [Inf,n] prompts for any number of n-vectors,
- % returned with row/column dimension n respectively.
- % [a,b] prompts for an 2D matrix with row dimension a and
- % column dimension b
- % [a,Inf,b] prompt for a 3D matrix with row dimension a,
- % page dimension b, and any column dimension.
- % - 'c' type can only deal with single vectors
- % - NaN for 'c' type treated as Inf
- % - Defaults (missing or empty) to NaN
- %
- % n ('x'type)
- % - Number of contrasts required by 'x' type (n(1))
- % ( n(2) can be used specify length of contrast vectors if )
- % ( a design matrix isn't passed )
- % - Defaults (missing or empty) to 1 - vector contrast
- %
- % mx ('n', 'w', 'n1', 'w1', 'bn1' & 'bw1' types)
- % - Maximum value (inclusive)
- %
- % mm ('r' type)
- % - Maximum and minimum values (inclusive)
- %
- % m - Number of unique conditions required by 'c' type
- % - Inf implies no restriction
- % - Defaults (missing or empty) to Inf - no restriction
- %
- % P - set (vector) of numbers of which a permutation is required
- %
- % X - Design matrix for contrast checking in 'x' type
- % - Can be either a straight matrix or a space structure (see spm_sp)
- % - Column dimension of design matrix specifies length of contrast
- % vectors (overriding n(2) is specified).
- %
- % Title - Title for questdlg in 'bd' type
- %
- % Labels - Labels for button and menu types.
- % - string matrix, one label per row
- % - bar delimited string
- % E.g. 'AnCova|Scaling|None'
- %
- % Values - Return values corresponding to Labels for button and menu types
- % - j-th row is returned if button / menu item j is selected
- % (row vectors are transposed)
- % - Defaults (missing or empty) to - (button) Labels
- % - ( menu ) menu item numbers
- %
- % DefItem - Default item number, for button and menu types.
- %
- % -- Parameters (output) --
- % p - results
- % YPos - Optional second output argument returns GUI position just used
- %
- %-----------------------------------------------------------------------
- % WINDOWS:
- %
- % spm_input uses the SPM 'Interactive' 'Tag'ged window. If this isn't
- % available and no figures are open, an 'Interactive' SPM window is
- % created (`spm('CreateIntWin')`). If figures are available, then the
- % current figure is used *unless* it is 'Tag'ged.
- %
- %-----------------------------------------------------------------------
- % SHORTCUTS:
- %
- % Buttons SHORTCUT - If the Type parameter is a bar delimited string, then
- % the Type is taken as 'b' with the specified labels, and the next parameter
- % (if specified) is taken for the Values.
- %
- % Yes/No question shortcut - p = spm_input(Prompt,YPos,'y/n') expands
- % to p = spm_input(Prompt,YPos,'b','yes|no',...), enabling easy use of
- % spm_input for yes/no dialogue. Values defaults to 'yn', so 'y' or 'n'
- % is returned as appropriate.
- %
- %-----------------------------------------------------------------------
- % EXAMPLES:
- % ( Specified YPos is overriden if global CMDLINE is )
- % ( true, when the command line versions are used. )
- %
- % p = spm_input
- % Command line input of an evaluated string, default prompt.
- % p = spm_input('Enter a value',1)
- % Evaluated string input, prompted by 'Enter a value', in
- % position 1 of the dialog figure.
- % p = spm_input(str,'+1','e',0.001)
- % Evaluated string input, prompted by contents of string str,
- % in next position of the dialog figure.
- % Default value of 0.001 offered.
- % p = spm_input(str,2,'e',[],5)
- % Evaluated string input, prompted by contents of string str,
- % in second position of the dialog figure.
- % Vector of length 5 required - returned as column vector
- % p = spm_input(str,2,'e',[],[Inf,5])
- % ...as above, but can enter multiple 5-vectors in a matrix,
- % returned with 5-vectors in rows
- % p = spm_input(str,0,'c','ababab')
- % Condition string input, prompted by contents of string str
- % Uses command line interface.
- % Default string of 'ababab' offered.
- % p = spm_input(str,0,'c','010101')
- % As above, but default string of '010101' offered.
- % [p,YPos] = spm_input(str,'0','s','Image')
- % String input, same position as last used, prompted by str,
- % default of 'Image' offered. YPos returns GUI position used.
- % p = spm_input(str,'-1','y/n')
- % Yes/No buttons for question with prompt str, in position one
- % before the last used Returns 'y' or 'n'.
- % p = spm_input(str,'-1','y/n',[1,0],2)
- % As above, but returns 1 for yes response, 0 for no,
- % with 'no' as the default response
- % p = spm_input(str,4,'AnCova|Scaling')
- % Presents two buttons labelled 'AnCova' & 'Scaling', with
- % prompt str, in position 4 of the dialog figure. Returns the
- % string on the depresed button, where buttons can be pressed
- % with the mouse or by the respective keyboard accelerators
- % 'a' & 's' (or 'A' & 'S').
- % p = spm_input(str,-4,'b','AnCova|Scaling',[],2)
- % As above, but makes "Scaling" the default response, and
- % overrides global CMDLINE
- % p = spm_input(str,0,'b','AnCova|Scaling|None',[1,2,3])
- % Prompts for [A]ncova / [S]caling / [N]one in MatLab command
- % window, returns 1, 2, or 3 according to the first character
- % of the entered string as one of 'a', 's', or 'n' (case
- % insensitive).
- % p = spm_input(str,1,'b','AnCova',1)
- % Since there's only one button, this just displays the response
- % in GUI position 1 (or on the command line if global CMDLINE
- % is true), and returns 1.
- % p = spm_input(str,'+0','br1','None|Mask',[-Inf,NaN],0.8)
- % Presents two buttons labelled "None" & "Mask" (which return
- % -Inf & NaN if clicked), together with an editable text widget
- % for entry of a single real number. The default of 0.8 is
- % initially presented in the edit window, and can be selected by
- % pressing return.
- % Uses the previous GUI position, unless global CMDLINE is true,
- % in which case a command-line equivalent is used.
- % p = spm_input(str,'+0','w1')
- % Prompts for a single whole number using a combination of
- % buttons and edit widget, using the previous GUI position,
- % or the command line if global CMDLINE is true.
- % p = spm_input(str,'!0','m','Single Subject|Multi Subject|Multi Study')
- % Prints the prompt str in a pull down menu containing items
- % 'Single Subject', 'Multi Subject' & 'Multi Study'. When OK is
- % clicked p is returned as the index of the choice, 1,2, or 3
- % respectively. Uses last used position in GUI, irrespective of
- % global CMDLINE
- % p = spm_input(str,5,'m',...
- % 'Single Subject|Multi Subject|Multi Study',...
- % ['SS';'MS';'SP'],2)
- % As above, but returns strings 'SS', 'MS', or 'SP' according to
- % the respective choice, with 'MS; as the default response.
- % p = spm_input(str,0,'m',...
- % 'Single Subject|Multi Subject|Multi Study',...
- % ['SS';'MS';'SP'],2)
- % As above, but the menu is presented in the command window
- % as a numbered list.
- % spm_input('AnCova, GrandMean scaling',0,'d')
- % Displays message in a box in the MatLab command window
- % [null,YPos]=spm_input('Session 1','+1','d!','fMRI')
- % Displays 'fMRI: Session 1' in next GUI position of the
- % 'Interactive' window. If CMDLINE is 1, then nothing is done.
- % Position used is returned in YPos.
- %
- %-----------------------------------------------------------------------
- % FORMAT h = spm_input(Prompt,YPos,'m!',Labels,cb,UD,XCB);
- % GUI PullDown menu utility - creates a pulldown menu in the Interactive window
- % FORMAT H = spm_input(Prompt,YPos,'b!',Labels,cb,UD,XCB);
- % GUI Buttons utility - creates GUI buttons in the Interactive window
- %
- % Prompt, YPos, Labels - as with 'm'enu/'b'utton types
- % cb - CallBack string
- % UD - UserData
- % XCB - Extended CallBack handling - allows different CallBack for each item,
- % and use of UD in CallBack strings. [Defaults to 1 for PullDown type
- % when multiple CallBacks specified, 0 o/w.]
- % H - Handle of 'PullDown' uicontrol / 'Button's
- %
- % In "normal" mode (when XCB is false), this is essentially a utility
- % to create a PullDown menu widget or set of buttons in the SPM
- % 'Interactive' figure, using positioning and Label definition
- % conveniences of the spm_input 'm'enu & 'b'utton types. If Prompt is
- % not empty, then the PullDown/Buttons appears on the right, with the
- % Prompt on the left, otherwise the PullDown/Buttons use the whole
- % width of the Interactive figure. The PopUp's CallBack string is
- % specified in cb, and [optional] UserData may be passed as UD.
- %
- % For buttons, a separate callback can be specified for each button, by
- % passing the callbacks corresponding to the Labels as rows of a
- % cellstr or string matrix.
- %
- % This "different CallBacks" facility can also be extended to the
- % PullDown type, using the "extended callback" mode (when XCB is
- % true). % In addition, in "extended callback", you can use UD to
- % refer to the UserData argument in the CallBack strings. (What happens
- % is this: The cb & UD are stored as fields in the PopUp's UserData
- % structure, and the PopUp's callback is set to spm_input('!m_cb'),
- % which reads UD into the functions workspace and eval's the
- % appropriate CallBack string. Note that this means that base
- % workspace variables are inaccessible (put what you need in UD), and
- % that any return arguments from CallBack functions are not passed back
- % to the base workspace).
- %
- %
- %-----------------------------------------------------------------------
- % UTILITY FUNCTIONS:
- %
- % FORMAT colour = spm_input('!Colour')
- % Returns colour for input widgets, as specified in COLOUR parameter at
- % start of code.
- % colour - [r,g,b] colour triple
- %
- % FORMAT [iCond,msg] = spm_input('!iCond',str,n,m)
- % Parser for special 'c'ondition type: Handles digit strings and
- % strings of indicator chars.
- % str - input string
- % n - length of condition vector required [defaut Inf - no restriction]
- % m - number of conditions required [default Inf - no restrictions]
- % iCond - Integer condition indicator vector
- % msg - status message
- %
- % FORMAT hM = spm_input('!InptConMen',Finter,H)
- % Sets a basic Input ContextMenu for the figure
- % Finter - figure to set menu in
- % H - handles of objects to delete on "crash out" option
- % hM - handle of UIContextMenu
- %
- % FORMAT [CmdLine,YPos] = spm_input('!CmdLine',YPos)
- % Sorts out whether to use CmdLine or not & canonicalises YPos
- % CmdLine - Binary flag
- % YPos - Position index
- %
- % FORMAT Finter = spm_input('!GetWin',F)
- % Locates (or creates) figure to work in
- % F - Interactive Figure, defaults to 'Interactive'
- % Finter - Handle of figure to use
- %
- % FORMAT [PLoc,cF] = spm_input('!PointerJump',RRec,F,XDisp)
- % Raise window & jump pointer over question
- % RRec - Response rectangle of current question
- % F - Interactive Figure, Defaults to 'Interactive'
- % XDisp - X-displacement of cursor relative to RRec
- % PLoc - Pointer location before jumping
- % cF - Current figure before making F current.
- %
- % FORMAT [PLoc,cF] = spm_input('!PointerJumpBack',PLoc,cF)
- % Replace pointer and reset CurrentFigure back
- % PLoc - Pointer location before jumping
- % cF - Previous current figure
- %
- % FORMAT spm_input('!PrntPrmpt',Prompt,TipStr,Title)
- % Print prompt for CmdLine questioning
- % Prompt - prompt string, callstr, or string matrix
- % TipStr - tip string
- % Title - title string
- %
- % FORMAT [Frec,QRec,PRec,RRec] = spm_input('!InputRects',YPos,rec,F)
- % Returns rectangles (pixels) used in GUI
- % YPos - Position index
- % rec - Rectangle specifier: String, one of 'Frec','QRec','PRec','RRec'
- % Defaults to '', which returns them all.
- % F - Interactive Figure, Defaults to spm_figure('FindWin','Interactive')
- % FRec - Position of interactive window
- % QRec - Position of entire question
- % PRec - Position of prompt
- % RRec - Position of response
- %
- % FORMAT spm_input('!DeleteInputObj',F)
- % Deltes input objects (only) from figure F
- % F - Interactive Figure, Defaults to spm_figure('FindWin','Interactive')
- %
- % FORMAT [CPos,hCPos] = spm_input('!CurrentPos',F)
- % Returns currently used GUI question positions & their handles
- % F - Interactive Figure, Defaults to spm_figure('FindWin','Interactive')
- % CPos - Vector of position indices
- % hCPos - (n x CPos) matrix of object handles
- %
- % FORMAT h = spm_input('!FindInputObj',F)
- % Returns handles of input GUI objects in figure F
- % F - Interactive Figure, Defaults to spm_figure('FindWin','Interactive')
- % h - vector of object handles
- %
- % FORMAT [NPos,CPos,hCPos] = spm_input('!NextPos',YPos,F,CmdLine)
- % Returns next position index, specified by YPos
- % YPos - Absolute (integer) or relative (string) position index
- % Defaults to '+1'
- % F - Interactive Figure, defaults to spm_figure('FindWin','Interactive')
- % CmdLine - Command line? Defaults to spm_input('!CmdLine',YPos)
- % NPos - Next position index
- % CPos & hCPos - as for !CurrentPos
- %
- % FORMAT NPos = spm_input('!SetNextPos',YPos,F,CmdLine)
- % Sets up for input at next position index, specified by YPos. This utility
- % function can be used stand-alone to implicitly set the next position
- % by clearing positions NPos and greater.
- % YPos - Absolute (integer) or relative (string) position index
- % Defaults to '+1'
- % F - Interactive Figure, defaults to spm_figure('FindWin','Interactive')
- % CmdLine - Command line? Defaults to spm_input('!CmdLine',YPos)
- % NPos - Next position index
- %
- % FORMAT MPos = spm_input('!MaxPos',F,FRec3)
- % Returns maximum position index for figure F
- % F - Interactive Figure, Defaults to spm_figure('FindWin','Interactive')
- % Not required if FRec3 is specified
- % FRec3 - Length of interactive figure in pixels
- %
- % FORMAT spm_input('!EditableKeyPressFcn',h,ch)
- % KeyPress callback for GUI string / eval input
- %
- % FORMAT spm_input('!ButtonKeyPressFcn',h,Keys,DefItem,ch)
- % KeyPress callback for GUI buttons
- %
- % FORMAT spm_input('!PullDownKeyPressFcn',h,ch,DefItem)
- % KeyPress callback for GUI pulldown menus
- %
- % FORMAT spm_input('!m_cb')
- % Extended CallBack handler for 'p' PullDown utility type
- %
- % FORMAT spm_input('!dScroll',h,str)
- % Scroll text string in object h
- % h - handle of text object
- % Prompt - Text to scroll (Defaults to 'UserData' of h)
- %
- %-----------------------------------------------------------------------
- % SUBFUNCTIONS:
- %
- % FORMAT [Keys,Labs] = sf_labkeys(Labels)
- % Make unique character keys for the Labels, ignoring case.
- % Used with 'b'utton types.
- %
- % FORMAT [p,msg] = sf_eEval(str,Type,n,m)
- % Common code for evaluating various input types.
- %
- % FORMAT str = sf_SzStr(n,l)
- % Common code to construct prompt strings for pre-specified vector/matrix sizes
- %
- % FORMAT [p,msg] = sf_SzChk(p,n,msg)
- % Common code to check (& canonicalise) sizes of input vectors/matrices
- %
- %_______________________________________________________________________
- % @(#)spm_input.m 2.8 Andrew Holmes 03/03/04
- %-Parameters
- %=======================================================================
- PJump = 1; %-Jumping of pointer to question?
- TTips = 1; %-Use ToolTipStrings? (which can be annoying!)
- ConCrash = 1; %-Add "crash out" option to 'Interactive'fig.ContextMenu
- %-Condition arguments
- %=======================================================================
- if nargin<1||isempty(varargin{1}), Prompt=''; else Prompt=varargin{1}; end
- if ~isempty(Prompt) && ischar(Prompt) && Prompt(1)=='!'
- %-Utility functions have Prompt string starting with '!'
- Type = Prompt;
- else %-Should be an input request: get Type & YPos
- if nargin<3||isempty(varargin{3}), Type='e'; else Type=varargin{3}; end
- if any(Type=='|'), Type='b|'; end
- if nargin<2||isempty(varargin{2}), YPos='+1'; else YPos=varargin{2}; end
- [CmdLine,YPos] = spm_input('!CmdLine',YPos);
- if ~CmdLine %-Setup for GUI use
- %-Locate (or create) figure to work in
- Finter = spm_input('!GetWin');
- COLOUR = get(Finter,'Color');
-
- %-Find out which Y-position to use, setup for use
- YPos = spm_input('!SetNextPos',YPos,Finter,CmdLine);
-
- %-Determine position of objects
- [FRec,QRec,PRec,RRec]=spm_input('!InputRects',YPos,'',Finter);
- end
- end
- switch lower(Type)
- case {'s','s+','e','n','w','i','r','c','x','p'} %-String and evaluated input
- %=======================================================================
- %-Condition arguments
- if nargin<6||isempty(varargin{6}), m=[]; else m=varargin{6}; end
- if nargin<5||isempty(varargin{5}), n=[]; else n=varargin{5}; end
- if nargin<4, DefStr=''; else DefStr=varargin{4}; end
- if strcmpi(Type,'s+')
- %-DefStr should be a cellstr for 's+' type.
- if isempty(DefStr), DefStr = {};
- else DefStr = cellstr(DefStr); end
- DefStr = DefStr(:);
- else
- %-DefStr needs to be a string
- if ~ischar(DefStr), DefStr=num2str(DefStr); end
- DefStr = DefStr(:)';
- end
- strM='';
- switch lower(Type) %-Type specific defaults/setup
- case 's', TTstr='enter string';
- case 's+',TTstr='enter string - multi-line';
- case 'e', TTstr='enter expression to evaluate';
- case 'n', TTstr='enter expression - natural number(s)';
- if ~isempty(m), strM=sprintf(' (in [1,%d])',m); TTstr=[TTstr,strM]; end
- case 'w', TTstr='enter expression - whole number(s)';
- if ~isempty(m), strM=sprintf(' (in [0,%d])',m); TTstr=[TTstr,strM]; end
- case 'i', TTstr='enter expression - integer(s)';
- case 'r', TTstr='enter expression - real number(s)';
- if ~isempty(m), TTstr=[TTstr,sprintf(' in [%g,%g]',min(m),max(m))]; end
- case 'c', TTstr='enter indicator vector e.g. 0101... or abab...';
- if ~isempty(m) && isfinite(m), strM=sprintf(' (%d)',m); end
- case 'x', TTstr='enter contrast matrix';
- case 'p',
- if isempty(n), error('permutation of what?'), else P=n(:)'; end
- if isempty(m), n = [1,length(P)]; end
- m = P;
- if isempty(setxor(m,[1:max(m)]))
- TTstr=['enter permutation of [1:',num2str(max(m)),']'];
- else
- TTstr=['enter permutation of [',num2str(m),']'];
- end
- otherwise
- TTstr='enter expression';
- end
- strN = sf_SzStr(n);
- if CmdLine %-Use CmdLine to get answer
- %-----------------------------------------------------------------------
- spm_input('!PrntPrmpt',[Prompt,strN,strM],TTstr)
- %-Do Eval Types in Base workspace, catch errors
- switch lower(Type), case 's'
- if ~isempty(DefStr)
- Prompt=[Prompt,' (Default: ',DefStr,' )'];
- end
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
- while isempty(str)
- spm('Beep')
- fprintf('! %s : enter something!\n',mfilename)
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
- end
- p = str; msg = '';
- case 's+'
- fprintf(['Multi-line input: Type ''.'' on a line',...
- ' of its own to terminate input.\n'])
- if ~isempty(DefStr)
- fprintf('Default : (press return to accept)\n')
- fprintf(' : %s\n',DefStr{:})
- end
- fprintf('\n')
- str = input('l001 : ','s');
- while (isempty(str) || strcmp(str,'.')) && isempty(DefStr)
- spm('Beep')
- fprintf('! %s : enter something!\n',mfilename)
- str = input('l001 : ','s');
- end
- if isempty(str)
- %-Accept default
- p = DefStr;
- else
- %-Got some input, allow entry of additional lines
- p = {str};
- str = input(sprintf('l%03u : ',length(p)+1),'s');
- while ~strcmp(str,'.')
- p = [p;{str}];
- str = input(sprintf('l%03u : ',length(p)+1),'s');
- end
- end
- msg = '';
- otherwise
- if ~isempty(DefStr)
- Prompt=[Prompt,' (Default: ',DefStr,' )'];
- end
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
- [p,msg] = sf_eEval(str,Type,n,m);
- while ischar(p)
- spm('Beep'), fprintf('! %s : %s\n',mfilename,msg)
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
- [p,msg] = sf_eEval(str,Type,n,m);
- end
- end
- if ~isempty(msg), fprintf('\t%s\n',msg), end
- else %-Use GUI to get answer
- %-----------------------------------------------------------------------
- %-Create text and edit control objects
- %---------------------------------------------------------------
- hPrmpt = uicontrol(Finter,'Style','Text',...
- 'String',[strN,Prompt,strM],...
- 'Tag',['GUIinput_',int2str(YPos)],...
- 'UserData','',...
- 'BackgroundColor',COLOUR,...
- 'HorizontalAlignment','Right',...
- 'Position',PRec);
- if TTips, set(hPrmpt,'ToolTipString',[strN,Prompt,strM]); end
- %-Default button surrounding edit widget (if a DefStr given)
- %-Callback sets hPrmpt UserData, and EditWidget string, to DefStr
- % (Buttons UserData holds handles [hPrmpt,hEditWidget], set later)
- cb = ['set(get(gcbo,''UserData'')*[1;0],''UserData'',',...
- 'get(gcbo,''String'')),',...
- 'set(get(gcbo,''UserData'')*[0;1],''String'',',...
- 'get(gcbo,''String''))'];
- if ~isempty(DefStr)
- if iscellstr(DefStr), str=[DefStr{1},'...'];
- else str=DefStr; end
- hDef = uicontrol(Finter,'Style','PushButton',...
- 'String',DefStr,...
- 'ToolTipString',...
- ['Click on border to accept default: ' str],...
- 'Tag',['GUIinput_',int2str(YPos)],...
- 'UserData',[],...
- 'BackgroundColor',COLOUR,...
- 'CallBack',cb,...
- 'Position',RRec+[-2,-2,+4,+4]);
- else
- hDef = [];
- end
- %-Edit widget: Callback puts string into hPrompts UserData
- cb = 'set(get(gcbo,''UserData''),''UserData'',get(gcbo,''String''))';
- h = uicontrol(Finter,'Style','Edit',...
- 'String',DefStr,...
- 'Max',strcmpi(Type,'s+')+1,...
- 'Tag',['GUIinput_',int2str(YPos)],...
- 'UserData',hPrmpt,...
- 'CallBack',cb,...
- 'Horizontalalignment','Left',...
- 'BackgroundColor','w',...
- 'Position',RRec);
- set(hDef,'UserData',[hPrmpt,h])
- uifocus(h);
- if TTips, set(h,'ToolTipString',TTstr), end
- %-Figure ContextMenu for shortcuts
- hM = spm_input('!InptConMen',Finter,[hPrmpt,hDef,h]);
- cb = [ 'set(get(gcbo,''UserData''),''String'',',...
- '[''spm_load('''''',spm_select(1),'''''')'']), ',...
- 'set(get(get(gcbo,''UserData''),''UserData''),''UserData'',',...
- 'get(get(gcbo,''UserData''),''String''))'];
- uimenu(hM,'Label','load from text file','Separator','on',...
- 'CallBack',cb,'UserData',h)
- %-Bring window to fore & jump pointer to edit widget
- [PLoc,cF] = spm_input('!PointerJump',RRec,Finter);
- %-Setup FigureKeyPressFcn for editing of entry widget without clicking
- set(Finter,'KeyPressFcn',[...
- 'spm_input(''!EditableKeyPressFcn'',',...
- 'findobj(gcf,''Tag'',''GUIinput_',int2str(YPos),''',',...
- '''Style'',''edit''),',...
- 'get(gcbf,''CurrentCharacter''))'])
- %-Wait for edit, do eval Types in Base workspace, catch errors
- %---------------------------------------------------------------
- waitfor(hPrmpt,'UserData')
- if ~ishandle(hPrmpt), error(['Input window cleared whilst waiting ',...
- 'for response: Bailing out!']), end
- str = get(hPrmpt,'UserData');
- switch lower(Type), case 's'
- p = str; msg = '';
- case 's+'
- p = cellstr(str); msg = '';
- otherwise
- [p,msg] = sf_eEval(str,Type,n,m);
- while ischar(p)
- set(h,'Style','Text',...
- 'String',msg,'HorizontalAlignment','Center',...
- 'ForegroundColor','r')
- spm('Beep'), pause(2)
- set(h,'Style','Edit',...
- 'String',str,...
- 'HorizontalAlignment','Left',...
- 'ForegroundColor','k')
- %set(hPrmpt,'UserData','');
- waitfor(hPrmpt,'UserData')
- if ~ishandle(hPrmpt), error(['Input window cleared ',...
- 'whilst waiting for response: Bailing out!']),end
- str = get(hPrmpt,'UserData');
- [p,msg] = sf_eEval(str,Type,n,m);
- end
- end
- %-Fix edit window, clean up, reposition pointer, set CurrentFig back
- delete([hM,hDef]), set(Finter,'KeyPressFcn','')
- set(h,'Style','Text','HorizontalAlignment','Center',...
- 'ToolTipString',msg,...
- 'BackgroundColor',COLOUR)
- spm_input('!PointerJumpBack',PLoc,cF)
- drawnow
- end % (if CmdLine)
- %-Return response
- %-----------------------------------------------------------------------
- varargout = {p,YPos};
- case {'b','bd','b|','y/n','be1','bn1','bw1','bi1','br1',...
- '-n1','n1','-w1','w1','m'} %-'b'utton & 'm'enu Types
- %=======================================================================
- %-Condition arguments
- switch lower(Type), case {'b','be1','bi1','br1','m'}
- m = []; Title = '';
- if nargin<6, DefItem=[]; else DefItem=varargin{6}; end
- if nargin<5, Values=[]; else Values =varargin{5}; end
- if nargin<4, Labels=''; else Labels =varargin{4}; end
- case 'bd'
- if nargin<7, Title=''; else Title =varargin{7}; end
- if nargin<6, DefItem=[]; else DefItem=varargin{6}; end
- if nargin<5, Values=[]; else Values =varargin{5}; end
- if nargin<4, Labels=''; else Labels =varargin{4}; end
- case 'y/n'
- Title = '';
- if nargin<5, DefItem=[]; else DefItem=varargin{5}; end
- if nargin<4, Values=[]; else Values =varargin{4}; end
- if isempty(Values), Values='yn'; end
- Labels = {'yes','no'};
- case 'b|'
- Title = '';
- if nargin<5, DefItem=[]; else DefItem=varargin{5}; end
- if nargin<4, Values=[]; else Values =varargin{4}; end
- Labels = varargin{3};
- case 'bn1'
- if nargin<7, m=[]; else m=varargin{7}; end
- if nargin<6, DefItem=[]; else DefItem=varargin{6}; end
- if nargin<5, Values=[]; else Values =varargin{5}; end
- if nargin<4, Labels=[1:5]'; Values=[1:5]; Type='-n1';
- else Labels=varargin{4}; end
- case 'bw1'
- if nargin<7, m=[]; else m=varargin{7}; end
- if nargin<6, DefItem=[]; else DefItem=varargin{6}; end
- if nargin<5, Values=[]; else Values =varargin{5}; end
- if nargin<4, Labels=[0:4]'; Values=[0:4]; Type='-w1';
- else Labels=varargin{4}; end
- case {'-n1','n1','-w1','w1'}
- if nargin<5, m=[]; else m=varargin{5}; end
- if nargin<4, DefItem=[]; else DefItem=varargin{4}; end
- switch lower(Type)
- case {'n1','-n1'}, Labels=[1:min([5,m])]'; Values=Labels'; Type='-n1';
- case {'w1','-w1'}, Labels=[0:min([4,m])]'; Values=Labels'; Type='-w1';
- end
- end
- %-Check some labels were specified
- if isempty(Labels), error('No Labels specified'), end
- if iscellstr(Labels), Labels=char(Labels); end
- %-Convert Labels "option" string to string matrix if required
- if ischar(Labels) && any(Labels(:)=='|')
- OptStr=Labels;
- BarPos=find([OptStr=='|',1]);
- Labels=OptStr(1:BarPos(1)-1);
- for Bar = 2:sum(OptStr=='|')+1
- Labels=strvcat(Labels,OptStr(BarPos(Bar-1)+1:BarPos(Bar)-1));
- end
- end
- %-Set default Values for the Labels
- if isempty(Values)
- if strcmpi(Type,'m')
- Values=[1:size(Labels,1)]';
- else
- Values=Labels;
- end
- else
- %-Make sure Values are in rows
- if size(Labels,1)>1 && size(Values,1)==1, Values = Values'; end
- %-Check numbers of Labels and Values match
- if (size(Labels,1)~=size(Values,1))
- error('Labels & Values incompatible sizes'), end
- end
- %-Numeric Labels to strings
- if isnumeric(Labels)
- tmp = Labels; Labels = cell(size(tmp,1),1);
- for i=1:numel(tmp), Labels{i}=num2str(tmp(i,:)); end
- Labels=char(Labels);
- end
- switch lower(Type), case {'b','bd','b|','y/n'} %-Process button types
- %=======================================================================
-
- %-Make unique character keys for the Labels, sort DefItem
- %---------------------------------------------------------------
- nLabels = size(Labels,1);
- [Keys,Labs] = sf_labkeys(Labels);
- if ~isempty(DefItem) && any(DefItem==[1:nLabels])
- DefKey = Keys(DefItem);
- else
- DefItem = 0;
- DefKey = '';
- end
- if CmdLine
- %-Display question prompt
- spm_input('!PrntPrmpt',Prompt,'',Title)
- %-Build prompt
- %-------------------------------------------------------
- if ~isempty(Labs)
- Prmpt = ['[',Keys(1),']',deblank(Labs(1,:)),' '];
- for i = 2:nLabels
- Prmpt=[Prmpt,'/ [',Keys(i),']',deblank(Labs(i,:)),' '];
- end
- else
- Prmpt = ['[',Keys(1),'] '];
- for i = 2:nLabels, Prmpt=[Prmpt,'/ [',Keys(i),'] ']; end
- end
- if DefItem
- Prmpt = [Prmpt,...
- ' (Default: ',deblank(Labels(DefItem,:)),')'];
- end
- %-Ask for user response
- %-------------------------------------------------------
- if nLabels==1
- %-Only one choice - auto-pick & display
- k = 1; fprintf('%s: %s\t(only option)',Prmpt,Labels)
- else
- str = input([Prmpt,'? '],'s');
- if isempty(str), str=DefKey; end
- while isempty(str) || ~any(lower(Keys)==lower(str(1)))
- if ~isempty(str),fprintf('%c\t!Out of range\n',7),end
- str = input([Prmpt,'? '],'s');
- if isempty(str), str=DefKey; end
- end
- k = find(lower(Keys)==lower(str(1)));
- end
- fprintf('\n')
- p = Values(k,:); if ischar(p), p=deblank(p); end
- elseif strcmpi(Type,'bd')
- if nLabels>3, error('at most 3 labels for GUI ''bd'' type'), end
- tmp = cellstr(Labels);
- if DefItem
- tmp = [tmp; tmp(DefItem)];
- Prompt = cellstr(Prompt); Prompt=Prompt(:);
- Prompt = [Prompt;{' '};...
- {['[default: ',tmp{DefItem},']']}];
- else
- tmp = [tmp; tmp(1)];
- end
- k = min(find(strcmp(tmp,...
- questdlg(Prompt,sprintf('%s: %s...',spm('Version'),Title),...
- tmp{:}))));
- p = Values(k,:); if ischar(p), p=deblank(p); end
- else
- Tag = ['GUIinput_',int2str(YPos)]; %-Tag for widgets
- %-Create text and edit control objects
- %-'UserData' of prompt contains answer
- %-------------------------------------------------------
- hPrmpt = uicontrol(Finter,'Style','Text',...
- 'String',Prompt,...
- 'Tag',Tag,...
- 'UserData',[],...
- 'BackgroundColor',COLOUR,...
- 'HorizontalAlignment','Right',...
- 'Position',PRec);
- if TTips, set(hPrmpt,'ToolTipString',Prompt); end
-
- if nLabels==1
- %-Only one choice - auto-pick
- k = 1;
- else
- %-Draw buttons and process response
- dX = RRec(3)/nLabels;
-
- if TTips, str = ['select with mouse or use kbd: ',...
- sprintf('%c/',Keys(1:end-1)),Keys(end)];
- else str=''; end
-
- %-Store button # in buttons 'UserData' property
- %-Store handle of prompt string in buttons 'Max' property
- %-Button callback sets UserData of prompt string to
- % number of pressed button
- cb = ['set(get(gcbo,''UserData''),''UserData'',',...
- 'get(gcbo,''Max''))'];
- H = [];
- XDisp = [];
- for i=1:nLabels
- if i==DefItem
- %-Default button, outline it
- h = uicontrol(Finter,'Style','Frame',...
- 'BackGroundColor','k',...
- 'ForeGroundColor','k',...
- 'Tag',Tag,...
- 'Position',...
- [RRec(1)+(i-1)*dX ...
- RRec(2)-1 dX RRec(4)+2]);
- XDisp = (i-1/3)*dX;
- H = [H,h];
- end
- h = uicontrol(Finter,'Style','Pushbutton',...
- 'String',deblank(Labels(i,:)),...
- 'ToolTipString',sprintf('%s\n%s',deblank(Labels(i,:)),str),...
- 'Tag',Tag,...
- 'Max',i,...
- 'UserData',hPrmpt,...
- 'BackgroundColor',COLOUR,...
- 'Callback',cb,...
- 'Position',[RRec(1)+(i-1)*dX+1 ...
- RRec(2) dX-2 RRec(4)]);
- if i == DefItem, uifocus(h); end
- H = [H,h];
- end
-
- %-Figure ContextMenu for shortcuts
- hM = spm_input('!InptConMen',Finter,[hPrmpt,H]);
- %-Bring window to fore & jump pointer to default button
- [PLoc,cF]=spm_input('!PointerJump',RRec,Finter,XDisp);
-
- %-Callback for KeyPress, to store valid button # in
- % UserData of Prompt, DefItem if (DefItem~=0)
- % & return (ASCII-13) is pressed
- set(Finter,'KeyPressFcn',...
- ['spm_input(''!ButtonKeyPressFcn'',',...
- 'findobj(gcf,''Tag'',''',Tag,''',',...
- '''Style'',''text''),',...
- '''',lower(Keys),''',',num2str(DefItem),',',...
- 'get(gcbf,''CurrentCharacter''))'])
- %-Wait for button press, process results
- %-----------------------------------------------
- waitfor(hPrmpt,'UserData')
- if ~ishandle(hPrmpt)
- error(['Input objects cleared whilst ',...
- 'waiting for response: Bailing out!'])
- end
- k = get(hPrmpt,'UserData');
- %-Clean up
- delete([H,hM]), set(Finter,'KeyPressFcn','')
- spm_input('!PointerJumpBack',PLoc,cF)
- end
-
- %-Display answer
- uicontrol(Finter,'Style','Text',...
- 'String',deblank(Labels(k,:)),...
- 'Tag',Tag,...
- 'Horizontalalignment','Center',...
- 'BackgroundColor',COLOUR,...
- 'Position',RRec);
- drawnow
- p = Values(k,:); if ischar(p), p=deblank(p); end
- end
- case {'be1','bn1','bw1','bi1','br1','-n1','-w1'}
- %-Process button/entry combo types
- %=======================================================================
- if ischar(DefItem), DefStr=DefItem; else DefStr=num2str(DefItem); end
- if isempty(m), strM=''; else strM=sprintf(' (<=%d)',m); end
- if CmdLine
- %-Process default item
- %---------------------------------------------------------------
- if ~isempty(DefItem)
- [DefVal,msg] = sf_eEval(DefStr,Type(2),1);
- if ischar(DefVal), error(['Invalid DefItem: ',msg]), end
- Labels = strvcat(Labels,DefStr);
- Values = [Values;DefVal];
- DefItem = size(Labels,1);
- end
- %-Add option to specify...
- Labels = strvcat(Labels,'specify...');
- %-Process options
- nLabels = size(Labels,1);
- [Keys,Labs] = sf_labkeys(Labels);
- if ~isempty(DefItem), DefKey = Keys(DefItem); else DefKey = ''; end
- %-Print banner prompt
- %---------------------------------------------------------------
- spm_input('!PrntPrmpt',Prompt) %-Display question prompt
- if Type(1)=='-' %-No special buttons - go straight to input
- k = size(Labels,1);
- else %-Offer buttons, default or "specify..."
-
- %-Build prompt
- %-------------------------------------------------------
- if ~isempty(Labs)
- Prmpt = ['[',Keys(1),']',deblank(Labs(1,:)),' '];
- for i = 2:nLabels
- Prmpt=[Prmpt,'/ [',Keys(i),']',deblank(Labs(i,:)),' '];
- end
- else
- Prmpt = ['[',Keys(1),'] '];
- for i = 2:nLabels, Prmpt=[Prmpt,'/ [',Keys(i),'] ']; end
- end
- if DefItem, Prmpt = [Prmpt,...
- ' (Default: ',deblank(Labels(DefItem,:)),')']; end
-
- %-Ask for user response
- %-------------------------------------------------------
- if nLabels==1
- %-Only one choice - auto-pick & display
- k = 1; fprintf('%s: %s\t(only option)',Prmpt,Labels)
- else
- str = input([Prmpt,'? '],'s');
- if isempty(str), str=DefKey; end
- while isempty(str) || ~any(lower(Keys)==lower(str(1)))
- if ~isempty(str),fprintf('%c\t!Invalid response\n',7),end
- str = input([Prmpt,'? '],'s');
- if isempty(str), str=DefKey; end
- end
- k = find(lower(Keys)==lower(str(1)));
- end
- fprintf('\n')
- end
- %-Process response: prompt for value if "specify..." option chosen
- %===============================================================
- if k<size(Labels,1)
- p = Values(k,:); if ischar(p), p=deblank(p); end
- else
- %-"specify option chosen: ask user to specify
- %-------------------------------------------------------
- switch lower(Type(2))
- case 's', tstr=' string';
- case 'e', tstr='n expression';
- case 'n', tstr=' natural number';
- case 'w', tstr=' whole number';
- case 'i', tstr='n integer';
- case 'r', tstr=' real number';
- otherwise, tstr='';
- end
-
- Prompt = sprintf('%s (a%s%s)',Prompt,tstr,strM);
- if ~isempty(DefStr)
- Prompt=sprintf('%s\b, default %s)',Prompt,DefStr); end
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
-
- %-Eval in Base workspace, catch errors
- [p,msg] = sf_eEval(str,Type(2),1,m);
- while ischar(p)
- spm('Beep'), fprintf('! %s : %s\n',mfilename,msg)
- str = input([Prompt,' : '],'s');
- if isempty(str), str=DefStr; end
- [p,msg] = sf_eEval(str,Type(2),1,m);
- end
- end
- else
- Tag = ['GUIinput_',int2str(YPos)]; %-Tag for widgets
- nLabels = size(Labels,1); %-#buttons
- %-Create text and edit control objects
- %-'UserData' of prompt contains answer
- %---------------------------------------------------------------
- hPrmpt = uicontrol(Finter,'Style','Text',...
- 'String',[Prompt,strM],...
- 'Tag',Tag,...
- 'UserData',[],...
- 'BackgroundColor',COLOUR,...
- 'HorizontalAlignment','Right',...
- 'Position',PRec);
- if TTips, set(hPrmpt,'ToolTipString',[Prompt,strM]); end
- %-Draw buttons & entry widget, & process response
- dX = RRec(3)*(2/3)/nLabels;
- %-Store button # in buttons 'UserData'
- %-Store handle of prompt string in buttons 'Max' property
- %-Callback sets UserData of prompt string to button number.
- cb = ['set(get(gcbo,''UserData''),''UserData'',get(gcbo,''Max''))'];
- if TTips, str=sprintf('select by mouse or enter value in text widget');
- else str=''; end
- H = [];
- for i=1:nLabels
- h = uicontrol(Finter,'Style','Pushbutton',...
- 'String',deblank(Labels(i,:)),...
- 'Max',i,...
- 'ToolTipString',sprintf('%s\n%s',deblank(Labels(i,:)),str),...
- 'Tag',Tag,...
- 'UserData',hPrmpt,...
- 'BackgroundColor',COLOUR,...
- 'Callback',cb,...
- 'Position',[RRec(1)+(i-1)*dX+1 RRec(2) dX-2 RRec(4)]);
- H = [H,h];
- end
- %-Default button surrounding edit widget (if a DefStr given)
- %-Callback sets hPrmpt UserData, and EditWidget string, to DefStr
- % (Buttons UserData holds handles [hPrmpt,hEditWidget], set later)
- cb = ['set(subsref(get(gcbo,''UserData''),substruct(''()'',{1})),',...
- '''UserData'',get(gcbo,''String'')),',...
- 'set(subsref(get(gcbo,''UserData''),substruct(''()'',{2})),',...
- '''String'',get(gcbo,''String''))'];
- if ~isempty(DefStr)
- hDef = uicontrol(Finter,'Style','PushButton',...
- 'String',DefStr,...
- 'ToolTipString',['Click on border to accept ',...
- 'default: ' DefStr],...
- 'Tag',Tag,...
- 'UserData',[],...
- 'CallBack',cb,...
- 'BackgroundColor',COLOUR,...
- 'Position',...
- [RRec(1)+RRec(3)*(2/3) RRec(2)-2 RRec(3)/3+2 RRec(4)+4]);
- H = [H,hDef];
- else
- hDef = [];
- end
- %-Edit widget: Callback puts string into hPrompts UserData
- cb = ['set(get(gcbo,''UserData''),''UserData'',get(gcbo,''String''))'];
- h = uicontrol(Finter,'Style','Edit',...
- 'String',DefStr,...
- 'ToolTipString',str,...
- 'Tag',Tag,...
- 'UserData',hPrmpt,...
- 'CallBack',cb,...
- 'Horizontalalignment','Center',...
- 'BackgroundColor','w',...
- 'Position',...
- [RRec(1)+RRec(3)*(2/3)+2 RRec(2) RRec(3)/3-2 RRec(4)]);
- set(hDef,'UserData',[hPrmpt,h])
- uifocus(h);
- H = [H,h];
- %-Figure ContextMenu for shortcuts
- hM = spm_input('!InptConMen',Finter,[hPrmpt,H]);
- %-Bring window to fore & jump pointer to default button
- [PLoc,cF] = spm_input('!PointerJump',RRec,Finter,RRec(3)*0.95);
- %-Setup FigureKeyPressFcn for editing of entry widget without clicking
- set(Finter,'KeyPressFcn',[...
- 'spm_input(''!EditableKeyPressFcn'',',...
- 'findobj(gcf,''Tag'',''GUIinput_',int2str(YPos),''',',...
- '''Style'',''edit''),',...
- 'get(gcbf,''CurrentCharacter''))'])
- %-Wait for button press, process results
- %---------------------------------------------------------------
- waitfor(hPrmpt,'UserData')
- if ~ishandle(hPrmpt), error(['Input objects cleared whilst waiting ',...
- 'for response: Bailing out!']), end
- p = get(hPrmpt,'UserData');
- if ~ischar(p)
- k = p;
- p = Values(k,:); if ischar(p), p=deblank(p); end
- else
- Labels = strvcat(Labels,'specify...');
- k = size(Labels,1);
- [p,msg] = sf_eEval(p,Type(2),1,m);
- while ischar(p)
- set(H,'Visible','off')
- h = uicontrol('Style','Text','String',msg,...
- 'Horizontalalignment','Center',...
- 'ForegroundColor','r',...
- 'BackgroundColor',COLOUR,...
- 'Tag',Tag,'Position',RRec);
- spm('Beep')
- pause(2), delete(h), set(H,'Visible','on')
- set(hPrmpt,'UserData','')
- waitfor(hPrmpt,'UserData')
- if ~ishandle(hPrmpt), error(['Input objects cleared ',...
- 'whilst waiting for response: Bailing out!']),end
- p = get(hPrmpt,'UserData');
- if ischar(p), [p,msg] = sf_eEval(p,Type(2),1,m); end
- end
- end
- %-Clean up
- delete([H,hM]), set(Finter,'KeyPressFcn','')
- spm_input('!PointerJumpBack',PLoc,cF)
- %-Display answer
- uicontrol(Finter,'Style','Text',...
- 'String',num2str(p),...
- 'Tag',Tag,...
- 'Horizontalalignment','Center',...
- 'BackgroundColor',COLOUR,...
- 'Position',RRec);
- drawnow
- end % (if CmdLine)
- case 'm' %-Process menu type
- %=======================================================================
- nLabels = size(Labels,1);
- if ~isempty(DefItem) && ~any(DefItem==[1:nLabels]), DefItem=[]; end
- %-Process pull down menu type
- if CmdLine
- spm_input('!PrntPrmpt',Prompt)
- nLabels = size(Labels,1);
- for i = 1:nLabels, fprintf('\t%2d : %s\n',i,Labels(i,:)), end
- Prmpt = ['Menu choice (1-',int2str(nLabels),')'];
- if ~isempty(DefItem)
- Prmpt=[Prmpt,' (Default: ',num2str(DefItem),')'];
- end
- %-Ask for user response
- %-------------------------------------------------------
- if nLabels==1
- %-Only one choice - auto-pick & display
- k = 1;
- fprintf('Menu choice: 1 - %s\t(only option)',Labels)
- else
- k = input([Prmpt,' ? ']);
- if ~isempty(DefItem) && isempty(k), k=DefItem; end
- while isempty(k) || ~any([1:nLabels]==k)
- if ~isempty(k),fprintf('%c\t!Out of range\n',7),end
- k = input([Prmpt,' ? ']);
- if ~isempty(DefItem) && isempty(k), k=DefItem; end
- end
- end
- fprintf('\n')
-
- else
- Tag = ['GUIinput_',int2str(YPos)]; %-Tag for widgets
- if nLabels==1
- %-Only one choice - auto-pick
- k = 1;
- else
- Labs=[repmat(' ',nLabels,2),Labels];
- if ~isempty(DefItem)
- Labs(DefItem,1)='*';
- H = uicontrol(Finter,'Style','Frame',...
- 'BackGroundColor','k',...
- 'ForeGroundColor','k',...
- 'Position',QRec+[-1,-1,+2,+2]);
- else
- H = [];
- end
- cb = ['if (get(gcbo,''Value'')>1),',...
- 'set(gcbo,''UserData'',''Selected''), end'];
- hPopUp = uicontrol(Finter,'Style','popupmenu',...
- 'HorizontalAlignment','Left',...
- 'ForegroundColor','k',...
- 'BackgroundColor',COLOUR,...
- 'String',strvcat([Prompt,'...'],Labs),...
- 'Tag',Tag,...
- 'UserData',DefItem,...
- 'CallBack',cb,...
- 'Position',QRec);
- if TTips
- cLabs = cellstr(Labels);
- cInd = num2cell(1:nLabels);
- scLabs = [cInd; cLabs'];
- scLabs = sprintf('%d: %s\n',scLabs{:});
- set(hPopUp,'ToolTipString',sprintf(['select with ',...
- 'mouse or type option number (1-',...
- num2str(nLabels),') & press return\n%s'],scLabs));
- end
-
- %-Figure ContextMenu for shortcuts
- hM = spm_input('!InptConMen',Finter,[hPopUp,H]);
- %-Bring window to fore & jump pointer to menu widget
- [PLoc,cF] = spm_input('!PointerJump',RRec,Finter);
-
- %-Callback for KeyPresses
- cb=['spm_input(''!PullDownKeyPressFcn'',',...
- 'findobj(gcf,''Tag'',''',Tag,'''),',...
- 'get(gcf,''CurrentCharacter''))'];
- set(Finter,'KeyPressFcn',cb)
- %-Wait for menu selection
- %-----------------------------------------------
- waitfor(hPopUp,'UserData')
- if ~ishandle(hPopUp), error(['Input object cleared ',...
- 'whilst waiting for response: Bailing out!']),end
- k = get(hPopUp,'Value')-1;
- %-Clean up
- delete([H,hM]), set(Finter,'KeyPressFcn','')
- set(hPopUp,'Style','Text',...
- 'Horizontalalignment','Center',...
- 'String',deblank(Labels(k,:)),...
- 'BackgroundColor',COLOUR)
- spm_input('!PointerJumpBack',PLoc,cF)
- end
-
- %-Display answer
- uicontrol(Finter,'Style','Text',...
- 'String',deblank(Labels(k,:)),...
- 'Tag',Tag,...
- 'Horizontalalignment','Center',...
- 'BackgroundColor',COLOUR,...
- 'Position',QRec);
- drawnow
- end
- p = Values(k,:); if ischar(p), p=deblank(p); end
- otherwise, error('unrecognised type')
- end % (switch lower(Type) within case {'b','b|','y/n'})
- %-Return response
- %-----------------------------------------------------------------------
- varargout = {p,YPos};
- case {'m!','b!'} %-GUI PullDown/Buttons utility
- %=======================================================================
- % H = spm_input(Prompt,YPos,'p',Labels,cb,UD,XCB)
- %-Condition arguments
- if nargin<7, XCB = 0; else XCB = varargin{7}; end
- if nargin<6, UD = []; else UD = varargin{6}; end
- if nargin<5, cb = ''; else cb = varargin{5}; end
- if nargin<4, Labels = []; else Labels = varargin{4}; end
- if CmdLine, error('Can''t do CmdLine GUI utilities!'), end
- if isempty(cb), cb = 'disp(''(CallBack not set)'')'; end
- if ischar(cb), cb = cellstr(cb); end
- if length(cb)>1 && strcmpi(Type,'m!'), XCB=1; end
- if iscellstr(Labels), Labels=char(Labels); end
- %-Convert Labels "option" string to string matrix if required
- if any(Labels=='|')
- OptStr=Labels;
- BarPos=find([OptStr=='|',1]);
- Labels=OptStr(1:BarPos(1)-1);
- for Bar = 2:sum(OptStr=='|')+1
- Labels=strvcat(Labels,OptStr(BarPos(Bar-1)+1:BarPos(Bar)-1));
- end
- end
- %-Check #CallBacks
- if ~( length(cb)==1 || (length(cb)==size(Labels,1)) )
- error('Labels & Callbacks size mismatch'), end
- %-Draw Prompt
- %-----------------------------------------------------------------------
- Tag = ['GUIinput_',int2str(YPos)]; %-Tag for widgets
- if ~isempty(Prompt)
- uicontrol(Finter,'Style','Text',...
- 'String',Prompt,...
- 'Tag',Tag,...
- 'HorizontalAlignment','Right',...
- 'BackgroundColor',COLOUR,...
- 'Position',PRec)
- Rec = RRec;
- else
- Rec = QRec;
- end
- %-Sort out UserData for extended callbacks (handled by spm_input('!m_cb')
- %-----------------------------------------------------------------------
- if XCB, if iscell(UD), UD={UD}; end, UD = struct('UD',UD,'cb',{cb}); end
- %-Draw PullDown or Buttons
- %-----------------------------------------------------------------------
- switch lower(Type), case 'm!'
- if XCB, UD.cb=cb; cb = {'spm_input(''!m_cb'')'}; end
- H = uicontrol(Finter,'Style','popupmenu',...
- 'HorizontalAlignment','Left',...
- 'ForegroundColor','k',...
- 'BackgroundColor',COLOUR,...
- 'String',Labels,...
- 'Tag',Tag,...
- 'UserData',UD,...
- 'CallBack',char(cb),...
- 'Position',Rec);
- case 'b!'
- nLabels = size(Labels,1);
- dX = Rec(3)/nLabels;
- H = [];
- for i=1:nLabels
- if length(cb)>1, tcb=cb(i); else tcb=cb; end
- if XCB, UD.cb=tcb; tcb = {'spm_input(''!m_cb'')'}; end
- h = uicontrol(Finter,'Style','Pushbutton',...
- 'String',deblank(Labels(i,:)),...
- 'ToolTipString','',...
- 'Tag',Tag,...
- 'UserData',UD,...
- 'BackgroundColor',COLOUR,...
- 'Callback',char(tcb),...
- 'Position',[Rec(1)+(i-1)*dX+1 ...
- Rec(2) dX-2 Rec(4)]);
- H = [H,h];
- end
- end
- %-Bring window to fore & jump pointer to menu widget
- [PLoc,cF] = spm_input('!PointerJump',RRec,Finter);
- varargout = {H};
- case {'d','d!'} %-Display message
- %=======================================================================
- %-Condition arguments
- if nargin<4, Label=''; else Label=varargin{4}; end
- if CmdLine && strcmpi(Type,'d')
- fprintf('\n +-%s%s+',Label,repmat('-',1,57-length(Label)))
- Prompt = [Prompt,' '];
- while ~isempty(Prompt)
- tmp = length(Prompt);
- if tmp>56, tmp=min([max(find(Prompt(1:56)==' ')),56]); end
- fprintf('\n | %s%s |',Prompt(1:tmp),repmat(' ',1,56-tmp))
- Prompt(1:tmp)=[];
- end
- fprintf('\n +-%s+\n',repmat('-',1,57))
- elseif ~CmdLine
- if ~isempty(Label), Prompt = [Label,': ',Prompt]; end
- figure(Finter)
- %-Create text axes and edit control objects
- %---------------------------------------------------------------
- h = uicontrol(Finter,'Style','Text',...
- 'String',Prompt(1:min(length(Prompt),56)),...
- 'FontWeight','bold',...
- 'Tag',['GUIinput_',int2str(YPos)],...
- 'HorizontalAlignment','Left',...
- 'ForegroundColor','k',...
- 'BackgroundColor',COLOUR,...
- 'UserData',Prompt,...
- 'Position',QRec);
- if length(Prompt)>56
- pause(1)
- set(h,'ToolTipString',Prompt)
- spm_input('!dScroll',h)
- uicontrol(Finter,'Style','PushButton','String','>',...
- 'ToolTipString','press to scroll message',...
- 'Tag',['GUIinput_',int2str(YPos)],...
- 'UserData',h,...
- 'CallBack',[...
- 'set(gcbo,''Visible'',''off''),',...
- 'spm_input(''!dScroll'',get(gcbo,''UserData'')),',...
- 'set(gcbo,''Visible'',''on'')'],...
- 'BackgroundColor',COLOUR,...
- 'Position',[QRec(1)+QRec(3)-10,QRec(2),15,QRec(4)]);
- end
- end
- if nargout>0, varargout={[],YPos}; end
- %=======================================================================
- % U T I L I T Y F U N C T I O N S
- %=======================================================================
- case '!colour'
- %=======================================================================
- % colour = spm_input('!Colour')
- varargout = {COLOUR};
- case '!icond'
- %=======================================================================
- % [iCond,msg] = spm_input('!iCond',str,n,m)
- % Parse condition indicator spec strings:
- % '2 3 2 3', '0 1 0 1', '2323', '0101', 'abab', 'R A R A'
- if nargin<4, m=Inf; else m=varargin{4}; end
- if nargin<3, n=NaN; else n=varargin{3}; end
- if any(isnan(n(:)))
- n=Inf;
- elseif (length(n(:))==2 && ~any(n==1)) || length(n(:))>2
- error('condition input can only do vectors')
- end
- if nargin<2, i=''; else i=varargin{2}; end
- if isempty(i), varargout={[],'empty input'}; return, end
- msg = ''; i=i(:)';
- if ischar(i)
- if i(1)=='0' && all(ismember(unique(i(:)),char(abs('0'):abs('9'))))
- %-Leading zeros in a digit list
- msg = sprintf('%s expanded',i);
- z = min(find([diff(i=='0'),1]));
- i = [zeros(1,z), spm_input('!iCond',i(z+1:end))'];
- else
- %-Try an eval, for functions & string #s
- i = evalin('base',['[',i,']'],'i');
- end
- end
- if ischar(i)
- %-Evaluation error from above: see if it's an 'abab' or 'a b a b' type:
- [c,null,i] = unique(lower(i(~isspace(i))));
- if all(ismember(c,char(abs('a'):abs('z'))))
- %-Map characters a-z to 1-26, but let 'r' be zero (rest)
- tmp = c-'a'+1; tmp(tmp=='r'-'a'+1)=0;
- i = tmp(i);
- msg = [sprintf('[%s] mapped to [',c),...
- sprintf('%d,',tmp(1:end-1)),...
- sprintf('%d',tmp(end)),']'];
- else
- i = '!'; msg = 'evaluation error';
- end
- elseif ~all(floor(i(:))==i(:))
- i = '!'; msg = 'must be integers';
- elseif length(i)==1 && prod(n)>1
- msg = sprintf('%d expanded',i);
- i = floor(i./10.^[floor(log10(i)+eps):-1:0]);
- i = i-[0,10*i(1:end-1)];
- end
- %-Check size of i & #conditions
- if ~ischar(i), [i,msg] = sf_SzChk(i,n,msg); end
- if ~ischar(i) && isfinite(m) && length(unique(i))~=m
- i = '!'; msg = sprintf('%d conditions required',m);
- end
- varargout = {i,msg};
- case '!inptconmen'
- %=======================================================================
- % hM = spm_input('!InptConMen',Finter,H)
- if nargin<3, H=[]; else H=varargin{3}; end
- if nargin<2, varargout={[]}; else Finter=varargin{2}; end
- hM = uicontextmenu('Parent',Finter);
- if ConCrash
- uimenu(hM,'Label','crash out','Separator','on',...
- 'CallBack','delete(get(gcbo,''UserData''))',...
- 'UserData',[hM,H])
- end
- set(Finter,'UIContextMenu',hM)
- varargout={hM};
- case '!cmdline'
- %=======================================================================
- % [CmdLine,YPos] = spm_input('!CmdLine',YPos)
- %-Sorts out whether to use CmdLine or not & canonicalises YPos
- if nargin<2, YPos=''; else YPos=varargin{2}; end
- if isempty(YPos), YPos='+1'; end
- CmdLine = [];
- %-Special YPos specifications
- if ischar(YPos)
- if(YPos(1)=='!'), CmdLine=0; YPos(1)=[]; end
- elseif YPos==0
- CmdLine=1;
- elseif YPos<0
- CmdLine=0;
- YPos=-YPos;
- end
- CmdLine = spm('CmdLine',CmdLine);
- if CmdLine, YPos=0; end
- varargout = {CmdLine,YPos};
- case '!getwin'
- %=======================================================================
- % Finter = spm_input('!GetWin',F)
- %-Locate (or create) figure to work in (Don't use 'Tag'ged figs)
- if nargin<2, F='Interactive'; else F=varargin{2}; end
- Finter = spm_figure('FindWin',F);
- if isempty(Finter)
- if ~isempty(get(0,'Children'))
- if isempty(get(gcf,'Tag')), Finter = gcf;
- else Finter = spm('CreateIntWin'); end
- else
- Finter = spm('CreateIntWin');
- end
- end
- varargout = {Finter};
- case '!pointerjump'
- %=======================================================================
- % [PLoc,cF] = spm_input('!PointerJump',RRec,F,XDisp)
- %-Raise window & jump pointer over question
- if nargin<4, XDisp=[]; else XDisp=varargin{4}; end
- if nargin<3, F='Interactive'; else F=varargin{3}; end
- if nargin<2, error('Insufficient arguments'), else RRec=varargin{2}; end
- F = spm_figure('FindWin',F);
- PLoc = get(0,'PointerLocation');
- cF = get(0,'CurrentFigure');
- if ~isempty(F)
- figure(F)
- FRec = get(F,'Position');
- if isempty(XDisp), XDisp=RRec(3)*4/5; end
- if PJump, set(0,'PointerLocation',...
- floor([(FRec(1)+RRec(1)+XDisp), (FRec(2)+RRec(2)+RRec(4)/3)]));
- end
- end
- varargout = {PLoc,cF};
- case '!pointerjumpback'
- %=======================================================================
- % spm_input('!PointerJumpBack',PLoc,cF)
- %-Replace pointer and reset CurrentFigure back
- if nargin<4, cF=[]; else F=varargin{3}; end
- if nargin<2, error('Insufficient arguments'), else PLoc=varargin{2}; end
- if PJump, set(0,'PointerLocation',PLoc), end
- cF = spm_figure('FindWin',cF);
- if ~isempty(cF), set(0,'CurrentFigure',cF); end
- case '!prntprmpt'
- %=======================================================================
- % spm_input('!PrntPrmpt',Prompt,TipStr,Title)
- %-Print prompt for CmdLine questioning
- if nargin<4, Title = ''; else Title = varargin{4}; end
- if nargin<3, TipStr = ''; else TipStr = varargin{3}; end
- if nargin<2, Prompt = ''; else Prompt = varargin{2}; end
- if isempty(Prompt), Prompt='Enter an expression'; end
- Prompt = cellstr(Prompt);
- if ~isempty(TipStr)
- tmp = 8 + length(Prompt{end}) + length(TipStr);
- if tmp < 62
- TipStr = sprintf('%s(%s)',repmat(' ',1,70-tmp),TipStr);
- else
- TipStr = sprintf('\n%s(%s)',repmat(' ',1,max(0,70-length(TipStr))),TipStr);
- end
- end
- if isempty(Title)
- fprintf('\n%s\n',repmat('~',1,72))
- else
- fprintf('\n= %s %s\n',Title,repmat('~',1,72-length(Title)-3))
- end
- fprintf('\t%s',Prompt{1})
- for i=2:numel(Prompt), fprintf('\n\t%s',Prompt{i}), end
- fprintf('%s\n%s\n',TipStr,repmat('~',1,72))
- case '!inputrects'
- %=======================================================================
- % [Frec,QRec,PRec,RRec,Sz,Se] = spm_input('!InputRects',YPos,rec,F)
- if nargin<4, F='Interactive'; else F=varargin{4}; end
- if nargin<3, rec=''; else rec=varargin{3}; end
- if nargin<2, YPos=1; else YPos=varargin{2}; end
- F = spm_figure('FindWin',F);
- if isempty(F), error('Figure not found'), end
- Units = get(F,'Units');
- set(F,'Units','pixels')
- FRec = get(F,'Position');
- set(F,'Units',Units);
- Xdim = FRec(3); Ydim = FRec(4);
- WS = spm('WinScale');
- Sz = round(22*min(WS)); %-Height
- Pd = Sz/2; %-Pad
- Se = 2*round(25*min(WS)/2); %-Seperation
- Yo = round(2*min(WS)); %-Y offset for responses
- a = 5.5/10;
- y = Ydim - Se*YPos;
- QRec = [Pd y Xdim-2*Pd Sz]; %-Question
- PRec = [Pd y floor(a*Xdim)-2*Pd Sz]; %-Prompt
- RRec = [ceil(a*Xdim) y+Yo floor((1-a)*Xdim)-Pd Sz]; %-Response
- % MRec = [010 y Xdim-50 Sz]; %-Menu PullDown
- % BRec = MRec + [Xdim-50+1, 0+1, 50-Xdim+30, 0]; %-Menu PullDown OK butt
- if ~isempty(rec)
- varargout = {eval(rec)};
- else
- varargout = {FRec,QRec,PRec,RRec,Sz,Se};
- end
- case '!deleteinputobj'
- %=======================================================================
- % spm_input('!DeleteInputObj',F)
- if nargin<2, F='Interactive'; else F=varargin{2}; end
- h = spm_input('!FindInputObj',F);
- delete(h(h>0))
- case {'!currentpos','!findinputobj'}
- %=======================================================================
- % [CPos,hCPos] = spm_input('!CurrentPos',F)
- % h = spm_input('!FindInputObj',F)
- % hPos contains handles: Columns contain handles corresponding to Pos
- if nargin<2, F='Interactive'; else F=varargin{2}; end
- F = spm_figure('FindWin',F);
- %-Find tags and YPos positions of 'GUIinput_' 'Tag'ged objects
- H = [];
- YPos = [];
- for h = get(F,'Children')'
- tmp = get(h,'Tag');
- if ~isempty(tmp)
- if strcmp(tmp(1:min(length(tmp),9)),'GUIinput_')
- H = [H, h];
- YPos = [YPos, eval(tmp(10:end))];
- end
- end
- end
- switch lower(Type), case '!findinputobj'
- varargout = {H};
- case '!currentpos'
- if nargout<2
- varargout = {max(YPos),[]};
- elseif isempty(H)
- varargout = {[],[]};
- else
- %-Sort out
- tmp = sort(YPos);
- CPos = tmp(find([1,diff(tmp)]));
- nPos = length(CPos);
- nPerPos = diff(find([1,diff(tmp),1]));
- hCPos = zeros(max(nPerPos),nPos);
- for i = 1:nPos
- hCPos(1:nPerPos(i),i) = H(YPos==CPos(i))';
- end
- varargout = {CPos,hCPos};
- end
- end
- case '!nextpos'
- %=======================================================================
- % [NPos,CPos,hCPos] = spm_input('!NextPos',YPos,F,CmdLine)
- %-Return next position to use
- if nargin<3, F='Interactive'; else F=varargin{3}; end
- if nargin<2, YPos='+1'; else YPos=varargin{2}; end
- if nargin<4, [CmdLine,YPos]=spm_input('!CmdLine',YPos);
- else CmdLine=varargin{4}; end
- F = spm_figure('FindWin',F);
- %-Get current positions
- if nargout<3
- CPos = spm_input('!CurrentPos',F);
- hCPos = [];
- else
- [CPos,hCPos] = spm_input('!CurrentPos',F);
- end
- if CmdLine
- NPos = 0;
- else
- MPos = spm_input('!MaxPos',F);
- if ischar(YPos)
- %-Relative YPos
- %-Strip any '!' prefix from YPos
- if(YPos(1)=='!'), YPos(1)=[]; end
- if strncmp(YPos,'_',1)
- %-YPos='_' means bottom
- YPos=eval(['MPos+',YPos(2:end)],'MPos');
- else
- YPos = max([0,CPos])+eval(YPos);
- end
- else
- %-Absolute YPos
- YPos=abs(YPos);
- end
- NPos = min(max(1,YPos),MPos);
- end
- varargout = {NPos,CPos,hCPos};
- case '!setnextpos'
- %=======================================================================
- % NPos = spm_input('!SetNextPos',YPos,F,CmdLine)
- %-Set next position to use
- if nargin<3, F='Interactive'; else F=varargin{3}; end
- if nargin<2, YPos='+1'; else YPos=varargin{2}; end
- if nargin<4, [CmdLine,YPos]=spm_input('!CmdLine',YPos);
- else CmdLine=varargin{4}; end
- %-Find out which Y-position to use
- [NPos,CPos,hCPos] = spm_input('!NextPos',YPos,F,CmdLine);
- %-Delete any previous inputs using positions NPos and after
- if any(CPos>=NPos), h=hCPos(:,CPos>=NPos); delete(h(h>0)), end
- varargout = {NPos};
- case '!maxpos'
- %=======================================================================
- % MPos = spm_input('!MaxPos',F,FRec3)
- %
- if nargin<3
- if nargin<2, F='Interactive'; else F=varargin{2}; end
- F = spm_figure('FindWin',F);
- if isempty(F)
- FRec3=spm('WinSize','Interactive')*[0;0;0;1];
- else
- %-Get figure size
- Units = get(F,'Units');
- set(F,'Units','pixels')
- FRec3 = get(F,'Position')*[0;0;0;1];
- set(F,'Units',Units);
- end
- end
- Se = round(25*min(spm('WinScale')));
- MPos = floor((FRec3-5)/Se);
- varargout = {MPos};
- case '!editablekeypressfcn'
- %=======================================================================
- % spm_input('!EditableKeyPressFcn',h,ch,hPrmpt)
- if nargin<2, error('Insufficient arguments'), else h=varargin{2}; end
- if isempty(h), set(gcbf,'KeyPressFcn','','UserData',[]), return, end
- if nargin<3, ch=get(get(h,'Parent'),'CurrentCharacter'); else ch=varargin{3};end
- if nargin<4, hPrmpt=get(h,'UserData'); else hPrmpt=varargin{4}; end
- tmp = get(h,'String');
- if isempty(tmp), tmp=''; end
- if iscellstr(tmp) && length(tmp)==1; tmp=tmp{:}; end
- if isempty(ch) %- shift / control / &c. pressed
- return
- elseif any(abs(ch)==[32:126]) %-Character
- if iscellstr(tmp), return, end
- tmp = [tmp, ch];
- elseif abs(ch)==21 %- ^U - kill
- tmp = '';
- elseif any(abs(ch)==[8,127]) %-BackSpace or Delete
- if iscellstr(tmp), return, end
- if ~isempty(tmp), tmp(length(tmp))=''; end
- elseif abs(ch)==13 %-Return pressed
- if ~isempty(tmp)
- set(hPrmpt,'UserData',get(h,'String'))
- end
- return
- else
- %-Illegal character
- return
- end
- set(h,'String',tmp)
- case '!buttonkeypressfcn'
- %=======================================================================
- % spm_input('!ButtonKeyPressFcn',h,Keys,DefItem,ch)
- %-Callback for KeyPress, to store valid button # in UserData of Prompt,
- % DefItem if (DefItem~=0) & return (ASCII-13) is pressed
- %-Condition arguments
- if nargin<2, error('Insufficient arguments'), else h=varargin{2}; end
- if isempty(h), set(gcf,'KeyPressFcn','','UserData',[]), return, end
- if nargin<3, error('Insufficient arguments'); else Keys=varargin{3}; end
- if nargin<4, DefItem=0; else DefItem=varargin{4}; end
- if nargin<5, ch=get(gcf,'CurrentCharacter'); else ch=varargin{5}; end
- if isempty(ch)
- %- shift / control / &c. pressed
- return
- elseif (DefItem && ch==13)
- But = DefItem;
- else
- But = find(lower(ch)==lower(Keys));
- end
- if ~isempty(But), set(h,'UserData',But), end
- case '!pulldownkeypressfcn'
- %=======================================================================
- % spm_input('!PullDownKeyPressFcn',h,ch,DefItem)
- if nargin<2, error('Insufficient arguments'), else h=varargin{2}; end
- if isempty(h), set(gcf,'KeyPressFcn',''), return, end
- if nargin<3, ch=get(get(h,'Parent'),'CurrentCharacter'); else ch=varargin{3};end
- if nargin<4, DefItem=get(h,'UserData'); else ch=varargin{4}; end
- Pmax = get(h,'Max');
- Pval = get(h,'Value');
- if Pmax==1, return, end
- if isempty(ch)
- %- shift / control / &c. pressed
- return
- elseif abs(ch)==13
- if Pval==1
- if DefItem, set(h,'Value',max(2,min(DefItem+1,Pmax))), end
- else
- set(h,'UserData','Selected')
- end
- elseif any(ch=='bpu')
- %-Move "b"ack "u"p to "p"revious entry
- set(h,'Value',max(2,Pval-1))
- elseif any(ch=='fnd')
- %-Move "f"orward "d"own to "n"ext entry
- set(h,'Value',min(Pval+1,Pmax))
- elseif any(ch=='123456789')
- %-Move to entry n
- set(h,'Value',max(2,min(eval(ch)+1,Pmax)))
- else
- %-Illegal character
- end
- case '!m_cb' %-CallBack handler for extended CallBack 'p'ullDown type
- %=======================================================================
- % spm_input('!m_cb')
- %-Get PopUp handle and value
- h = gcbo;
- n = get(h,'Value');
- %-Get PopUp's UserData, check cb and UD fields exist, extract cb & UD
- tmp = get(h,'UserData');
- if ~(isfield(tmp,'cb') && isfield(tmp,'UD'))
- error('Invalid UserData structure for spm_input extended callback')
- end
- cb = tmp.cb;
- UD = tmp.UD;
- %-Evaluate appropriate CallBack string (ignoring any return arguments)
- % NB: Using varargout={eval(cb{n})}; gives an error if the CallBack
- % has no return arguments!
- if length(cb)==1, eval(char(cb)); else eval(cb{n}); end
- case '!dscroll'
- %=======================================================================
- % spm_input('!dScroll',h,Prompt)
- %-Scroll text in object h
- if nargin<2, return, else h=varargin{2}; end
- if nargin<3, Prompt = get(h,'UserData'); else Prompt=varargin{3}; end
- tmp = Prompt;
- if length(Prompt)>56
- while length(tmp)>56
- tic, while(toc<0.1), pause(0.05), end
- tmp(1)=[];
- set(h,'String',tmp(1:min(length(tmp),56)))
- end
- pause(1)
- set(h,'String',Prompt(1:min(length(Prompt),56)))
- end
- otherwise
- %=======================================================================
- error(['Invalid type/action: ',Type])
- %=======================================================================
- end % (case lower(Type))
- %=======================================================================
- %- S U B - F U N C T I O N S
- %=======================================================================
- function [Keys,Labs] = sf_labkeys(Labels)
- %=======================================================================
- %-Make unique character keys for the Labels, ignoring case
- if nargin<1, error('insufficient arguments'), end
- if iscellstr(Labels), Labels = char(Labels); end
- if isempty(Labels), Keys=''; Labs=''; return, end
- Keys=Labels(:,1)';
- nLabels = size(Labels,1);
- if any(~diff(abs(sort(lower(Keys)))))
- if nLabels<10
- Keys = sprintf('%d',[1:nLabels]);
- elseif nLabels<=26
- Keys = sprintf('%c',abs('a')+[0:nLabels-1]);
- else
- error('Too many buttons!')
- end
- Labs = Labels;
- else
- Labs = Labels(:,2:end);
- end
- function [p,msg] = sf_eEval(str,Type,n,m)
- %=======================================================================
- %-Evaluation and error trapping of typed input
- if nargin<4, m=[]; end
- if nargin<3, n=[]; end
- if nargin<2, Type='e'; end
- if nargin<1, str=''; end
- if isempty(str), p='!'; msg='empty input'; return, end
- switch lower(Type)
- case 's'
- p = str; msg = '';
- case 'e'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'n'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- elseif any(floor(p(:))~=p(:)|p(:)<1)||~isreal(p)
- p='!'; msg='natural number(s) required';
- elseif ~isempty(m) && any(p(:)>m)
- p='!'; msg=['max value is ',num2str(m)];
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'w'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- elseif any(floor(p(:))~=p(:)|p(:)<0)||~isreal(p)
- p='!'; msg='whole number(s) required';
- elseif ~isempty(m) && any(p(:)>m)
- p='!'; msg=['max value is ',num2str(m)];
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'i'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- elseif any(floor(p(:))~=p(:))||~isreal(p)
- p='!'; msg='integer(s) required';
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'p'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- elseif ~isempty(setxor(p(:)',m))
- p='!'; msg='invalid permutation';
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'r'
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- elseif ~isreal(p)
- p='!'; msg='real number(s) required';
- elseif ~isempty(m) && ( max(p)>max(m) || min(p)<min(m) )
- p='!'; msg=sprintf('real(s) in [%g,%g] required',min(m),max(m));
- else
- [p,msg] = sf_SzChk(p,n);
- end
- case 'c'
- if isempty(m), m=Inf; end
- [p,msg] = spm_input('!iCond',str,n,m);
- case 'x'
- X = m; %-Design matrix/space-structure
- if isempty(n), n=1; end
- %-Sort out contrast matrix dimensions (contrast vectors in rows)
- if length(n)==1, n=[n,Inf]; else n=reshape(n(1:2),1,2); end
- if ~isempty(X) % - override n(2) w/ design column dimension
- n(2) = spm_SpUtil('size',X,2);
- end
- p = evalin('base',['[',str,']'],'''!''');
- if ischar(p)
- msg = 'evaluation error';
- else
- if isfinite(n(2)) && size(p,2)<n(2)
- tmp = n(2) -size(p,2);
- p = [p, zeros(size(p,1),tmp)];
- if size(p,1)>1, str=' columns'; else str='s'; end
- msg = sprintf('right padded with %d zero%s',tmp,str);
- else
- msg = '';
- end
- if size(p,2)>n(2)
- p='!'; msg=sprintf('too long - only %d prams',n(2));
- elseif isfinite(n(1)) && size(p,1)~=n(1)
- p='!';
- if n(1)==1, msg='vector required';
- else msg=sprintf('%d contrasts required',n(1)); end
- elseif ~isempty(X) && ~spm_SpUtil('allCon',X,p')
- p='!'; msg='invalid contrast';
- end
- end
- otherwise
- error('unrecognised type');
- end
- function str = sf_SzStr(n,l)
- %=======================================================================
- %-Size info string construction
- if nargin<2, l=0; else l=1; end
- if nargin<1, error('insufficient arguments'), end
- if isempty(n), n=NaN; end
- n=n(:); if length(n)==1, n=[n,1]; end, dn=length(n);
- if any(isnan(n)) || (prod(n)==1 && dn<=2) || (dn==2 && min(n)==1 && isinf(max(n)))
- str = ''; lstr = '';
- elseif dn==2 && min(n)==1
- str = sprintf('[%d]',max(n)); lstr = [str,'-vector'];
- elseif dn==2 && sum(isinf(n))==1
- str = sprintf('[%d]',min(n)); lstr = [str,'-vector(s)'];
- else
- str='';
- for i = 1:dn
- if isfinite(n(i)), str = sprintf('%s,%d',str,n(i));
- else str = sprintf('%s,*',str); end
- end
- str = ['[',str(2:end),']']; lstr = [str,'-matrix'];
- end
- if l, str=sprintf('\t%s',lstr); else str=[str,' ']; end
- function [p,msg] = sf_SzChk(p,n,msg)
- %=======================================================================
- %-Size checking
- if nargin<3, msg=''; end
- if nargin<2, n=[]; end, if isempty(n), n=NaN; else n=n(:)'; end
- if nargin<1, error('insufficient arguments'), end
- if ischar(p) || any(isnan(n(:))), return, end
- if length(n)==1, n=[n,1]; end
- dn = length(n);
- sp = size(p);
- dp = ndims(p);
- if dn==2 && min(n)==1
- %-[1,1], [1,n], [n,1], [1,Inf], [Inf,1] - vector - allow transpose
- %---------------------------------------------------------------
- i = min(find(n==max(n)));
- if n(i)==1 && max(sp)>1
- p='!'; msg='scalar required';
- elseif ndims(p)~=2 || ~any(sp==1) || ( isfinite(n(i)) && max(sp)~=n(i) )
- %-error: Not2D | not vector | not right length
- if isfinite(n(i)), str=sprintf('%d-',n(i)); else str=''; end
- p='!'; msg=[str,'vector required'];
- elseif sp(i)==1 && n(i)~=1
- p=p'; msg=[msg,' (input transposed)'];
- end
- elseif dn==2 && sum(isinf(n))==1
- %-[n,Inf], [Inf,n] - n vector(s) required - allow transposing
- %---------------------------------------------------------------
- i = find(isfinite(n));
- if ndims(p)~=2 || ~any(sp==n(i))
- p='!'; msg=sprintf('%d-vector(s) required',min(n));
- elseif sp(i)~=n
- p=p'; msg=[msg,' (input transposed)'];
- end
- else
- %-multi-dimensional matrix required - check dimensions
- %---------------------------------------------------------------
- if ndims(p)~=dn || ~all( size(p)==n | isinf(n) )
- p = '!'; msg='';
- for i = 1:dn
- if isfinite(n(i)), msg = sprintf('%s,%d',msg,n(i));
- else msg = sprintf('%s,*',msg); end
- end
- msg = ['[',msg(2:end),']-matrix required'];
- end
- end
- %==========================================================================
- function uifocus(h)
- try
- if strcmpi(get(h, 'Style'), 'PushButton') == 1
- uicontrol(gcbo);
- else
- uicontrol(h);
- end
- end
|