RC2 compatibility
[phpeclipse.git] / net.sourceforge.phpeclipse / src / net / sourceforge / phpdt / internal / ui / text / SubstitutionTextReader.java
1 /**********************************************************************
2 Copyright (c) 2000, 2002 IBM Corp. and others.
3 All rights reserved. This program and the accompanying materials
4 are made available under the terms of the Common Public License v1.0
5 which accompanies this distribution, and is available at
6 http://www.eclipse.org/legal/cpl-v10.html
7
8 Contributors:
9     IBM Corporation - Initial implementation
10 **********************************************************************/
11
12 package net.sourceforge.phpdt.internal.ui.text;
13
14
15 import java.io.IOException;
16 import java.io.Reader;
17
18 import net.sourceforge.phpdt.internal.corext.phpdoc.SingleCharReader;
19
20
21 /**
22  * Reads the text contents from a reader and computes for each character
23  * a potential substitution. The substitution may eat more characters than 
24  * only the one passed into the computation routine.
25  */
26 public abstract class SubstitutionTextReader extends SingleCharReader {
27         
28         protected static final String LINE_DELIM= System.getProperty("line.separator", "\n"); //$NON-NLS-1$ //$NON-NLS-2$
29         
30         private Reader fReader;
31         private boolean fWasWhiteSpace;
32         private int fCharAfterWhiteSpace;
33
34         /**
35          * Tells whether white space characters are skipped.
36          */
37         private boolean fSkipWhiteSpace= true;
38         
39         private boolean fReadFromBuffer;
40         private StringBuffer fBuffer;
41         private int fIndex;
42
43
44         protected SubstitutionTextReader(Reader reader) {
45                 fReader= reader;
46                 fBuffer= new StringBuffer();
47                 fIndex= 0;
48                 fReadFromBuffer= false;
49                 fCharAfterWhiteSpace= -1;
50                 fWasWhiteSpace= true;
51         }
52         
53         /**
54          * Implement to compute the substitution for the given character and 
55          * if necessary subsequent characters. Use <code>nextChar</code>
56          * to read subsequent characters.
57          */
58         protected abstract String computeSubstitution(int c) throws IOException;
59         
60         /**
61          * Returns the internal reader.
62          */
63         protected Reader getReader() {
64                 return fReader;
65         }
66          
67         /**
68          * Returns the next character.
69          */
70         protected int nextChar() throws IOException {
71                 fReadFromBuffer= (fBuffer.length() > 0);
72                 if (fReadFromBuffer) {
73                         char ch= fBuffer.charAt(fIndex++);
74                         if (fIndex >= fBuffer.length()) {
75                                 fBuffer.setLength(0);
76                                 fIndex= 0;
77                         }
78                         return ch;
79                 } else {
80                         int ch= fCharAfterWhiteSpace;
81                         if (ch == -1) {
82                                 ch= fReader.read();
83                         }
84                         if (fSkipWhiteSpace && Character.isWhitespace((char)ch)) {
85                                 do {
86                                         ch= fReader.read();
87                                 } while (Character.isWhitespace((char)ch));
88                                 if (ch != -1) {
89                                         fCharAfterWhiteSpace= ch;
90                                         return ' ';
91                                 }
92                         } else {
93                                 fCharAfterWhiteSpace= -1;
94                         }
95                         return ch;
96                 }
97         }
98         
99         /**
100          * @see Reader#read()
101          */
102         public int read() throws IOException {
103                 int c;
104                 do {
105                         
106                         c= nextChar();
107                         while (!fReadFromBuffer) {
108                                 String s= computeSubstitution(c);
109                                 if (s == null)
110                                         break;
111                                 if (s.length() > 0)
112                                         fBuffer.insert(0, s);
113                                 c= nextChar();
114                         }
115                         
116                 } while (fSkipWhiteSpace && fWasWhiteSpace && (c == ' '));
117                 fWasWhiteSpace= (c == ' ' || c == '\r' || c == '\n');
118                 return c;
119         }
120                 
121         /**
122          * @see Reader#ready()
123          */             
124     public boolean ready() throws IOException {
125                 return fReader.ready();
126         }
127                 
128         /**
129          * @see Reader#close()
130          */             
131         public void close() throws IOException {
132                 fReader.close();
133         }
134         
135         /**
136          * @see Reader#reset()
137          */             
138         public void reset() throws IOException {
139                 fReader.reset();
140                 fWasWhiteSpace= true;
141                 fCharAfterWhiteSpace= -1;
142                 fBuffer.setLength(0);
143                 fIndex= 0;              
144         }
145
146         protected final void setSkipWhitespace(boolean state) {
147                 fSkipWhiteSpace= state;
148         }
149
150         protected final boolean isSkippingWhitespace() {
151                 return fSkipWhiteSpace;
152         }
153 }