/ Check-in [b1a9e291]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:In the command-line shell, change the units on the ".width" directive from bytes to characters.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | cli-char-width
Files: files | file ages | folders
SHA1: b1a9e2916f5b4adef91c34563f71b98e79a10c12
User & Date: drh 2015-02-26 14:27:16
Original Comment: In the command-line shell, change the units on the ".width" separate from bytes to characters.
Context
2015-02-26
14:27
In the command-line shell, change the units on the ".width" directive from bytes to characters. Leaf check-in: b1a9e291 user: drh tags: cli-char-width
02:33
Simplifications to the description of the nByte parameter to sqlite3_prepare() and friends. check-in: 4bee8295 user: drh tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/shell.c.

   783    783   static void interrupt_handler(int NotUsed){
   784    784     UNUSED_PARAMETER(NotUsed);
   785    785     seenInterrupt++;
   786    786     if( seenInterrupt>2 ) exit(1);
   787    787     if( db ) sqlite3_interrupt(db);
   788    788   }
   789    789   #endif
          790  +
          791  +/*
          792  +** Return the length of a string in characters.  Multibyte UTF8 characters
          793  +** count as a single character.
          794  +*/
          795  +static int strlenChar(const char *z){
          796  +  int n = 0;
          797  +  while( *z ){
          798  +    if( (0xc0&*(z++))!=0x80 ) n++;
          799  +  }
          800  +  return n;
          801  +}
          802  +
          803  +/*
          804  +** Print abs(w) characters of string "z" on FILE "out".
          805  +**
          806  +** w is in units of characters, not bytes!
          807  +**
          808  +** The output is always exactly abs(w) characters wide.  If z contains
          809  +** more than abs(w) characters, it is truncated.  If z contains fewer
          810  +** than abs(w) characters it is padded with spaces.  Spaces are added
          811  +** on the right if w>0 (left justification) or on the left if w<0
          812  +** (right justification).
          813  +*/
          814  +static void outputFixedWidth(FILE *out, int w, const char *z){
          815  +  int n = strlenChar(z);
          816  +  int absw = w<0 ? -w : w;
          817  +  int i;
          818  +
          819  +  if( n<=absw ){
          820  +    if( w<0 ) for(i=absw-n; i>0; i--) putc(' ', out);
          821  +    fputs(z, out);
          822  +    if( w>0 ) for(i=absw-n; i>0; i--) putc(' ', out);
          823  +  }else{
          824  +    for(i=n=0; z[i]; i++){
          825  +      if( (z[i]&0xc0)==0x80 ) continue;
          826  +      if( n==absw ) break;
          827  +      n++;
          828  +    }
          829  +    fwrite(z, 1, i, out);
          830  +  }
          831  +}
   790    832   
   791    833   /*
   792    834   ** This is the callback routine that the shell
   793    835   ** invokes for each row of a query result.
   794    836   */
   795    837   static int shell_callback(
   796    838     void *pArg,
................................................................................
   824    866             int w, n;
   825    867             if( i<ArraySize(p->colWidth) ){
   826    868               w = p->colWidth[i];
   827    869             }else{
   828    870               w = 0;
   829    871             }
   830    872             if( w==0 ){
   831         -            w = strlen30(azCol[i] ? azCol[i] : "");
          873  +            w = strlenChar(azCol[i] ? azCol[i] : "");
   832    874               if( w<10 ) w = 10;
   833         -            n = strlen30(azArg && azArg[i] ? azArg[i] : p->nullValue);
          875  +            n = strlenChar(azArg && azArg[i] ? azArg[i] : p->nullValue);
   834    876               if( w<n ) w = n;
   835    877             }
   836    878             if( i<ArraySize(p->actualWidth) ){
   837    879               p->actualWidth[i] = w;
   838    880             }
   839    881             if( p->showHeader ){
   840         -            if( w<0 ){
   841         -              fprintf(p->out,"%*.*s%s",-w,-w,azCol[i],
   842         -                      i==nArg-1 ? p->rowSeparator : "  ");
   843         -            }else{
   844         -              fprintf(p->out,"%-*.*s%s",w,w,azCol[i],
   845         -                      i==nArg-1 ? p->rowSeparator : "  ");
   846         -            }
          882  +            outputFixedWidth(p->out, w, azCol[i]);
          883  +            fprintf(p->out, "%s", i==nArg-1 ? p->rowSeparator : "  ");
   847    884             }
   848    885           }
   849    886           if( p->showHeader ){
   850    887             for(i=0; i<nArg; i++){
   851    888               int w;
   852    889               if( i<ArraySize(p->actualWidth) ){
   853    890                  w = p->actualWidth[i];
................................................................................
   866    903           int w;
   867    904           if( i<ArraySize(p->actualWidth) ){
   868    905              w = p->actualWidth[i];
   869    906           }else{
   870    907              w = 10;
   871    908           }
   872    909           if( p->mode==MODE_Explain && azArg[i] && strlen30(azArg[i])>w ){
   873         -          w = strlen30(azArg[i]);
          910  +          w = strlenChar(azArg[i]);
   874    911           }
   875    912           if( i==1 && p->aiIndent && p->pStmt ){
   876    913             if( p->iIndent<p->nIndent ){
   877    914               fprintf(p->out, "%*.s", p->aiIndent[p->iIndent], "");
   878    915             }
   879    916             p->iIndent++;
   880    917           }
   881         -        if( w<0 ){
   882         -          fprintf(p->out,"%*.*s%s",-w,-w,
   883         -              azArg[i] ? azArg[i] : p->nullValue,
   884         -              i==nArg-1 ? p->rowSeparator : "  ");
   885         -        }else{
   886         -          fprintf(p->out,"%-*.*s%s",w,w,
   887         -              azArg[i] ? azArg[i] : p->nullValue,
   888         -              i==nArg-1 ? p->rowSeparator : "  ");
   889         -        }
          918  +        outputFixedWidth(p->out, w, azArg[i] ? azArg[i] : p->nullValue);
          919  +        fprintf(p->out, "%s", i==nArg-1 ? p->rowSeparator : "  ");
   890    920         }
   891    921         break;
   892    922       }
   893    923       case MODE_Semi:
   894    924       case MODE_List: {
   895    925         if( p->cnt++==0 && p->showHeader ){
   896    926           for(i=0; i<nArg; i++){