View Javadoc

1   /*
2    * Copyright 2004-2006 the Seasar Foundation and the Others.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    *     http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, 
13   * either express or implied. See the License for the specific language
14   * governing permissions and limitations under the License.
15   */
16  package org.seasar.tuigwaa.cms.core.wiki.base;
17  
18  import java.awt.Color;
19  import java.util.HashMap;
20  import java.util.Map;
21  
22  import org.apache.commons.logging.Log;
23  import org.apache.commons.logging.LogFactory;
24  import org.seasar.tuigwaa.cms.core.wiki.engine.Node;
25  import org.seasar.tuigwaa.cms.core.wiki.engine.SimpleNode;
26  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiArgs;
27  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiBlockPlugin;
28  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiCSVTable;
29  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiExcerpt;
30  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiInlinePlugin;
31  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiLetters;
32  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiStrongItalic;
33  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiTable;
34  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiTablecolumn;
35  import org.seasar.tuigwaa.cms.core.wiki.engine.WikiTablemember;
36  import org.seasar.tuigwaa.plugin.AbstractPlugin;
37  import org.seasar.tuigwaa.plugin.PluginRequest;
38  
39  
40  /***
41   * VisitorUtils class Provides node object related tasks which is common during
42   * various visitor, plugin execution. The difference from WikiHelper is that
43   * this class quite depends on node object structure itself.
44   * 
45   * 
46   * @author someda
47   */
48  public class VisitorUtils {
49  
50  	private static Log log_ = LogFactory.getLog(VisitorUtils.class);
51  
52  	private static final String STRONGITALIC_MARK = "'";
53  
54  	private static final int BOLD_NUM = 2;
55  	private static final int ITALIC_NUM = 3;
56  	private static final int BOLDITALIC_NUM = 5;
57  
58  	private static Map colorMap_ = new HashMap();
59  
60  	private static final String[] TAG_ESCAPE = { "<", "&lt;", ">", "&gt;" };
61  	private static final String[] OTHER_ESCAPE = {"&","&amp;"};
62  
63  	static {
64  		colorMap_.put("red", Color.RED);
65  		colorMap_.put("blue", Color.BLUE);
66  		colorMap_.put("black", Color.BLACK);
67  		colorMap_.put("cyan", Color.CYAN);
68  		colorMap_.put("green", Color.GREEN);
69  		colorMap_.put("gray", Color.GRAY);
70  	}
71  	
72  	// ----- [Start] Excerpt related methods -----
73  	public static boolean isExcerptStartNeeded(WikiExcerpt node){
74  		
75  		boolean flag = true;		
76  		Node parent = node.jjtGetParent();
77  		if(parent instanceof WikiExcerpt){
78  			int plevel = ((WikiExcerpt)parent).level;
79  			if(node.level <= plevel){
80  				flag = false;
81  			}			
82  		}
83  		return flag;
84  	}		
85  	
86  	// ----- [Start] Table related methods -----
87  	/***
88  	 * Before accepting node tree, need to set node properties for colspan,
89  	 * rowspan.
90  	 * 
91  	 * The value of colspan or rowspan which might be set after trailing should
92  	 * be incremented before being used in visitor.
93  	 */
94  	public static void prepareWikiTable(SimpleNode node, Object data) {
95  
96  		if (!(node instanceof WikiTable) && !(node instanceof WikiCSVTable))
97  			throw new IllegalArgumentException(
98  					"The class other than WikiTable or WikiCSVTable cannot be accepted.");
99  
100 		for (int i = 0; i < node.jjtGetNumChildren(); i++) {
101 			if (node.jjtGetChild(i) instanceof WikiTablemember) {
102 				WikiTablemember member = (WikiTablemember) node.jjtGetChild(i);
103 				int colspannum = 0;
104 				for (int j = 0; j < member.jjtGetNumChildren(); j++) {
105 					WikiTablecolumn column = (WikiTablecolumn) member
106 							.jjtGetChild(j);
107 					if (column.iscolspan) {
108 						colspannum++;
109 					} else if (column.isrowspan) {
110 						int rowspannum = 1;
111 						for (int k = i - 1; k >= 0; k--) {
112 							// Access to previous WikiTablemember object to set
113 							// rowspan
114 							if (node.jjtGetChild(k) instanceof WikiTablemember) {
115 								WikiTablecolumn leftcolumn = (WikiTablecolumn) node
116 										.jjtGetChild(k).jjtGetChild(j);
117 								if (leftcolumn.isrowspan) {
118 									rowspannum++;
119 									continue;
120 								} else {
121 									leftcolumn.rowspannum = rowspannum;
122 									break;
123 								}
124 							} else { // in case WikiError
125 								break;
126 							}
127 						}
128 					} else {
129 						if (colspannum > 0) {
130 							column.colspannum = colspannum;
131 							colspannum = 0;
132 						}
133 					}
134 				}
135 			}
136 		}
137 	}
138 
139 	// ----- [End] Table related methods -----
140 
141 	// ----- [Start] StrongItalic related methods -----
142 	public static String getAppendString(WikiStrongItalic node, boolean pre) {
143 		int num = node.prelevel - node.postlevel;
144 		if (!pre)
145 			num = 0 - num;
146 
147 		if (num <= 0)
148 			return null;
149 
150 		StringBuffer buf = new StringBuffer();
151 		while (num > 0) {
152 			buf.append(STRONGITALIC_MARK);
153 			num--;
154 		}
155 		return buf.toString();
156 	}
157 
158 	public static boolean isBold(WikiStrongItalic node) {
159 		int level = (node.prelevel > node.postlevel) ? node.postlevel
160 				: node.prelevel;
161 		return (level == BOLD_NUM || level == BOLDITALIC_NUM) ? true : false;
162 	}
163 
164 	public static boolean isItalic(WikiStrongItalic node) {
165 		int level = (node.prelevel > node.postlevel) ? node.postlevel
166 				: node.prelevel;
167 		return (level == ITALIC_NUM || level == BOLDITALIC_NUM) ? true : false;
168 	}
169 
170 	// ----- [End] StrongItalic related methods -----
171 
172 	// ----- [Start] BlockPlugin/InlinePlugin related methods -----
173 	public static PluginRequest createPluginRequest(Node node) {
174 
175 		if (!(node instanceof WikiBlockPlugin)
176 				&& !(node instanceof WikiInlinePlugin))
177 			throw new IllegalArgumentException(
178 					"The class other than WikiBlockPlugin or WikiInlinePlugin cannot be accepted.");
179 
180 		String name = null;
181 		String[] args = getArgs(node);
182 		int mode = 0;
183 
184 		if (node instanceof WikiBlockPlugin) {
185 			WikiBlockPlugin p = (WikiBlockPlugin) node;
186 			name = p.name;
187 			mode = AbstractPlugin.BLOCKPLUGIN_MODE;
188 		}
189 		if (node instanceof WikiInlinePlugin) {
190 			WikiInlinePlugin p = (WikiInlinePlugin) node;
191 			name = p.name;
192 			mode = AbstractPlugin.INLINEPLUGIN_MODE;
193 		}
194 		PluginRequest prequest = new PluginRequest(args, null, name, mode);
195 		return prequest;
196 	}
197 
198 	public static String[] getArgs(Node node) {
199 		String args[] = null;
200 		if (node.jjtGetNumChildren() > 0
201 				&& node.jjtGetChild(0) instanceof WikiArgs) {
202 			WikiArgs child = (WikiArgs) node.jjtGetChild(0);
203 			args = child.args;
204 		}
205 		return args;
206 	}
207 
208 	// ----- [End] BlockPlugin/InlinePlugin related methods -----
209 
210 	public static Color getColorByString(String s, boolean foreground) {
211 
212 		Color c = (foreground) ? Color.BLACK : Color.WHITE; // default
213 		if (s.startsWith("#")) {
214 			String code = "0x" + s.substring(1);
215 			try {
216 				c = Color.decode(Integer.decode(code).toString());
217 			} catch (Exception e) {
218 				log_.error(e.getMessage());
219 			}
220 		} else {
221 			// for color name like "blue", "red"
222 			if (colorMap_.get(s.toLowerCase()) != null) {
223 				c = (Color) colorMap_.get(s.toLowerCase());
224 			}
225 		}
226 		return c;
227 	}
228 
229 	// ----- HTMLWikiVisitor related
230 	public static String escape(String letter) {
231 		return replaceArray(letter,TAG_ESCAPE,true);		
232 	}
233 	
234 	public static String getAnchorId(SimpleNode node){		
235 		String anchor = null;
236 		for(int i=0;i<node.jjtGetNumChildren();i++){
237 			if(node.jjtGetChild(i) instanceof WikiLetters){
238 				WikiLetters l = (WikiLetters) node.jjtGetChild(i);
239 				if(l.isAnchor){
240 					anchor = l.letter;
241 					break;
242 				}
243 			}
244 		}
245 		return anchor;
246 	}
247 	
248 	// -- TextWikiVisitor related
249 	public static String unescape(String letter){		
250 		letter = replaceArray(letter,TAG_ESCAPE,false);
251 		letter = replaceArray(letter,OTHER_ESCAPE,false);		
252 		return letter;
253 	}
254 	
255 	
256 	private static String replaceArray(String letter, String[] array, boolean forward){
257 	
258 		if(letter == null) return "";
259 		String ret = letter;
260 		if(forward){			
261 			for(int i=0;i<array.length-1;i +=2){
262 				ret = ret.replaceAll(array[i],array[i+1]);
263 			}						
264 		}else{
265 			for(int i=1;i<array.length;i +=2){
266 				ret = ret.replaceAll(array[i],array[i-1]);
267 			}			
268 		}
269 		return ret;		
270 	}			
271 
272 }