1 package pl.caltha.forms.internal.ui;
2
3 import java.io.ByteArrayInputStream;
4 import java.io.ByteArrayOutputStream;
5 import java.io.PrintWriter;
6 import java.io.StringWriter;
7 import java.util.Properties;
8
9 import org.w3c.tidy.Tidy;
10 import org.xml.sax.Attributes;
11
12 import pl.caltha.forms.ConstructionException;
13 import pl.caltha.forms.FormsService;
14 import pl.caltha.forms.internal.model.InstanceImpl;
15 import pl.caltha.forms.internal.util.TidyWrapper;
16
17 /***
18 * HTML input control. Includes:
19 * <ul>
20 * <li><code>htmlarea</code></li>
21 * </ul>
22 *
23 * @author <a href="mailto:zwierzem@ngo.pl">Damian Gajda</a>
24 * @version $Id: NodeControlHTML.java,v 1.2 2005/01/20 16:44:52 pablo Exp $
25 */
26 public class NodeControlHTML extends NodeControl
27 {
28 public NodeControlHTML(String type, Attributes atts)
29 throws ConstructionException
30 {
31 super(type, atts);
32 }
33
34 /*** Tidy configuration. */
35 private static Properties tidyConfiguration;
36 /*** PoolService is used to pool jTidy objects. */
37
38
39
40
41 /*** Key for Tidy error log state value. */
42 private String TIDY_ERROR_LOG = "htmlarea.tidyErrorLog";
43
44 void setValue(InstanceImpl instance, String value)
45 {
46
47 org.dom4j.Node contextNode = ((ReferenceSingle)ref).getContextNode(instance);
48 instance.setStateValue(contextNode, TIDY_ERROR_LOG, null);
49
50
51
52
53 TidyWrapper tidyWrap = new TidyWrapper();
54
55 try
56 {
57
58 Tidy tidy = tidyWrap.getTidy();
59 tidy.setConfigurationFromProps(tidyConfiguration);
60 tidy.setCharEncoding(org.w3c.tidy.Configuration.UTF8);
61 tidy.setXHTML(true);
62 tidy.setShowWarnings(false);
63
64 ByteArrayInputStream inputStream = new ByteArrayInputStream(value.getBytes("UTF-8"));
65 ByteArrayOutputStream outputStream = new ByteArrayOutputStream(value.length()+256);
66
67 StringWriter errorWriter = new StringWriter(256);
68 tidy.setErrout(new PrintWriter(errorWriter));
69
70 tidy.parse(inputStream, outputStream);
71
72 String outputValue;
73
74 if(tidy.getParseErrors() > 0)
75 {
76
77 outputValue = value;
78
79
80 String errorLog = errorWriter.toString();
81 instance.setStateValue(contextNode, TIDY_ERROR_LOG, errorLog);
82 }
83 else
84
85 {
86 outputValue = outputStream.toString("UTF-8");
87 }
88
89 outputValue = stripHTMLHead(outputValue);
90
91 super.setValue(instance, outputValue);
92 }
93 catch(java.io.UnsupportedEncodingException e)
94 {
95
96 }
97
98
99
100 }
101
102 /*** Removes everything but <code><body></code> tag contents. */
103 private String stripHTMLHead(String htmlDoc)
104 {
105 int bodyStartIndex = htmlDoc.indexOf("<body");
106 int bodyEndIndex = htmlDoc.indexOf("</body>");
107
108 if(bodyStartIndex > -1)
109 {
110 for(int i = bodyStartIndex; i < bodyEndIndex; i++)
111 {
112 if(htmlDoc.charAt(i) == '>')
113 {
114 bodyStartIndex = i+1;
115 break;
116 }
117 }
118
119 if(bodyStartIndex < bodyEndIndex)
120 {
121 return htmlDoc.substring(bodyStartIndex, bodyEndIndex);
122 }
123 }
124
125 return htmlDoc;
126 }
127
128 public boolean hasError(InstanceImpl instance)
129 {
130 return (getTidyErrorLog(instance) != null);
131 }
132
133 public String getTidyErrorLog(InstanceImpl instance)
134 {
135 org.dom4j.Node contextNode = ((ReferenceSingle)ref).getContextNode(instance);
136 return (String)(instance.getStateValue(contextNode, TIDY_ERROR_LOG));
137 }
138
139
140
141
142 /*** Gets a Tidy instance which will be used by this control.
143 */
144 protected void init(UI ui)
145 throws ConstructionException
146 {
147 super.init(ui);
148 FormsService formToolService = ui.getForm().getFormToolService();
149 if(tidyConfiguration == null)
150 {
151 tidyConfiguration = formToolService.getTidyConfiguration();
152 }
153 }
154 }