Ruler reset for notebooks
patg
27 Aug 2011: Updated to accommodate notebooks as subwindows. Igor packs the winrecreation data in a private format, which is base-85 encoded at the recreation level, but some compression? binary under that. In any case recreating the notebook as a standalone temporarily allows the usual winRecreation data to be extracted, and the ruler reset then proceeds in the old way.
Thanks to Ulrich Froebe for pointing this out and his patience while I stumbled a bit getting it to work.
//====================================================================================================================================
// ResetRuler
// ----------
// * SUMMARY: 'ResetRuler' resets all of the settable parameters in a notebook to the original settings determined at the time
// of the original creation of the ruler. This is useful because subsequent changes in settings are added on top
// of the ruler's defaults, and do not get reset when a line such as:
//
// notebook notebook0,ruler="Normal"
//
// is executed. This function allows all settings to be returned to the original ruler's defaults, including the
// vOffset, textRGB, font, margins, justification, tabs, fStyle, fSize, and spacing commands. The command also
// sets the 'ruler' as the current ruler for the notebook, and can therefore be used as the ruler command for
// programatic notebook creation, setting the conditions back to a known state, without the programmer needing
// to know anything about the ruler being set (except its name...).
//
// * ARGUMENTS:
// - nb: Notebook to set ruler defaults. An error is raised if the notebook does not exist. If the notebook is
// a subwindow the full '#' separated window path should be passed.
//
// - ruler: Name of the ruler to set. An error is raised if the ruler does not exist for the named notebook.
//
// - [instance]: Optional variable. Use this instance of the notebook name (only useful if there is more than one subwindow
// with an embedded notebook, whence more than one notebook can legally have the same name).
// Zero based for the first notebook created. Default 0.
//
// - [errMsg]: Optional pass-by-reference string to receive error message. If present the function will not abort.
//
// * RETURNS: V_AbortCode (zero for no error).
//
// * ON ERROR:
// If 'errMsg' is passed: sets 'errMsg'=<error string>, returns V_AbortCode. ('errMsg' is "" for no error.)
// If 'errMsg' is not a parameter: aborts with error message.
//
// * SOURCE: Patrick Groenestein, 2010
//
// * UPDATES: 20110515 Created from PG61_NotebookUtils.
// 20110821 Added support for notebooks in subwindows.
//
//------------------------------+---------------------------------------------------------------+-------------------------------------
FUNCTION ResetRuler(nb,ruler [,instance,errMsg])
variable instance;
string nb,ruler,&errMsg;
variable err,i,n,pos,len;
variable isSW=itemsInList(nb,"#")-1;
string s0,nbStr,cmd,rgb,nbRef,zd;
TRY
if( !strlen(ruler))
ruler = "Normal";
endif;
if( !strlen(nb))
nb = winName(0,16); abortOnValue !strlen(nb),5;
isSW = 0;
endif;
abortOnValue !winType(nb),6;
if(isSW)
nbStr = winRecreation(stringFromList(0,nb,"#"),0); abortOnRTE;
nbRef = stringFromList(isSW,nb,"#");
for(i=0,cmd="",n=itemsInList(nbStr,"\r") ; i<n ; i+=1)
s0 = stringFromList(i,nbStr,"\r")
if(stringMatch(s0,"\tNewNotebook *") && strSearch(s0,"/N="+nbRef+" ",0,2)>=0)
if(instance>0)
instance -= 1;
else
// Found the required notebook; extract its data into 'cmd', minus the 'NewNotebook' line
//
for(i+=1,s0=stringFromList(i,nbStr,"\r") ; stringMatch(s0,"\tNotebook *") ; i+=1,s0=stringFromList(i,nbStr,"\r"))
cmd += s0+"\r";
endfor;
// Could use UniqueName here
//
for(i=0,zd="PG62_NBTmp_0" ; winType(zd) ; i+=1,zd="PG62_NBTmp_"+num2iStr(i))
endfor;
// Create an invisible, temporary, stand-alone notebook to extract commands from
// Needs the loop to avoid command buffer overflow
//
cmd[0] = "newNotebook/V=0/F=1/N="+zd+"\r";
for(i=0,n=itemsInList(cmd,"\r") ; i<n ; i+=1)
s0 = stringFromList(i,cmd,"\r");
s0 = replaceString("kwTopWin",s0,zd,0,1);
execute/Z/Q s0; abortOnRTE; abortOnValue V_Flag,2;
endfor;
// Extract the 'winRecreation()', now free of 'zdata' lines
//
cmd = winRecreation(zd,0);
doWindow/K $zd;
break;
endif;
endif;
endfor;
nbStr = cmd;
cmd = "";
else
nbStr = winRecreation(nb,0); abortOnRTE; // Normal standalone notebook
endif;
nbRef = "$nb";
nbStr = stringFromList(0,listMatch(nbStr,"\tNotebook "+nbRef+" newRuler="+ruler+", *","\r"),"\r"); abortOnValue !strlen(nbStr),3;
nbStr = replaceString("newRuler=",replaceString(nbRef,nbStr,nb,0,1),"ruler=",0,1);
pos = strSearch(nbStr,"rulerDefaults=",0,2); abortOnValue pos<0,4;
len = strlen(nbStr)-1;
cmd = nbStr[pos,len];
nbStr[pos,len] = "";
pos -= 1;
nbStr[pos,pos] = ""; // trailing space
nbStr[0,0] = ""; // leading tab
sscanf cmd,"rulerDefaults={\"%*[^\"]\",%*d,%*d,(%[^)])",rgb; abortOnRTE;
notebook $nb,Ruler=$ruler,vOffset=0,font="default",fSize= -1,fStyle= -1; abortOnRTE;
execute/Q/Z nbStr+"textRGB=("+rgb+")"; abortOnValue V_Flag,2;
abortOnRTE;
CATCH
variable ev;
string es="";
if(V_AbortCode<0)
es = getRTErrMessage();
ev = getRTError(1);
elseif(V_AbortCode>1)
es = "Error 0. {BUG}\n"; // V_AbortCode 0 (not used)
es += "Error 1. {BUG}\n"; // V_AbortCode 1 (error passing up the line)
es += "Igor error: {"+GetErrMessage(V_Flag,2)+"}.\n"; // V_AbortCode 2
es += "Cannot find 'newRuler' command for the ruler \""+ruler+"\".\n"; // V_AbortCode 3
es += "Cannot find 'rulerDefaults' command for the ruler \""+ruler+"\".\n"; // V_AbortCode 4
es += "No notebook windows found.\n"; // V_AbortCode 5
es += "Notebook window '"+nb+"' not found.\n"; // V_AbortCode 6
es += "<Undocumented error> {BUG}\n"; // V_AbortCode <undocumented>
ev = min(V_AbortCode,itemsInList(es,"\n")-1);
es = stringFromList(ev,es,"\n");
endif;
ENDTRY;
// Add cleanup here
// <none>
if(V_AbortCode)
// This function's error: set the error environment for this error.
// Otherwise just pass the error received from some other function back up the line.
//
es[0] = getRTStackInfo(1)+" error <"+num2iStr(V_AbortCode)+">: ";
if(paramIsDefault(errMsg))
variable/G V_Error=V_AbortCode;
string/G S_Error=es;
print es;
abort es;
else
errMsg = es;
endif;
endif;
return(V_AbortCode);
END
// ResetRuler
// ----------
// * SUMMARY: 'ResetRuler' resets all of the settable parameters in a notebook to the original settings determined at the time
// of the original creation of the ruler. This is useful because subsequent changes in settings are added on top
// of the ruler's defaults, and do not get reset when a line such as:
//
// notebook notebook0,ruler="Normal"
//
// is executed. This function allows all settings to be returned to the original ruler's defaults, including the
// vOffset, textRGB, font, margins, justification, tabs, fStyle, fSize, and spacing commands. The command also
// sets the 'ruler' as the current ruler for the notebook, and can therefore be used as the ruler command for
// programatic notebook creation, setting the conditions back to a known state, without the programmer needing
// to know anything about the ruler being set (except its name...).
//
// * ARGUMENTS:
// - nb: Notebook to set ruler defaults. An error is raised if the notebook does not exist. If the notebook is
// a subwindow the full '#' separated window path should be passed.
//
// - ruler: Name of the ruler to set. An error is raised if the ruler does not exist for the named notebook.
//
// - [instance]: Optional variable. Use this instance of the notebook name (only useful if there is more than one subwindow
// with an embedded notebook, whence more than one notebook can legally have the same name).
// Zero based for the first notebook created. Default 0.
//
// - [errMsg]: Optional pass-by-reference string to receive error message. If present the function will not abort.
//
// * RETURNS: V_AbortCode (zero for no error).
//
// * ON ERROR:
// If 'errMsg' is passed: sets 'errMsg'=<error string>, returns V_AbortCode. ('errMsg' is "" for no error.)
// If 'errMsg' is not a parameter: aborts with error message.
//
// * SOURCE: Patrick Groenestein, 2010
//
// * UPDATES: 20110515 Created from PG61_NotebookUtils.
// 20110821 Added support for notebooks in subwindows.
//
//------------------------------+---------------------------------------------------------------+-------------------------------------
FUNCTION ResetRuler(nb,ruler [,instance,errMsg])
variable instance;
string nb,ruler,&errMsg;
variable err,i,n,pos,len;
variable isSW=itemsInList(nb,"#")-1;
string s0,nbStr,cmd,rgb,nbRef,zd;
TRY
if( !strlen(ruler))
ruler = "Normal";
endif;
if( !strlen(nb))
nb = winName(0,16); abortOnValue !strlen(nb),5;
isSW = 0;
endif;
abortOnValue !winType(nb),6;
if(isSW)
nbStr = winRecreation(stringFromList(0,nb,"#"),0); abortOnRTE;
nbRef = stringFromList(isSW,nb,"#");
for(i=0,cmd="",n=itemsInList(nbStr,"\r") ; i<n ; i+=1)
s0 = stringFromList(i,nbStr,"\r")
if(stringMatch(s0,"\tNewNotebook *") && strSearch(s0,"/N="+nbRef+" ",0,2)>=0)
if(instance>0)
instance -= 1;
else
// Found the required notebook; extract its data into 'cmd', minus the 'NewNotebook' line
//
for(i+=1,s0=stringFromList(i,nbStr,"\r") ; stringMatch(s0,"\tNotebook *") ; i+=1,s0=stringFromList(i,nbStr,"\r"))
cmd += s0+"\r";
endfor;
// Could use UniqueName here
//
for(i=0,zd="PG62_NBTmp_0" ; winType(zd) ; i+=1,zd="PG62_NBTmp_"+num2iStr(i))
endfor;
// Create an invisible, temporary, stand-alone notebook to extract commands from
// Needs the loop to avoid command buffer overflow
//
cmd[0] = "newNotebook/V=0/F=1/N="+zd+"\r";
for(i=0,n=itemsInList(cmd,"\r") ; i<n ; i+=1)
s0 = stringFromList(i,cmd,"\r");
s0 = replaceString("kwTopWin",s0,zd,0,1);
execute/Z/Q s0; abortOnRTE; abortOnValue V_Flag,2;
endfor;
// Extract the 'winRecreation()', now free of 'zdata' lines
//
cmd = winRecreation(zd,0);
doWindow/K $zd;
break;
endif;
endif;
endfor;
nbStr = cmd;
cmd = "";
else
nbStr = winRecreation(nb,0); abortOnRTE; // Normal standalone notebook
endif;
nbRef = "$nb";
nbStr = stringFromList(0,listMatch(nbStr,"\tNotebook "+nbRef+" newRuler="+ruler+", *","\r"),"\r"); abortOnValue !strlen(nbStr),3;
nbStr = replaceString("newRuler=",replaceString(nbRef,nbStr,nb,0,1),"ruler=",0,1);
pos = strSearch(nbStr,"rulerDefaults=",0,2); abortOnValue pos<0,4;
len = strlen(nbStr)-1;
cmd = nbStr[pos,len];
nbStr[pos,len] = "";
pos -= 1;
nbStr[pos,pos] = ""; // trailing space
nbStr[0,0] = ""; // leading tab
sscanf cmd,"rulerDefaults={\"%*[^\"]\",%*d,%*d,(%[^)])",rgb; abortOnRTE;
notebook $nb,Ruler=$ruler,vOffset=0,font="default",fSize= -1,fStyle= -1; abortOnRTE;
execute/Q/Z nbStr+"textRGB=("+rgb+")"; abortOnValue V_Flag,2;
abortOnRTE;
CATCH
variable ev;
string es="";
if(V_AbortCode<0)
es = getRTErrMessage();
ev = getRTError(1);
elseif(V_AbortCode>1)
es = "Error 0. {BUG}\n"; // V_AbortCode 0 (not used)
es += "Error 1. {BUG}\n"; // V_AbortCode 1 (error passing up the line)
es += "Igor error: {"+GetErrMessage(V_Flag,2)+"}.\n"; // V_AbortCode 2
es += "Cannot find 'newRuler' command for the ruler \""+ruler+"\".\n"; // V_AbortCode 3
es += "Cannot find 'rulerDefaults' command for the ruler \""+ruler+"\".\n"; // V_AbortCode 4
es += "No notebook windows found.\n"; // V_AbortCode 5
es += "Notebook window '"+nb+"' not found.\n"; // V_AbortCode 6
es += "<Undocumented error> {BUG}\n"; // V_AbortCode <undocumented>
ev = min(V_AbortCode,itemsInList(es,"\n")-1);
es = stringFromList(ev,es,"\n");
endif;
ENDTRY;
// Add cleanup here
// <none>
if(V_AbortCode)
// This function's error: set the error environment for this error.
// Otherwise just pass the error received from some other function back up the line.
//
es[0] = getRTStackInfo(1)+" error <"+num2iStr(V_AbortCode)+">: ";
if(paramIsDefault(errMsg))
variable/G V_Error=V_AbortCode;
string/G S_Error=es;
print es;
abort es;
else
errMsg = es;
endif;
endif;
return(V_AbortCode);
END
Forum
Support
Gallery
Igor Pro 9
Learn More
Igor XOP Toolkit
Learn More
Igor NIDAQ Tools MX
Learn More
August 27, 2011 at 12:17 am - Permalink