0001 function hh = uitabpanel(varargin)
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049
0050
0051 tag = '';
0052 units = 'normalized';
0053 position = [0,0,1,1];
0054 fontweight = 'normal';
0055 [style,type] = deal('lefttop',2);
0056 visible = 'on';
0057
0058 foregroundcolor = [1,1,1];
0059 backgroundcolor = [0.7725,0.8431,0.9608];
0060 panelbackgroundcolor = [0.4314,0.5882,0.8431];
0061 titlehighlightcolor = [1,0.8,0];
0062
0063 horizontalalignment = 'center';
0064 [createfcn,deletefcn,resizefcn] = deal({},{},{});
0065
0066 active = 0;
0067 styles = {'popup','lefttop','righttop','leftbottom','rightbottom', ...
0068 'centertop','centerbottom'};
0069
0070 for k=1:2:nargin
0071 property = lower(varargin{k});
0072 value = varargin{k+1};
0073 switch property
0074 case {'style','tabposition','titleposition'}
0075 style = value;
0076 type = strmatch(lower(style),styles);
0077 if isempty(type)
0078 error(['Bad value for Style/TitlePosition property: ' style '.']);
0079 end
0080 case 'fontsize'
0081 fontsize = value;
0082 case {'title','string'}
0083 string = value;
0084 ntab = length(string);
0085 case {'frameposition','position'}
0086 position = value;
0087 case {'framebackgroundcolor','backgroundcolor'}
0088 backgroundcolor = value;
0089 case {'framebordertype','bordertype'}
0090 bordertype = value;
0091 case {'panelheights','heights'}
0092 panelheight = value;
0093 case {'titleforegroundcolor','foregroundcolor'}
0094 foregroundcolor = value;
0095 case {'selecteditem','active'}
0096 active = value;
0097 otherwise
0098 eval([property '= value;']);
0099 end
0100 end
0101
0102 if ~exist('parent','var')
0103 parent = gcf;
0104 end
0105 if ~exist('margins','var')
0106 if type==1
0107 margins = {[1.5,0.75,1.5,1],'characters'};
0108 else
0109 margins = {1,'pixels'};
0110 end
0111 end
0112 if ~iscell(margins)
0113 margins = {margins,units};
0114 end
0115
0116 if ~exist('bordertype','var')
0117 if type==1
0118 bordertype = 'etchedin';
0119 else
0120 bordertype = 'none';
0121 end
0122 end
0123
0124 if ~exist('titlebackgroundcolor','var')
0125 titlebackgroundcolor = 0.95*panelbackgroundcolor;
0126 end
0127
0128 cmenu = uicontextmenu;
0129 uimenu(cmenu,'Label','Goto Tab');
0130 uimenu(cmenu,'Separator','on');
0131
0132 htab = uipanel( ...
0133 'Parent',parent, ...
0134 'Units',units, ...
0135 'Position',position, ...
0136 'DeleteFcn',deletefcn, ...
0137 'ResizeFcn',resizefcn, ...
0138 'BackgroundColor',backgroundcolor, ...
0139 'BorderType',bordertype, ...
0140 'UIContextMenu',cmenu, ...
0141 'Visible',visible, ...
0142 'FontSize', fontsize,...
0143 'Tag',tag);
0144 set(htab,'Units','pixels');
0145 tabpos = get(htab,'Position');
0146
0147 status = uicontainer( ...
0148 'Parent',htab, ...
0149 'BackgroundColor',backgroundcolor, ...
0150 'Units',margins{2}, ...
0151 'Position',[1,1,1,1], ...
0152 'UIContextMenu',cmenu, ...
0153 'Visible','off');
0154 set(status,'Units','pixels');
0155 charsz = get(status,'Position');
0156 margins = [charsz(1:2),charsz(1:2)].*margins{1};
0157 set(status,'Units','characters');
0158 set(status,'Position',[1,1,1,1]);
0159 set(status,'Units','pixels');
0160 charsz = get(status,'Position');
0161 titleheight = 2*charsz(4);
0162
0163 if type==1
0164
0165
0166
0167 panelpos = tabpos;
0168 titlepos = [margins(1),tabpos(2)+tabpos(4)-titleheight-margins(2), ...
0169 tabpos(3)-sum(margins([1,3])),titleheight];
0170 ttextpos = [0.05,0.1,0.9,0.76];
0171
0172 if ~exist('panelheight','var')
0173 panelheight = ones(1,ntab);
0174 end
0175 if ~exist('panelbordertype','var')
0176 panelbordertype = 'line';
0177 end
0178
0179 for k=1:ntab
0180 title(k) = uicontrol( ...
0181 'Parent',htab, ...
0182 'Units','pixels', ...
0183 'Position',titlepos, ...
0184 'ForegroundColor',foregroundcolor, ...
0185 'BackgroundColor',titlebackgroundcolor, ...
0186 'FontWeight',fontweight, ...
0187 'FontSize', fontsize,...
0188 'HorizontalAlignment',horizontalalignment, ...
0189 'Callback',{@PopupTabCbk,k}, ...
0190 'Style','toggle', ...
0191 'String',string{k}, ...
0192 'Value',0, ...
0193 'Visible','on');
0194
0195 panel(k) = uipanel( ...
0196 'Parent',htab, ...
0197 'Units','pixels', ...
0198 'Position',titlepos+[0,0,0,panelheight(k)*charsz(4)], ...
0199 'BackgroundColor',panelbackgroundcolor, ...
0200 'BorderType',panelbordertype, ...
0201 'Visible','off');
0202
0203 uimenu(cmenu, ...
0204 'Label',string{k}, ...
0205 'Callback',{@PopupTabCbk,k});
0206 end
0207
0208 uimenu(cmenu,'Separator','on');
0209 uimenu(cmenu, ...
0210 'Label','Expand All', ...
0211 'Callback',{@PopupTabEnableAllCbk,'on'});
0212 uimenu(cmenu, ...
0213 'Label','Collapse All', ...
0214 'Callback',{@PopupTabEnableAllCbk,'off'});
0215
0216 sliderpos = [tabpos(3)-14,2,15,tabpos(4)-3];
0217 slider = uicontrol( ...
0218 'Parent',htab, ...
0219 'Units','pixels', ...
0220 'Position',sliderpos, ...
0221 'BackgroundColor',panelbackgroundcolor, ...
0222 'Style','slider', ...
0223 'Callback',@PopupTabSliderCbk, ...
0224 'Value',0, ...
0225 'Min',-1, ...
0226 'Max',0, ...
0227 'Visible','off');
0228
0229 statuspos = titlepos;
0230 statuspos([2,4]) = [margins(4),panelpos(4)-(ntab+1)*(margins(4)+titlepos(4))];
0231 set(status,'Position',statuspos);
0232 PopupTabCbk(title(1),[],active);
0233 set(status,'ResizeFcn',@PopupTabResizeCbk);
0234
0235 else
0236
0237
0238
0239 margins(3:4) = -(margins(1:2)+margins(3:4));
0240 switch type
0241 case 2
0242 [loop,sign] = deal(1:ntab,[1,0,1,0]);
0243 case 3
0244 [loop,sign] = deal(ntab:-1:1,[ntab,0,0,0]);
0245 case 4
0246 [loop,sign] = deal(1:ntab,[1,0,1,1]);
0247 case 5
0248 [loop,sign] = deal(ntab:-1:1,[ntab,0,0,1]);
0249 case 6
0250 [loop,sign] = deal(1:ntab,[1,ntab,1,0]);
0251 case 7
0252 [loop,sign] = deal(1:ntab,[1,ntab,1,1]);
0253 end
0254 addtitle = 2*[sign(3:4),-1,-1];
0255 if sign(3)
0256 ttextpos = [0.05,0.08,0.9,0.76];
0257 else
0258 ttextpos = [0.05,0.05,0.9,0.76];
0259 end
0260
0261 if ~exist('panelbordertype','var')
0262 panelbordertype = 'beveledout';
0263 end
0264
0265 for k=1:ntab
0266 title(k) = uipanel( ...
0267 'Parent',htab, ...
0268 'Units','pixels', ...
0269 'BackgroundColor',titlebackgroundcolor, ...
0270 'BorderType',panelbordertype, ...
0271 'ButtonDownFcn',{@TopBottomTabCbk,k}, ...
0272 'Visible','on');
0273
0274
0275 ttext(k) = uicontrol( ...
0276 'Parent',title(k), ...
0277 'Units','normalized', ...
0278 'Position',ttextpos, ...
0279 'ForegroundColor',foregroundcolor, ...
0280 'BackgroundColor',titlebackgroundcolor, ...
0281 'HorizontalAlignment',horizontalalignment, ...
0282 'Style','text', ...
0283 'String',string{k}, ...
0284 'Enable','inactive', ...
0285 'FontSize', fontsize,...
0286 'HitTest','off',...
0287 'Visible','on');
0288
0289 panel(k) = uipanel( ...
0290 'Parent',htab, ...
0291 'Units','pixels', ...
0292 'BackgroundColor',panelbackgroundcolor, ...
0293 'BorderType',panelbordertype, ...
0294 'Visible','off');
0295
0296 uimenu(cmenu, ...
0297 'Label',string{k}, ...
0298 'Callback',{@TopBottomTabCbk,k});
0299 end
0300
0301 if ~active, active = 1; end
0302 set(panel(active),'Visible','on');
0303
0304 inset(1) = uicontrol( ...
0305 'Parent',htab, ...
0306 'Units','pixels', ...
0307 'BackgroundColor',panelbackgroundcolor, ...
0308 'Style','text', ...
0309 'Visible','on');
0310 if ~isnan(titlehighlightcolor)
0311 inset(2) = uicontrol( ...
0312 'Parent',htab, ...
0313 'Units','pixels', ...
0314 'BackgroundColor',titlehighlightcolor, ...
0315 'Style','text', ...
0316 'Visible','on');
0317 inset(3) = uicontrol( ...
0318 'Parent',htab, ...
0319 'Units','pixels', ...
0320 'BackgroundColor',0.85*titlehighlightcolor, ...
0321 'Style','text', ...
0322 'Visible','on');
0323 end
0324
0325 TopBottomTabResizeCbk(status,[]);
0326 set(status,'ResizeFcn',@TopBottomTabResizeCbk);
0327 end
0328
0329 setappdata(htab,'panels',panel);
0330 setappdata(htab,'status',status);
0331 if ~isempty(createfcn)
0332 createfcn(htab,[],panel,status);
0333 end
0334
0335 if nargout, hh = htab; end
0336
0337
0338
0339
0340
0341 function PopupTabCbk(hobj,evdt,indx)
0342
0343 set(title,'Value',0);
0344 if indx>0
0345 indxvis = strcmp(get(panel(indx),'Visible'),'off');
0346 if indxvis
0347 set(panel(indx),'Visible','on');
0348 else
0349 set(panel(indx),'Visible','off');
0350 end
0351 end
0352 if isempty(strmatch('on',get(panel,'Visible')))
0353 set(status,'Visible','on');
0354 else
0355 set(status,'Visible','off');
0356 end
0357
0358 currval = get(slider,'Value');
0359 if currval<0
0360 set(slider,'Value',0);
0361 PopupTabSliderCbk(slider,evdt);
0362 end
0363 titlepos = get(title(1),'Position');
0364 addtolen = titlepos(2)+titlepos(4)+margins(4);
0365
0366 for k=1:ntab
0367 titlepos = get(title(k),'Position');
0368 titlepos(2) = addtolen-titlepos(4)-margins(4);
0369 set(title(k),'Position',titlepos);
0370 addtolen = titlepos(2);
0371 visible = strcmp(get(panel(k),'Visible'),'on');
0372 if visible
0373 panelpos = get(panel(k),'Position');
0374 addtolen = addtolen-panelpos(4);
0375 panelpos(2) = addtolen;
0376 set(panel(k),'Position',panelpos);
0377 end
0378 end
0379
0380 if visible
0381 botpos = get(panel(ntab),'Position');
0382 else
0383 botpos = get(title(ntab),'Position');
0384 end
0385
0386 visible = strcmp(get(slider,'Visible'),'on');
0387 addwidth = (-1)^(~visible);
0388 if botpos(2)*addwidth>0
0389 if visible
0390 set(slider,'Visible','off');
0391 else
0392 set(slider,'Visible','on');
0393 end
0394 else
0395 if visible
0396 addwidth = 0;
0397 else
0398 return;
0399 end
0400 end
0401
0402 addwidth = addwidth*sliderpos(3);
0403 for k=1:ntab
0404 titlepos = get(title(k),'Position');
0405 titlepos(3) = titlepos(3)+addwidth;
0406 set(title(k),'Position',titlepos);
0407 set(title(k),'UserData',titlepos(2));
0408
0409 panelpos = get(panel(k),'Position');
0410 panelpos(3) = panelpos(3)+addwidth;
0411 set(panel(k),'Position',panelpos);
0412 set(panel(k),'UserData',panelpos(2));
0413 end
0414
0415 toplen = botpos(2)-margins(2);
0416 if toplen>0
0417 set(slider,'Value',0);
0418 return;
0419 end
0420
0421 try
0422 if indxvis
0423 viewpos = get(panel(indx),'Position');
0424 if viewpos(2)-viewpos(4)<0
0425 if viewpos(4)+margins(4)<=tabpos(4);
0426 currval = min(0,viewpos(2)-margins(4)/2);
0427 else
0428 viewpos = get(title(indx),'Position');
0429 currval = viewpos(2)+viewpos(4)+margins(4)/2-tabpos(4);
0430 end
0431 end
0432 end
0433 catch
0434 end
0435
0436 set(slider,'Min',toplen);
0437 set(slider,'Value',max(currval,toplen));
0438 set(slider,'SliderStep',[0.3,1]/max(1,-toplen/100));
0439 PopupTabSliderCbk(slider,evdt);
0440
0441 end
0442
0443
0444
0445 function PopupTabSliderCbk(hobj,evdt)
0446
0447 currval = get(hobj,'Value');
0448 for k=1:ntab
0449 titlepos = get(title(k),'Position');
0450 titlepos(2) = get(title(k),'UserData')-currval;
0451 set(title(k),'Position',titlepos);
0452 panelpos = get(panel(k),'Position');
0453 panelpos(2) = get(panel(k),'UserData')-currval;
0454 set(panel(k),'Position',panelpos);
0455 end
0456
0457 end
0458
0459
0460
0461 function PopupTabEnableAllCbk(hobj,evdt,cstr)
0462
0463 set(panel,'Visible',cstr);
0464 PopupTabCbk(hobj,evdt,0);
0465
0466 end
0467
0468
0469
0470 function PopupTabResizeCbk(hobj,evdt)
0471
0472 oldpos = tabpos;
0473 units = get(htab,'Units');
0474 set(htab,'Units','pixels');
0475 tabpos = get(htab,'Position');
0476 set(htab,'Units',units);
0477
0478 addtopos = tabpos-oldpos;
0479 sliderpos([1,2,4]) = sliderpos([1,2,4])+addtopos([1,2,4]);
0480 set(slider,'Position',sliderpos);
0481
0482 addtopos = [tabpos(3:4)-oldpos(3:4),0,0];
0483 currval = get(slider,'Value');
0484 if currval<0
0485 set(slider,'Value',0);
0486 PopupTabSliderCbk(slider,evdt);
0487 end
0488
0489 for k=1:ntab
0490 titlepos = get(title(k),'Position');
0491 set(title(k),'Position',titlepos+addtopos);
0492 end
0493 PopupTabCbk(title(1),evdt,0);
0494
0495 visible = strcmp(get(slider,'Visible'),'on');
0496 if visible & currval<0
0497 set(slider,'Value',max(currval,get(slider,'Min')));
0498 PopupTabSliderCbk(slider,evdt);
0499 end
0500
0501 end
0502
0503
0504
0505
0506
0507 function TopBottomTabCbk(hobj,evdt,indx)
0508
0509 if active==indx, return; end
0510
0511
0512 n = active;
0513 titlepos = get(title(n),'Position');
0514 titlepos = titlepos+addtitle.*[n==sign(1),1,n==sign(1),1];
0515 titlepos(3) = titlepos(3)+addtitle(3)*(n==sign(2));
0516 set(title(n),'Position',titlepos,'BackgroundColor',titlebackgroundcolor);
0517 set(ttext(n),'FontWeight','normal','BackgroundColor',titlebackgroundcolor);
0518 set(panel(n),'Visible','off');
0519
0520
0521 active = indx;
0522 titlepos = get(title(indx),'Position');
0523 titlepos = titlepos-addtitle.*[indx==sign(1),1,indx==sign(1),1];
0524 titlepos(3) = titlepos(3)-addtitle(3)*(indx==sign(2));
0525
0526 set(title(indx),'Position',titlepos,'BackgroundColor',panelbackgroundcolor);
0527 set(ttext(indx),'FontWeight','bold','BackgroundColor',panelbackgroundcolor);
0528 insetpos = [titlepos(1)+1,titlepos(2)+sign(4)*titlepos(4)-2,titlepos(3)-1,3];
0529 set(inset(1),'Position',insetpos);
0530 try
0531 insetpos = insetpos+[0,(1-2*sign(4))*titleheight+2*sign(4),0,-2];
0532 set(inset(2),'Position',insetpos);
0533 set(inset(3),'Position',insetpos+[2,1-2*sign(4),-4,0]);
0534 catch
0535 end
0536 set(panel(indx),'Visible','on');
0537
0538 if isappdata(htab,'SelectionChangeFcn')
0539 SelectionChangeFcn = getappdata(htab,'SelectionChangeFcn');
0540 eventdata = struct('EventName','SelectionChanged', ...
0541 'OldValue',n,'NewValue',indx,'Panels',panel,'Status',status);
0542 if iscell(SelectionChangeFcn)
0543 SelectionChangeFcn{1}(hobj,eventdata,SelectionChangeFcn{2:end});
0544 else
0545 SelectionChangeFcn(hobj,eventdata);
0546 end
0547 end
0548
0549 end
0550
0551
0552
0553 function TopBottomTabResizeCbk(hobj,evdt)
0554
0555 units = get(htab,'Units');
0556 set(htab,'Units','pixels');
0557 tabpos = get(htab,'Position');
0558 set(htab,'Units',units);
0559
0560 titlepos = [0,0,0,titleheight];
0561 if sign(4)
0562 panelpos = [0,titleheight+1,tabpos(3),tabpos(4)-titleheight]+margins;
0563 titlepos(2) = panelpos(2)-titlepos(4);
0564 else
0565 panelpos = [0,0,tabpos(3),tabpos(4)-titleheight]+margins;
0566 titlepos(2) = panelpos(2)+panelpos(4);
0567 end
0568 set(panel,'Position',panelpos);
0569
0570 n = sum(cellfun('length',string))+2*ntab;
0571 if type<6
0572 if (n+2*ntab)*1.2*charsz(3)+2>panelpos(3)
0573 [loop,sign(1:3)] = deal(1:ntab,[1,ntab,1]);
0574 else
0575 if type==2 | type==4
0576 [loop,sign(1:3)] = deal(1:ntab,[1,0,1]);
0577 else
0578 [loop,sign(1:3)] = deal(ntab:-1:1,[ntab,0,0]);
0579 end
0580 end
0581 addtitle = 2*[sign(3:4),-1,-1];
0582 end
0583 titlepos(1) = panelpos(1)+(1-sign(3))*panelpos(3);
0584 for k=loop
0585 if sign(2)
0586 titlepos(3) = panelpos(3)*(length(string{k})+2)/n;
0587 addtopos = addtitle.*[k==1,1,k==1|k==ntab,1];
0588 else
0589 titlepos(3) = (length(string{k})+4)*1.2*charsz(3);
0590 addtopos = addtitle.*[k==sign(1),1,k==sign(1),1];
0591 end
0592 titlepos(1) = titlepos(1)-(1-sign(3))*titlepos(3);
0593 set(title(k),'Position',titlepos+addtopos);
0594 titlepos(1) = titlepos(1)+sign(3)*titlepos(3);
0595 end
0596
0597 statuspos = titlepos;
0598 statuspos(1) = sign(3)*titlepos(1)+2;
0599 statuspos(3) = titlepos(1)+sign(3)*(tabpos(3)-2*titlepos(1))-4;
0600
0601 titlepos = get(title(active),'Position');
0602 titlepos = titlepos-addtitle.*[active==sign(1),1,active==sign(1),1];
0603 titlepos(3) = titlepos(3)-addtitle(3)*(active==sign(2));
0604 set(title(active),'Position',titlepos,'BackgroundColor',panelbackgroundcolor);
0605 set(ttext(active),'FontWeight','bold','BackgroundColor',panelbackgroundcolor);
0606
0607 insetpos = [titlepos(1)+1,titlepos(2)+sign(4)*titlepos(4)-2,titlepos(3)-1,3];
0608 set(inset(1),'Position',insetpos);
0609 try
0610 insetpos = insetpos+[0,(1-2*sign(4))*titleheight+2*sign(4),0,-2];
0611 set(inset(2),'Position',insetpos);
0612 set(inset(3),'Position',insetpos+[2,1-2*sign(4),-4,0]);
0613 catch
0614 end
0615 try
0616
0617 set(status,'Position',statuspos,'Visible','on');
0618 catch
0619 set(status,'Visible','off');
0620 end
0621
0622 end
0623
0624 end