source: editwin.c @ ed2412d

barnowl_perlaimdebianowlrelease-1.10release-1.4release-1.5release-1.6release-1.7release-1.8release-1.9
Last change on this file since ed2412d was 060b3b4, checked in by James M. Kretchmar <kretch@mit.edu>, 22 years ago
Fixed bug in unsub command that could cause file corruption.
  • Property mode set to 100644
File size: 20.4 KB
Line 
1#include "owl.h"
2#include <stdlib.h>
3#include <unistd.h>
4#include <string.h>
5#include <ctype.h>
6
7static const char fileIdent[] = "$Id$";
8
9#define INCR 5000
10
11void owl_editwin_init(owl_editwin *e, WINDOW *win, int winlines, int wincols, int style, owl_history *hist) {
12  /* initialize the editwin e.
13   * 'win' is an already initialzed curses window that will be used by editwin
14   */
15  e->buff=owl_malloc(INCR); 
16  e->buff[0]='\0';
17  e->bufflen=0;
18  e->hist=hist;
19  e->allocated=INCR;
20  e->buffx=0;
21  e->buffy=0;
22  e->topline=0;
23  e->winlines=winlines;
24  e->wincols=wincols;
25  e->fillcol=owl_editwin_limit_maxcols(wincols-1, 
26                                       owl_global_get_edit_maxfillcols(&g));
27  e->wrapcol=owl_editwin_limit_maxcols(wincols-1, 
28                                       owl_global_get_edit_maxwrapcols(&g));
29  e->curswin=win;
30  e->style=style;
31  if ((style!=OWL_EDITWIN_STYLE_MULTILINE) &&
32      (style!=OWL_EDITWIN_STYLE_ONELINE)) {
33    e->style=OWL_EDITWIN_STYLE_MULTILINE;
34  }
35  e->lock=0;
36  e->dotsend=0;
37  if (win) werase(win);
38}
39
40void owl_editwin_set_curswin(owl_editwin *e, WINDOW *w, int winlines, int wincols) {
41  e->curswin=w;
42  e->winlines=winlines;
43  e->wincols=wincols;
44  e->fillcol=owl_editwin_limit_maxcols(wincols-1, 
45                                       owl_global_get_edit_maxfillcols(&g));
46  e->wrapcol=owl_editwin_limit_maxcols(wincols-1, 
47                                       owl_global_get_edit_maxwrapcols(&g));
48}
49
50WINDOW *owl_editwin_get_curswin(owl_editwin *e) {
51  return(e->curswin);
52}
53
54void owl_editwin_set_history(owl_editwin *e, owl_history *h) {
55  e->hist=h;
56}
57
58owl_history *owl_editwin_get_history(owl_editwin *e) {
59  return(e->hist);
60}
61
62void owl_editwin_set_dotsend(owl_editwin *e) {
63  e->dotsend=1;
64}
65
66int owl_editwin_limit_maxcols(int v, int maxv) {
67  if (maxv > 5 && v > maxv) {
68    return(maxv);
69  } else {
70    return(v);
71  }
72}
73
74void owl_editwin_set_locktext(owl_editwin *e, char *text) {
75  /* set text to be 'locked in' at the beginning of the buffer, any
76     previous text (including locked text) will be overwritten */
77 
78  int x, y;
79
80  x=e->buffx;
81  y=e->buffy;
82  e->buffx=0;
83  e->buffy=0;
84  owl_editwin_overwrite_string(e, text);
85  e->lock=strlen(text);
86  /* if (text[e->lock-1]=='\n') e->lock--; */
87  e->buffx=x;
88  e->buffy=y;
89  owl_editwin_adjust_for_locktext(e);
90  owl_editwin_redisplay(e, 0);
91}
92
93int owl_editwin_get_style(owl_editwin *e) {
94  return(e->style);
95}
96
97void owl_editwin_new_style(owl_editwin *e, int newstyle, owl_history *h) {
98  char *ptr;
99
100  owl_editwin_set_history(e, h);
101  if (e->style==newstyle) return;
102
103  if (newstyle==OWL_EDITWIN_STYLE_MULTILINE) {
104    e->style=newstyle;
105  } else if (newstyle==OWL_EDITWIN_STYLE_ONELINE) {
106    e->style=newstyle;
107
108    /* nuke everything after the first line */
109    if (e->bufflen > 0) {
110      ptr=strchr(e->buff, '\n')-1;
111      if (ptr) {
112        e->bufflen=ptr - e->buff;
113        e->buff[e->bufflen]='\0';
114        e->buffx=0;
115        e->buffy=0;
116      }
117    }
118  }
119}
120
121void owl_editwin_fullclear(owl_editwin *e) {
122  /* completly reinitialize the buffer */
123  owl_free(e->buff);
124  owl_editwin_init(e, e->curswin, e->winlines, e->wincols, e->style, e->hist);
125}
126
127void owl_editwin_clear(owl_editwin *e) {
128  /* clear all text except for locktext and put the cursor at the beginning */
129  int lock;
130  int dotsend=e->dotsend;
131  char *locktext=NULL;
132
133  lock=0;
134  if (e->lock > 0) {
135    lock=1;
136
137    locktext=owl_malloc(e->lock+20);
138    strncpy(locktext, e->buff, e->lock);
139    locktext[e->lock]='\0';
140  }
141
142  owl_free(e->buff);
143  owl_editwin_init(e, e->curswin, e->winlines, e->wincols, e->style, e->hist);
144
145  if (lock > 0) {
146    owl_editwin_set_locktext(e, locktext);
147  }
148  if (dotsend) {
149    owl_editwin_set_dotsend(e);
150  }
151
152  if (locktext) owl_free(locktext);
153  owl_editwin_adjust_for_locktext(e);
154}
155
156
157void _owl_editwin_addspace(owl_editwin *e) {
158  /* malloc more space for the buffer */
159  e->buff=owl_realloc(e->buff, e->allocated+INCR);
160  if (!e->buff) {
161    /* error */
162    return;
163  }
164  e->allocated+=INCR;
165}
166
167void owl_editwin_recenter(owl_editwin *e) {
168  e->topline=e->buffy-(e->winlines/2);
169  if (e->topline<0) e->topline=0;
170  if (e->topline>owl_editwin_get_numlines(e)) e->topline=owl_editwin_get_numlines(e);
171}
172
173void owl_editwin_redisplay(owl_editwin *e, int update) {
174  /* regenerate the text on the curses window */
175  /* if update == 1 then do a doupdate(), otherwise do not */
176 
177  char *ptr1, *ptr2, *ptr3, *buff;
178  int i;
179
180  werase(e->curswin);
181  wmove(e->curswin, 0, 0);
182
183  /* start at topline */
184  ptr1=e->buff;
185  for (i=0; i<e->topline; i++) {
186    ptr2=strchr(ptr1, '\n');
187    if (!ptr2) {
188      /* we're already on the last line */
189      break;
190    }
191    ptr1=ptr2+1;
192  }
193  /* ptr1 now stores the starting point */
194
195  /* find the ending point and store it in ptr3 */
196  ptr2=ptr1;
197  ptr3=ptr1;
198  for (i=0; i<e->winlines; i++) {
199    ptr3=strchr(ptr2, '\n');
200    if (!ptr3) {
201      /* we've hit the last line */
202      /* print everything to the end */
203      ptr3=e->buff+e->bufflen-1;
204      ptr3--;
205      break;
206    }
207    ptr2=ptr3+1;
208  }
209  ptr3+=2;
210
211  buff=owl_malloc(ptr3-ptr1+50);
212  strncpy(buff, ptr1, ptr3-ptr1);
213  buff[ptr3-ptr1]='\0';
214  waddstr(e->curswin, buff);
215  wmove(e->curswin, e->buffy-e->topline, e->buffx);
216  wnoutrefresh(e->curswin);
217  if (update==1) {
218    doupdate();
219  }
220  owl_free(buff);
221}
222
223
224int _owl_editwin_linewrap_word(owl_editwin *e) {
225  /* linewrap the word just before the cursor.
226   * returns 0 on success
227   * returns -1 if we could not wrap.
228   */
229
230  int i, z;
231
232  z=_owl_editwin_get_index_from_xy(e);
233  /* move back and line wrap the previous word */
234  for (i=z-1; ; i--) {
235    /* move back until you find a space or hit the beginning of the line */
236    if (e->buff[i]==' ') {
237      /* replace the space with a newline */
238      e->buff[i]='\n';
239      e->buffy++;
240      e->buffx=z-i-1;
241      /* were we on the last line */
242      return(0);
243    } else if (e->buff[i]=='\n' || i<=e->lock) {
244      /* we hit the begginning of the line or the buffer, we cannot
245       * wrap.
246       */
247      return(-1);
248    }
249  }
250}
251
252void owl_editwin_insert_char(owl_editwin *e, char c) {
253  /* insert a character at the current point (shift later
254   * characters over) */
255 
256  int z, i, ret;
257
258  /* \r is \n */
259  if (c=='\r') {
260    c='\n';
261  }
262
263  if (c=='\n' && e->style==OWL_EDITWIN_STYLE_ONELINE) {
264    /* perhaps later this will change some state that allows the string
265       to be read */
266    return;
267  }
268
269  /* make sure there is enough memory for the new text */
270  if ((e->bufflen+1) > (e->allocated-5)) {
271    _owl_editwin_addspace(e);
272  }
273
274  /* get the insertion point */
275  z=_owl_editwin_get_index_from_xy(e);
276
277  /* If we're going to insert at the last column do word wrapping, unless it's a \n */
278  if ((e->buffx+1==e->wrapcol) && (c!='\n')) {
279    ret=_owl_editwin_linewrap_word(e);
280    if (ret==-1) {
281      /* we couldn't wrap, insert a hard newline instead */
282      owl_editwin_insert_char(e, '\n');
283    }
284  }
285
286  z=_owl_editwin_get_index_from_xy(e);
287  /* shift all the other characters right */
288  for (i=e->bufflen; i>z; i--) {
289    e->buff[i]=e->buff[i-1];
290  }
291
292  /* insert the new one */
293  e->buff[z]=c;
294
295  /* housekeeping */
296  e->bufflen++;
297  e->buff[e->bufflen]='\0';
298
299  /* advance the cursor */
300  if (c=='\n') {
301    e->buffx=0;
302    e->buffy++;
303  } else {
304    e->buffx++;
305  }
306}
307
308void owl_editwin_overwrite_char(owl_editwin *e, char c) {
309  /* overwrite the character at the current point with 'c' */
310  int z;
311 
312  /* \r is \n */
313  if (c=='\r') {
314    c='\n';
315  }
316
317  if (c=='\n' && e->style==OWL_EDITWIN_STYLE_ONELINE) {
318    /* perhaps later this will change some state that allows the string
319       to be read */
320    return;
321  }
322
323  z=_owl_editwin_get_index_from_xy(e);
324
325  /* only if we are at the end of the buffer do we create new space */
326  if (z==e->bufflen) {
327    if ((e->bufflen+1) > (e->allocated-5)) {
328      _owl_editwin_addspace(e);
329    }
330  }
331 
332  e->buff[z]=c;
333
334  /* housekeeping if we are at the end of the buffer */
335  if (z==e->bufflen) {
336    e->bufflen++;
337    e->buff[e->bufflen]='\0';
338  }
339
340  /* advance the cursor */
341  if (c=='\n') {
342    e->buffx=0;
343    e->buffy++;
344  } else {
345    e->buffx++;
346  }
347
348}
349
350void owl_editwin_delete_char(owl_editwin *e) {
351  /* delete the character at the current point, following chars
352   * shift left.
353   */ 
354  int z, i;
355
356  if (e->bufflen==0) return;
357 
358  /* get the deletion point */
359  z=_owl_editwin_get_index_from_xy(e);
360
361  if (z==e->bufflen) return;
362
363  for (i=z; i<e->bufflen; i++) {
364    e->buff[i]=e->buff[i+1];
365  }
366  e->bufflen--;
367  e->buff[e->bufflen]='\0';
368}
369
370void owl_editwin_transpose_chars(owl_editwin *e) {
371  /* Swap the character at point with the character at point-1 and
372   * advance the pointer.  If point is at beginning of buffer do
373   * nothing.  If point is after the last character swap point-1 with
374   * point-2.  (Behaves as observed in tcsh and emacs). 
375   */
376
377  int z;
378  char tmp;
379
380  if (e->bufflen==0) return;
381 
382  /* get the cursor point */
383  z=_owl_editwin_get_index_from_xy(e);
384
385  if (z==e->bufflen) {
386    /* point is after last character */
387    z--;
388  } 
389
390  if (z-1 < e->lock) {
391    /* point is at beginning of buffer, do nothing */
392    return;
393  }
394
395  tmp=e->buff[z];
396  e->buff[z]=e->buff[z-1];
397  e->buff[z-1]=tmp;
398  owl_editwin_key_right(e);
399}
400
401void owl_editwin_insert_string(owl_editwin *e, char *string) {
402  /* insert 'string' at the current point, later text is shifted
403   * right
404   */
405  int i, j;
406
407  j=strlen(string);
408  for (i=0; i<j; i++) {
409    owl_editwin_insert_char(e, string[i]);
410  }
411}
412
413void owl_editwin_overwrite_string(owl_editwin *e, char *string) {
414  int i, j;
415  /* write 'string' at the current point, overwriting text that is
416   * already there
417   */
418
419  j=strlen(string);
420  for (i=0; i<j; i++) {
421    owl_editwin_overwrite_char(e, string[i]);
422  }
423}
424
425int _owl_editwin_get_index_from_xy(owl_editwin *e) {
426  /* get the index into e->buff for the current cursor
427   * position.
428   */
429  int i;
430  char *ptr1, *ptr2;
431
432  if (e->bufflen==0) return(0);
433 
434  /* first go to the yth line */
435  ptr1=e->buff;
436  for (i=0; i<e->buffy; i++) {
437    ptr2=strchr(ptr1, '\n');
438    if (!ptr2) {
439      /* we're already on the last line */
440      break;
441    }
442    ptr1=ptr2+1;
443  }
444
445  /* now go to the xth character */
446  ptr2=strchr(ptr1, '\n');
447  if (!ptr2) {
448    ptr2=e->buff+e->bufflen;
449  }
450
451  if ((ptr2-ptr1) < e->buffx) {
452    ptr1=ptr2-1;
453  } else {
454    ptr1+=e->buffx;
455  }
456
457  /* printf("DEBUG: index is %i\r\n", ptr1-e->buff); */
458  return(ptr1-e->buff);
459}
460
461void _owl_editwin_set_xy_by_index(owl_editwin *e, int index) {
462  int z, i;
463
464  z=_owl_editwin_get_index_from_xy(e);
465  if (index>z) {
466    for (i=0; i<index-z; i++) {
467      owl_editwin_key_right(e);
468    }
469  } else if (index<z) {
470    for (i=0; i<z-index; i++) {
471      owl_editwin_key_left(e);
472    }
473  }
474}
475
476void owl_editwin_adjust_for_locktext(owl_editwin *e) {
477  /* if we happen to have the cursor over locked text
478   * move it to be out of the locktext region */
479  if (_owl_editwin_get_index_from_xy(e)<e->lock) {
480    _owl_editwin_set_xy_by_index(e, e->lock);
481  }
482}
483
484void owl_editwin_backspace(owl_editwin *e) {
485  /* delete the char before the current one
486   * and shift later chars left
487   */
488  if (_owl_editwin_get_index_from_xy(e) > e->lock) {
489    owl_editwin_key_left(e);
490    owl_editwin_delete_char(e);
491  }
492  owl_editwin_adjust_for_locktext(e);
493}
494
495void owl_editwin_key_up(owl_editwin *e) {
496  if (e->buffy > 0) e->buffy--;
497  if (e->buffx >= owl_editwin_get_numchars_on_line(e, e->buffy)) {
498    e->buffx=owl_editwin_get_numchars_on_line(e, e->buffy);
499  }
500
501  /* do we need to scroll? */
502  if (e->buffy-e->topline < 0) {
503    e->topline-=e->winlines/2;
504  }
505
506  owl_editwin_adjust_for_locktext(e);
507}
508
509void owl_editwin_key_down(owl_editwin *e) {
510  /* move down if we can */
511  if (e->buffy+1 < owl_editwin_get_numlines(e)) e->buffy++;
512
513  /* if we're past the last character move back */
514  if (e->buffx >= owl_editwin_get_numchars_on_line(e, e->buffy)) {
515    e->buffx=owl_editwin_get_numchars_on_line(e, e->buffy);
516  }
517
518  /* do we need to scroll? */
519  if (e->buffy-e->topline > e->winlines) {
520    e->topline+=e->winlines/2;
521  }
522
523  /* adjust for locktext */
524  owl_editwin_adjust_for_locktext(e);
525}
526
527void owl_editwin_key_left(owl_editwin *e) {
528  /* move left if we can, and maybe up a line */
529  if (e->buffx>0) {
530    e->buffx--;
531  } else if (e->buffy>0) {
532    e->buffy--;
533    e->buffx=owl_editwin_get_numchars_on_line(e, e->buffy);
534  }
535
536  /* do we need to scroll up? */
537  if (e->buffy-e->topline < 0) {
538    e->topline-=e->winlines/2;
539  }
540
541  /* make sure to avoid locktext */
542  owl_editwin_adjust_for_locktext(e);
543}
544
545void owl_editwin_key_right(owl_editwin *e) {
546  int i;
547
548  /* move right if we can, and skip down a line if needed */
549  i=owl_editwin_get_numchars_on_line(e, e->buffy);
550  if (e->buffx < i) {
551    e->buffx++;
552    /*  } else if (e->buffy+1 < owl_editwin_get_numlines(e)) { */
553  } else if (_owl_editwin_get_index_from_xy(e) < e->bufflen) {
554    if (e->style==OWL_EDITWIN_STYLE_MULTILINE) {
555      e->buffx=0;
556      e->buffy++;
557    }
558  }
559
560  /* do we need to scroll down? */
561  if (e->buffy-e->topline >= e->winlines) {
562    e->topline+=e->winlines/2;
563  }
564}
565
566void owl_editwin_move_to_nextword(owl_editwin *e) {
567  int i, x;
568
569  /* if we're starting on a space, find the first non-space */
570  i=_owl_editwin_get_index_from_xy(e);
571  if (e->buff[i]==' ') {
572    for (x=i; x<e->bufflen; x++) {
573      if (e->buff[x]!=' ' && e->buff[x]!='\n') {
574        _owl_editwin_set_xy_by_index(e, x);
575        break;
576      }
577    }
578  }
579
580  /* find the next space, newline or end of line and go there, if
581     already at the end of the line, continue on to the next */
582  i=owl_editwin_get_numchars_on_line(e, e->buffy);
583  if (e->buffx < i) {
584    /* move right till end of line */
585    while (e->buffx < i) {
586      e->buffx++;
587      if (e->buff[_owl_editwin_get_index_from_xy(e)]==' ') return;
588      if (e->buffx == i) return;
589    }
590  } else if (e->buffx == i) {
591    /* try to move down */
592    if (e->style==OWL_EDITWIN_STYLE_MULTILINE) {
593      if (e->buffy+1 <  owl_editwin_get_numlines(e)) {
594        e->buffx=0;
595        e->buffy++;
596        owl_editwin_move_to_nextword(e);
597      }
598    }
599  }
600}
601
602void owl_editwin_move_to_previousword(owl_editwin *e) {
603  /* go backwards to the last non-space character */
604  int i, x;
605
606  /* are we already at the beginning of the word? */
607  i=_owl_editwin_get_index_from_xy(e);
608  if ( (e->buff[i]!=' ' && e->buff[i]!='\n' && e->buff[i]!='\0') &&
609       (e->buff[i-1]==' ' || e->buff[i-1]=='\n') ) {
610    owl_editwin_key_left(e);
611  }
612   
613  /* are we starting on a space character? */
614  i=_owl_editwin_get_index_from_xy(e);
615  if (e->buff[i]==' ' || e->buff[i]=='\n' || e->buff[i]=='\0') {
616    /* find the first non-space */
617    for (x=i; x>=e->lock; x--) {
618      if (e->buff[x]!=' ' && e->buff[x]!='\n' && e->buff[x]!='\0') {
619        _owl_editwin_set_xy_by_index(e, x);
620        break;
621      }
622    }
623  }
624
625  /* find the last non-space */
626  i=_owl_editwin_get_index_from_xy(e);
627  for (x=i; x>=e->lock; x--) {
628    if (e->buff[x-1]==' ' || e->buff[x-1]=='\n') {
629      _owl_editwin_set_xy_by_index(e, x);
630      break;
631    }
632  }
633  _owl_editwin_set_xy_by_index(e, x);
634}
635
636
637void owl_editwin_delete_nextword(owl_editwin *e) {
638  int z;
639
640  if (e->bufflen==0) return;
641
642  /* if we start out on a space character then gobble all the spaces
643     up first */
644  while (1) {
645    z=_owl_editwin_get_index_from_xy(e);
646    if (e->buff[z]==' ' || e->buff[z]=='\n') {
647      owl_editwin_delete_char(e);
648    } else {
649      break;
650    }
651  }
652
653  /* then nuke the next word */
654  while (1) {
655    z=_owl_editwin_get_index_from_xy(e);
656    if (e->buff[z+1]==' ' || e->buff[z+1]=='\n' || e->buff[z+1]=='\0') break;
657    owl_editwin_delete_char(e);
658  }
659  owl_editwin_delete_char(e);
660}
661
662void owl_editwin_delete_previousword(owl_editwin *e) {
663  /* go backwards to the last non-space character, then delete chars */
664  int i, startpos, endpos;
665
666  startpos = _owl_editwin_get_index_from_xy(e);
667  owl_editwin_move_to_previousword(e);
668  endpos = _owl_editwin_get_index_from_xy(e);
669  for (i=0; i<startpos-endpos; i++) {
670    owl_editwin_delete_char(e);
671  }
672}
673
674void owl_editwin_delete_to_endofline(owl_editwin *e) {
675  int i;
676
677  if (owl_editwin_get_numchars_on_line(e, e->buffy)>e->buffx) {
678    /* normal line */
679    i=_owl_editwin_get_index_from_xy(e);
680    while(i < e->bufflen) {
681      if (e->buff[i]!='\n') {
682        owl_editwin_delete_char(e);
683      } else if ((e->buff[i]=='\n') && (i==e->bufflen-1)) {
684        owl_editwin_delete_char(e);
685      } else {
686        return;
687      }
688    }
689  } else if (e->buffy+1 < owl_editwin_get_numlines(e)) {
690    /* line with cursor at the end but not on very last line */
691    owl_editwin_key_right(e);
692    owl_editwin_backspace(e);
693  }
694}
695
696void owl_editwin_move_to_line_end(owl_editwin *e) {
697  e->buffx=owl_editwin_get_numchars_on_line(e, e->buffy);
698}
699
700void owl_editwin_move_to_line_start(owl_editwin *e) {
701  e->buffx=0;
702  owl_editwin_adjust_for_locktext(e);
703}
704
705void owl_editwin_move_to_end(owl_editwin *e) {
706  /* go to last char */
707  e->buffy=owl_editwin_get_numlines(e)-1;
708  e->buffx=owl_editwin_get_numchars_on_line(e, e->buffy);
709  owl_editwin_key_right(e);
710
711  /* do we need to scroll? */
712  if (e->buffy-e->topline > e->winlines) {
713    e->topline+=e->winlines/2;
714  }
715}
716
717void owl_editwin_move_to_top(owl_editwin *e) {
718  _owl_editwin_set_xy_by_index(e, 0);
719
720  /* do we need to scroll? */
721  e->topline=0;
722
723  owl_editwin_adjust_for_locktext(e);
724}
725
726void owl_editwin_fill_paragraph(owl_editwin *e) {
727  int i, save;
728
729  /* save our starting point */
730  save=_owl_editwin_get_index_from_xy(e);
731
732  /* scan back to the beginning of this paragraph */
733  for (i=save; i>=e->lock; i--) {
734    if ( (i<=e->lock) ||
735         ((e->buff[i]=='\n') && (e->buff[i-1]=='\n'))) {
736      _owl_editwin_set_xy_by_index(e, i+1);
737      break;
738    }
739  }
740
741  /* main loop */
742  while (1) {
743    i=_owl_editwin_get_index_from_xy(e);
744
745    /* bail if we hit the end of the buffer */
746    if (i>=e->bufflen) break;
747
748    /* bail if we hit the end of the paragraph */
749    if (e->buff[i]=='\n' && e->buff[i+1]=='\n') break;
750
751    /* if we've travelled too far, linewrap */
752    if ((e->buffx) >= e->fillcol) {
753      _owl_editwin_linewrap_word(e);
754    }
755
756    /* did we hit the end of a line too soon? */
757    i=_owl_editwin_get_index_from_xy(e);
758    if (e->buff[i]=='\n' && e->buffx<e->fillcol-1) {
759      /* ********* we need to make sure we don't pull in a word that's too long ***********/
760      e->buff[i]=' ';
761    }
762   
763    /* fix spacing */
764    i=_owl_editwin_get_index_from_xy(e);
765    if (e->buff[i]==' ' && e->buff[i+1]==' ') {
766      if (e->buff[i-1]=='.' || e->buff[i-1]=='!' || e->buff[i-1]=='?') {
767        owl_editwin_key_right(e);
768      } else {
769        owl_editwin_delete_char(e);
770        /* if we did this ahead of the save point, adjust it */
771        if (i<save) save--;
772      }
773    } else {
774      owl_editwin_key_right(e);
775    }
776
777  }
778
779  /* put cursor back at starting point */
780  _owl_editwin_set_xy_by_index(e, save);
781
782  /* do we need to scroll? */
783  if (e->buffy-e->topline < 0) {
784    e->topline-=e->winlines/2;
785  }
786}
787
788/* returns if only whitespace remains */
789int owl_editwin_is_at_end(owl_editwin *e) {
790  int cur=_owl_editwin_get_index_from_xy(e);
791  return only_whitespace(e->buff+cur);
792}
793
794int owl_editwin_check_dotsend(owl_editwin *e) {
795  int i;
796
797  if (!e->dotsend) return(0);
798  for (i=e->bufflen-1; i>0; i--) {
799    if (e->buff[i] == '.' 
800        && (e->buff[i-1] == '\n' || e->buff[i-1] == '\r')
801        && (e->buff[i+1] == '\n' || e->buff[i+1] == '\r')) {
802      e->bufflen = i;
803      e->buff[i] = '\0';
804      return(1);
805    }
806    if (!isspace((int) e->buff[i])) {
807      return(0);
808    }
809  }
810  return(0);
811
812#if 0  /* old implementation */
813  if (e->bufflen>=2) {
814    if ((e->buff[e->bufflen-1]=='\n') &&
815        (e->buff[e->bufflen-2]=='.') &&
816        ((e->bufflen==2) || (e->buff[e->bufflen-3]=='\n'))) {
817      e->buff[e->bufflen-2]='\0';
818      e->bufflen-=2;
819      owl_editwin_redisplay(e, 0);
820      return(1);
821    }
822  }
823  return(0);
824#endif
825}
826
827void owl_editwin_post_process_char(owl_editwin *e, int j) {
828  /* check if we need to scroll down */
829  if (e->buffy-e->topline >= e->winlines) {
830    e->topline+=e->winlines/2;
831  }
832  if ((j==13 || j==10) && owl_editwin_check_dotsend(e)) {
833    owl_command_editmulti_done(e);
834    return;
835  }
836  owl_editwin_redisplay(e, 0); 
837}
838
839void owl_editwin_process_char(owl_editwin *e, int j) {
840  if (j == ERR) return;
841  if (j>127 || ((j<32) && (j!=10) && (j!=13))) {
842    return;
843  } else {
844    owl_editwin_insert_char(e, j);
845  }
846}
847
848char *owl_editwin_get_text(owl_editwin *e) {
849  return(e->buff+e->lock);
850}
851
852int owl_editwin_get_numchars_on_line(owl_editwin *e, int line) {
853  int i;
854  char *ptr1, *ptr2;
855
856  if (e->bufflen==0) return(0);
857 
858  /* first go to the yth line */
859  ptr1=e->buff;
860  for (i=0; i<line; i++) {
861    ptr2=strchr(ptr1, '\n');
862    if (!ptr2) {
863      /* we're already on the last line */
864      return(0);
865    }
866    ptr1=ptr2+1;
867  }
868
869  /* now go to the xth character */
870  ptr2=strchr(ptr1, '\n');
871  if (!ptr2) {
872    return(e->buff + e->bufflen - ptr1);
873  }
874  return(ptr2-ptr1); /* don't count the newline for now */
875}
876
877int owl_editwin_get_numlines(owl_editwin *e) {
878  return(owl_text_num_lines(e->buff));
879}
880
Note: See TracBrowser for help on using the repository browser.