File: spell.the

package info (click to toggle)
the 3.3~rc1-3
  • links: PTS
  • area: main
  • in suites: stretch
  • size: 5,492 kB
  • ctags: 5,889
  • sloc: ansic: 73,773; sh: 2,904; makefile: 803
file content (267 lines) | stat: -rw-r--r-- 8,899 bytes parent folder | download | duplicates (8)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
/*
$Id: spell.the,v 1.1 2001/01/04 09:42:04 mark Exp $
*/
/***********************************************************************/
/* Description: REXX macro to check spelling of words in a target.     */
/* Syntax:      spell target                                           */
/* Notes:       This macro spells words in the lines specified in the  */
/*              target.                                                */
/*              Full XEDIT/KEDIT/THE targets are supported include WORD*/
/*              (WORD option not yet supported)                        */
/*              This macro will only work with International Ispell    */
/*              v 3.1 or above.                                        */
/***********************************************************************/
Trace o
If batch() Then
   Do
     'emsg This macro cannot be run in batch'
     Exit 1
   End
arg1 = Arg(1)
noargs = Arg()
'preserve'
time_to_quit = 'NO'
spell_command = 'ispell -a'
no_match_line = "'A' to add, 'E' to edit, 'I' to ignore or 'Q' to quit."
If noargs = 0 Then arg1 = '1'               /* no args - assume 1 line */
forward = 1                  /* assume direction is forward by default */
'EXTRACT /LINE/SIZE/STAY/FTYPE/FNAME/CURLINE/RESERVED */BLOCK/ZONE/'    /* get various stuff */
reserved_start = curline.2
current_line = line.1                   /* save current line for later */
left_col = zone.1
right_col = zone.2
If arg1 = 'word' | arg1 = 'WORD' Then Call spell_word
Else Call spell_target

/* put things back the way they were */
'reserved * off'
Do i = 1 To reserved.0      /* restore any reserved lines as they were */
  'reserved' reserved.i
End
'reset block'
'zone' zone.1 zone.2
'restore'
Return

/*---------------------------------------------------------------------*/
spell_target:
/*---------------------------------------------------------------------*/
reply = valid_target(arg1)
If reply = 'ERROR' Then
   Do
     'EMSG Error: 17 Invalid target' arg1
     'restore'
     Exit
   End
If reply = 'NOTFOUND' Then
   Do
     'EMSG Error: 17 Target not found' arg1
     'restore'
     Exit
   End
If Translate(arg1) = 'BLOCK' Then
   Do
     'EXTRACT /BLOCK/'
     If block.1 \= 'LINE' Then
        Do
          left_col = block.3
          right_col = block.5
        End
   End
start_line = Word(reply,1)                        /* get starting line */
nolines = Word(reply,2)                         /* get number of lines */
If nolines < 0 Then Do                /* if target before current line */
   forward = 0                    /* indicate direction to be backward */
   nolines = nolines * -1                     /* make nolines positive */
End
'cursor cmdline'
':'||start_line                                    /* go to first line */
totlines = 0                             /* reset changed line counter */
Do Forever                              /* for each line to target ... */
   If nolines = 0 Then Leave
   respell_current_line = 'NO'
   'EXTRACT /CURLINE/TOF/EOF/LINE/'       /* get current line contents, etc.*/
   If tof.1 = 'ON',                    /* ignore line if on TOF or EOF */
   |  eof.1 = 'ON' Then Nop
   Else
     Do
       line = Translate(curline.3,,'`"1234567890	-=\~!@#$%^&*()_+|[]{};:,.<>/?',' ')
       wordidx = 0
       Do i = 1 To Words(line)
          word_start_col = Wordindex(line,i)
          If word_start_col >= left_col & word_start_col <= right_col Then
             Do
               wordidx = wordidx + 1
               word_in_line.wordidx = Word(line,i)
               word_start.wordidx = Wordindex(line,i)
             End
       End
       word_in_line.0 = wordidx
       word_start.0 = wordidx
       Call RunSpellCommand "word_in_line." "word_out_line." "stderr."
       Call TidyOutput
       Do i = 1 To word_out_line.0
          Parse Var word_out_line.i cmd . num . ':' wordlist
          Select
            When cmd = '*' | cmd = '+' | cmd = '-' Then Iterate
            When cmd = '#' Then Call no_match
            When cmd = '&' & num > 0 Then
                 Do
                   word_out_line.i = Translate(wordlist,' ',',')
                   Call matches
                 End
            Otherwise Nop
          End
          If time_to_quit = 'YES' Then Leave
          If respell_current_line = 'YES' Then Leave
       End
       /* display prompts etc here */
       drop word_in_line.
       drop word_out_line.
     End
   If time_to_quit = 'YES' Then Leave
   'cursor cmdline'
   If respell_current_line \= 'YES' Then
     Do
       If forward = 1 Then 'N'      /* if going forward, get next line */
       Else 'U'               /* if going backwards, get previous line */
       If rc \= 0 Then Leave                     /* shouldn't get here */
       nolines = nolines - 1
     End
End
'cursor cmdline'
If stay.1 = 'ON' Then ':'||current_line 
'msg Spelling complete'
Return                                               /* go back to THE */

/*---------------------------------------------------------------------*/
spell_word:
/*---------------------------------------------------------------------*/
Return

/*---------------------------------------------------------------------*/
no_match:
/*---------------------------------------------------------------------*/
'reserved * off'
Call HighlightWord                               /* highlight the word */
'reserved' reserved_start+1 'No suggestions for:' word_in_line.i
'reserved' reserved_start+2 no_match_line
Call ProcessResponse 'NOMATCH'
Return

/*---------------------------------------------------------------------*/
matches:
/*---------------------------------------------------------------------*/
'reserved * off'
Call HighlightWord                               /* highlight the word */
'reserved' reserved_start+1 'Suggestions for:' word_in_line.i
Do j = 1 To Min(Words(word_out_line.i),9)
   'reserved' j+1+reserved_start '  ('||j||')' Word(word_out_line.i,j)
End
'reserved' j+1+reserved_start 'Press a number,' no_match_line
Call ProcessResponse j-1
Return

/*---------------------------------------------------------------------*/
ProcessResponse:
/*---------------------------------------------------------------------*/
Parse Arg itemno .
Do Forever
   'readv KEY'
   readv.1 = Translate(readv.1)
   Select
     When readv.1 = 'A' Then
       Do
         insert.0 = 2
         insert.1 = '*' || word_in_line.i    /* add word to dictionary */
         insert.2 = '#'                             /* save dictionary */
         Call RunSpellCommand "insert." "result." "stderr."
         drop insert.
         drop result.
         Leave
       End
     When readv.1 = 'Q' Then
       Do
         time_to_quit = 'YES'
         Leave
       End
     When readv.1 = 'E' Then
       Do
         Call EditWord
         Leave
       End
     When readv.1 = 'I' Then Leave
     When Datatype(itemno) = 'NUM' & readv.1 >= 1 & readv.1 <= itemno Then
       Do
         itemno = itemno
         off = Length(Word(word_out_line.i,itemno))-Length(word_in_line.i)
         Do wordidx = i+1 To word_in_line.0
            word_start.wordidx = word_start.wordidx + off
         End
         'zone' word_start.i '*'
         'nomsg c/'||word_in_line.i||'/'||Word(word_out_line.i,readv.1)||'/'
         Leave
       End
     Otherwise 
       Do
         'emsg Invalid response'
       End
   End
End
'reserved * off'
'reset block'
'refresh'
Return

/*---------------------------------------------------------------------*/
HighlightWord:
/*---------------------------------------------------------------------*/
'reset block'
'cursor file' line.1 word_start.i + Length(word_in_line.i) -1
'mark box'
'cursor file' line.1 word_start.i
'mark box'
Return

/*---------------------------------------------------------------------*/
EditWord:
/*---------------------------------------------------------------------*/
orig_len = Length(word_in_line.i)
'readv cmdline' word_in_line.i
'zone' word_start.i '*'
'nomsg c/'||word_in_line.i||'/'||readv.1||'/'
word_in_line.i = Word(readv.1,1)
respell_current_line = 'YES'
'zone 1 *'
Return

/*---------------------------------------------------------------------*/
RunSpellCommand:
/*---------------------------------------------------------------------*/
Parse Arg instem outstem errstem .
rc = run_os(spell_command,instem,outstem,errstem)
If rc \= 0 Then
   'emsg Return code from "'||spell_command||'"' rc
If stderr.0 \= 0 Then
   Do
     Do i = 1 To stderr.0
        'emsg' stderr.i
     End
     'restore'
     Exit 1
   End
If rc \= 0 Then Exit 1
Return

/*---------------------------------------------------------------------*/
TidyOutput:
/*---------------------------------------------------------------------*/
Do m = 2 To word_out_line.0 By 2
   Queue word_out_line.m
End
numqueued = Queued()
Do m = 1 To numqueued
   Parse Pull word_out_line.m
End
word_out_line.0 = numqueued
Return