home *** CD-ROM | disk | FTP | other *** search
- #include <stdio.h>
- #include <string.h>
-
- #include "config.h"
- #include "buffer.h"
- #include "abbrev.h"
- #include "text.h"
- #include "ledit.h"
- #include "ins.h"
- #include "cmds.h"
- #include "misc.h"
-
-
- #ifdef HAS_ABBREVS
-
- #ifdef pc_system
- #define MAX_ABBREVS 48
- #else
- #define MAX_ABBREVS 256
- #endif
-
- #define MAX_ABBREV_LEN 48
- #define MAX_ABBREV_TABLES 10
- typedef struct Abbrev_Table_Type
- {
- int len; /* current length of abbrev */
- int empty; /* number of cell known to be empty */
- char abbrevs [MAX_ABBREVS][MAX_ABBREV_LEN];
- /* formatted as abbrev\0expansion */
- char word_chars[256]; /* word delimiters */
- char name[16]; /* name of table */
- }
- Abbrev_Table_Type;
-
- static Abbrev_Table_Type *Global_Abbrev_Table;
- static Abbrev_Table_Type *Abbrev_Tables [MAX_ABBREV_TABLES];
- int expand_abbrev (unsigned char ch)
- {
- Abbrev_Table_Type *tbl;
- int len, i;
- unsigned char *p;
- char *abbrev;
-
- if ((i = CBuf->abbrev_table_handle) == -1) tbl = NULL;
- else tbl = Abbrev_Tables [i];
-
- if (tbl == NULL)
- {
- tbl = Global_Abbrev_Table;
- if (tbl == NULL) return 0;
- }
-
- if (tbl->len == 0) return 0;
-
-
- if (tbl->word_chars[(int) ch]) return 0; /* not a delimiter */
-
- p = CLine->data + (Point - 1);
-
- while ((p >= CLine->data) && (tbl->word_chars[(int) *p]))
- {
- p--;
- }
- p++;
-
- len = (int) ((CLine->data + Point) - p);
- if ((len == 0) || (len >= MAX_ABBREV_LEN / 2)) return 0;
- /* It makes no sense to have an abbrev larger than its expansion! */
-
- ch = *p;
- for (i = 0; i < tbl->len; i++)
- {
- abbrev = tbl->abbrevs [i];
- if ((*abbrev == (char) ch) && (abbrev[len] == 0) &&
- (0 == strncmp (abbrev, (char *) p, len)))
- {
- Point -= len;
- abbrev += len + 1;
- deln (&len);
- len = strlen (abbrev);
- if (CBuf->flags & OVERWRITE_MODE)
- {
- deln (&len); /* this does not delete across lines */
- }
- ins_chars ((unsigned char *) abbrev, len);
- return 1;
- }
- }
- return 0;
- }
-
-
-
- static Abbrev_Table_Type *find_table (char *name, int *loc, int err)
- {
- Abbrev_Table_Type **tbl, **max;
- Abbrev_Table_Type **empty_tbl = NULL;
-
- tbl = Abbrev_Tables;
- max = tbl + MAX_ABBREV_TABLES;
-
- while (tbl < max)
- {
- if (*tbl == NULL)
- {
- if (empty_tbl == NULL) empty_tbl = tbl;
- }
- else if (strcmp (name, (*tbl)->name) == 0)
- {
- break;
- }
- tbl++;
- }
- *loc = (int) (tbl - Abbrev_Tables);
- if (tbl == max)
- {
- if (empty_tbl != NULL) *loc = (int) (empty_tbl - Abbrev_Tables);
- if (err) msg_error ("Table does not exist.");
- return NULL;
- }
- return *tbl;
- }
-
-
- void create_abbrev_table (char *name, char *word_chars)
- {
- Abbrev_Table_Type *tbl;
- int loc;
-
- tbl = find_table (name, &loc, 0);
- if (tbl == NULL)
- {
- if (loc == MAX_ABBREV_TABLES)
- {
- msg_error ("Abbrev Table Quota reached.");
- return;
- }
-
- tbl = (Abbrev_Table_Type *) SLMALLOC (sizeof (Abbrev_Table_Type));
- if (tbl == NULL)
- {
- msg_error ("Malloc error.");
- return;
- }
-
- Abbrev_Tables [loc] = tbl;
- }
-
- MEMSET ((char *) tbl, 0, sizeof (Abbrev_Table_Type));
-
- if (*word_chars == 0) word_chars = Jed_Word_Range;
-
- jed_make_lut ((unsigned char *) tbl->word_chars, (unsigned char *) word_chars, 0);
-
- strncpy (tbl->name, name, 15); /* The null char is here because of
- * the MEMSET
- */
-
- if (strcmp (name, "Global") == 0) Global_Abbrev_Table = tbl;
- }
-
- void delete_abbrev_table (char *name)
- {
- Abbrev_Table_Type *tbl;
- int n;
- Buffer *b;
-
- tbl = find_table (name, &n, 1);
- if (tbl == NULL) return;
-
- SLFREE (tbl);
- Abbrev_Tables[n] = NULL;
- if (tbl == Global_Abbrev_Table) Global_Abbrev_Table = NULL;
- b = CBuf;
- do
- {
- if (b->abbrev_table_handle == n) b->abbrev_table_handle = -1;
- b = b->next;
- }
- while (b != CBuf);
- }
-
-
- void define_abbrev (char *table, char *abbrev, char *expans)
- {
- Abbrev_Table_Type *tbl;
- int len, lena;
- int i;
- char *a;
-
- tbl = find_table (table, &len, 1);
- if (tbl == NULL) return;
-
- if (tbl->len == MAX_ABBREVS) return; /* silently return */
-
- lena = strlen (abbrev);
- len = lena + strlen (expans) + 1;
-
- if (len >= MAX_ABBREV_LEN)
- {
- msg_error ("Expansion is too long.");
- }
-
- for (i = 0; i < MAX_ABBREVS; i++)
- {
- a = tbl->abbrevs[i];
- if ((*a == 0)
- || ((a[lena] == 0) && (0 == strcmp (a, abbrev))))
- {
- strcpy (a, abbrev);
- strcpy (a + lena + 1, expans);
- tbl->len++;
- return;
- }
- }
- }
-
-
- void use_abbrev_table (char *name)
- {
- Abbrev_Table_Type *tbl;
- int loc;
-
- tbl = find_table (name, &loc, 1);
- if (tbl == NULL) return;
- CBuf->abbrev_table_handle = loc;
- }
-
- int abbrev_table_p (char *name)
- {
- int loc;
- if (find_table (name, &loc, 0) != NULL) return 1;
- return 0;
- }
-
- static void push_word (Abbrev_Table_Type *tbl)
- {
- char buf[256], *b, *w;
- int i, in_range;
-
- b = buf;
- w = tbl->word_chars;
-
- if (w[(unsigned char) '-'] != 0) *b++ = '-';
- in_range = 0;
-
- for (i = 33; i < 256; i++)
- {
- if ((i != '-') && (0 != w[i]))
- {
- if (i == '\\') *b++ = (char) i;
- *b = (char) i;
- if (in_range == 0)
- {
- *(b + 1) = '-';
- b += 2; *b = 0;
- in_range = 1;
- }
- }
- else
- {
- if (in_range)
- {
- if (*b == 0) b--; else b++;
- in_range = 0;
- }
- }
- }
- *b = 0;
- SLang_push_string (buf);
- }
-
- void what_abbrev_table (void)
- {
- Abbrev_Table_Type *tbl;
- int i;
- char *w = "";
-
-
- if ((i = CBuf->abbrev_table_handle) == -1) tbl = NULL;
- else tbl = Abbrev_Tables [i];
-
- if (tbl == NULL) tbl = Global_Abbrev_Table;
- if (tbl == NULL)
- {
- SLang_push_string (w);
- SLang_push_string (w);
- }
- else
- {
- SLang_push_string (tbl->name);
- push_word (tbl);
- }
- }
-
-
-
- void dump_abbrev_table (char *name)
- {
- Abbrev_Table_Type *tbl;
- char *abbrev;
- int i, len;
-
- if (NULL == (tbl = find_table (name, &len, 1))) return;
-
- len = tbl->len;
- for (i = 0; i < len; i++)
- {
- abbrev = tbl->abbrevs [i];
- if (*abbrev)
- {
- insert_string (abbrev);
- ins ('\t');
- insert_string (abbrev + (1 + strlen (abbrev)));
- newline ();
- }
- }
- push_word (tbl);
- }
-
-
- int list_abbrev_tables (void)
- {
- int n = 0;
- Abbrev_Table_Type **tbl, **max;
-
- tbl = Abbrev_Tables;
- max = tbl + MAX_ABBREV_TABLES;
-
- while ((tbl < max) && (*tbl != NULL))
- {
- n++;
- SLang_push_string ((*tbl)->name);
- tbl++;
- }
-
- return n;
- }
-
- #endif /* HAS_ABBREVS */
-