U8 *Tabs2Spaces(U8 *src) {//MAlloc str with tabs to spaces. I64 ch,i,j,l=StrLen(src)<<1+2,col=0; U8 *dst=MAlloc(l),*tmp; while (ch=*src++) { if (ch=='\t') { j=(col+8) & ~7; for (i=col; i<j; i++) { dst[i]=CH_SPACE; if (i>=l-2) { tmp=MAlloc(l<<1); MemCpy(tmp,dst,i+1); Free(dst); l<<=1; dst=tmp; } } col=j; } else { dst[col]=ch; if (col>=l-2) { tmp=MAlloc(l<<1); MemCpy(tmp,dst,col+1); Free(dst); l<<=1; dst=tmp; } col++; } } dst[col]=0; return dst; } U8 *ScaleIndent(U8 *src,F64 indent_scale_factor) {//MAlloced str. 8*0.25-->2 or 8*2.0-->16 I64 ch,i,col=0; U8 *dst,*dst2; while (ch=*src++) { if (ch=='\t') col=(col+8) & -0x8; else if (ch==CH_SPACE) col++; else break; } src--; col=Round(indent_scale_factor*col); dst=dst2=MAlloc(StrLen(src)+col/8+col&7+1); for (i=col/8; i>0; i--) *dst2++='\t'; for (i=col&7; i>0; i--) *dst2++=CH_SPACE; StrCpy(dst2,src); return dst; } U8 *MStrUtil(U8 *src,I64 flags,F64 indent_scale_factor=0) {//MAlloc StrUtil(). U8 *dst=StrNew(src),*dst2,*tmp; StrUtil(dst,flags); if (flags & SUF_T2S) { tmp=Tabs2Spaces(dst); Free(dst); dst=tmp; } if (flags & SUF_SCALE_INDENT) dst2=ScaleIndent(dst,indent_scale_factor); else dst2=StrNew(dst); //Shorten to just right size. Free(dst); return dst2; } U0 GetOutOfDollar() {//If a $ has been printed, print another $ to exit mode. CDoc *doc; if (IsRaw) { if (text.raw_flags&RWF_IN_DOLLAR) '$'; } else { if (fp_doc_put && (doc=(*fp_doc_put)(Fs)) && doc->flags&DOCF_IN_DOLLAR) '$'; } } I64 PressAKey() {//Print "Press a key" and wait for non-zero ASCII key. "$BK,1$PRESS A KEY$BK,0$\n"; return GetChar(,FALSE); } U0 Help() {//Dbg help or master help index file. if (IsDbgMode) DbgHelp; else PopUp("Type(\"::/Doc/HelpIndex.DD\");DocTop;View;"); } U0 ScanFlags(U8 *_dst_flags,U8 *lst,U8 *src) { /*More than 64 flags. Flags passed by ref. Examples: ScanFlags(&fuf_flags,Define("ST_FILE_UTIL_FLAGS"),fu_flags); I64 flags=0; ScanFlags(&flags,"R\0L\0Dump\0Scan\0","+Dump-R"); //Sets Bit#2, Clears Bit#0. */ I64 i; U8 *buf,*ptr; if (src) { buf=MAlloc(StrLen(src)+1); while (*src) { while (*src && *src!='+' && *src!='-') src++; if (*src=='+') { src++; if (*src) { ptr=buf; while (*src && *src!='+' && *src!='-' && *src!=CH_SPACE && *src!=CH_SHIFT_SPACE) *ptr++=*src++; *ptr=0; i=LstMatch(buf,lst); if (i>=0) LBts(_dst_flags,i); else { Free(buf); throw('ScanFlag'); } } } else if (*src=='-') { src++; if (*src) { ptr=buf; while (*src && *src!='+' && *src!='-' && *src!=CH_SPACE && *src!=CH_SHIFT_SPACE) *ptr++=*src++; *ptr=0; i=LstMatch(buf,lst); if (i>=0) LBtr(_dst_flags,i); else { Free(buf); throw('ScanFlag'); } } } } Free(buf); } } U8 *StrPrintFlags(U8 *dst,U8 *lst,I64 flags, Bool print_all=FALSE, I64 print_all_length=0) {//Only 64 flags. Flags passed by value. print_all will print false flags using `-`. //Specify print_all_length (list length) if print_all is true. I64 i=0; *dst=0; if (!print_all_length) print_all_length = 64; while (i < print_all_length) { if (Bt(&flags, i)) CatPrint(dst, "+%z", i, lst); else if (print_all) CatPrint(dst, "-%z", i, lst); i++; } return dst; }