KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > html > editor > coloring > EmbeddingUpdater


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2007 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20
21 package org.netbeans.modules.html.editor.coloring;
22
23 import java.util.List JavaDoc;
24 import java.util.logging.Level JavaDoc;
25 import java.util.logging.Logger JavaDoc;
26 import javax.swing.text.BadLocationException JavaDoc;
27 import javax.swing.text.Document JavaDoc;
28 import org.netbeans.api.html.lexer.HTMLTokenId;
29 import org.netbeans.api.lexer.Language;
30 import org.netbeans.api.lexer.Token;
31 import org.netbeans.api.lexer.TokenHierarchy;
32 import org.netbeans.api.lexer.TokenSequence;
33 import org.netbeans.editor.BaseDocument;
34 import org.netbeans.editor.BaseDocument;
35 import org.netbeans.editor.ext.html.parser.SyntaxElement;
36 import org.netbeans.editor.ext.html.parser.SyntaxParserListener;
37
38 /**
39  * Listens on HTML parser changes and updates embedding of nested languages accordingly.
40  *
41  * @author Marek.Fukala@Sun.com
42  */

43 public class EmbeddingUpdater implements SyntaxParserListener {
44     
45     private static final String JavaDoc JAVASCRIPT_MIMETYPE = "text/javascript";//NOI18N
46

47     //XXX update mimetype once Hanz fixes the mimetype in CSS editor module
48
private static final String JavaDoc CSS_MIMETYPE = "text/css2"; //NOI18N
49

50     private static final String JavaDoc HTML_SCRIPT_TAG_NAME = "script"; //NOI18N
51

52     private static final Logger JavaDoc LOGGER = Logger.getLogger(EmbeddingUpdater.class.getName());
53     
54     private final Document JavaDoc doc;
55     
56     private int scriptStart;
57     
58     public EmbeddingUpdater(Document JavaDoc doc) {
59         this.doc = doc;
60     }
61     
62     public void parsingFinished(List JavaDoc<SyntaxElement> elements) {
63         scriptStart = -1;
64         for(SyntaxElement sel : elements) {
65             if(sel.getType() == SyntaxElement.TYPE_TAG) {
66                 startTag((SyntaxElement.Tag)sel);
67             } else if(sel.getType() == SyntaxElement.TYPE_ENDTAG) {
68                 endTag((SyntaxElement.Named)sel);
69             }
70         }
71     }
72     
73     private void startTag(SyntaxElement.Tag sel) {
74         //script tag content embedding
75
if(HTML_SCRIPT_TAG_NAME.equals(sel.getName())) {
76             scriptStart = sel.getElementOffset() + sel.getElementLength();
77         }
78         //various attributes values embedding
79
for(SyntaxElement.TagAttribute tagattr : sel.getAttributes()) {
80             if("style".equalsIgnoreCase(tagattr.getName())) { //NOI18N
81
//XXX we need to look for it just in certain html tags
82
createEmbedding(CSS_MIMETYPE, tagattr);
83             } else if(tagattr.getName().startsWith("on") || tagattr.getName().startsWith("ON")) {
84                 //XXX very simple algorithm for finding "onclick" like attributes
85
//should be restricted according to the html specification
86
createEmbedding(JAVASCRIPT_MIMETYPE, tagattr);
87             }
88         }
89     }
90     
91     private void endTag(SyntaxElement.Named sel) {
92         if(HTML_SCRIPT_TAG_NAME.equals(sel.getName())) {
93             if(scriptStart != -1) {
94                 createEmbedding(JAVASCRIPT_MIMETYPE, scriptStart, sel.getElementOffset() - 1, 0,0);
95             }
96         }
97     }
98
99     private void createEmbedding(String JavaDoc mimeType, SyntaxElement.TagAttribute tagAttr) {
100         if(tagAttr.getValue().charAt(0) == '\'' || tagAttr.getValue().charAt(0) == '"') {
101             //cut off the qutation marks
102
createEmbedding(mimeType, tagAttr.getValueOffset(), tagAttr.getValueOffset() + tagAttr.getValue().length(), 1, 1);
103         } else {
104             createEmbedding(mimeType, tagAttr.getValueOffset(), tagAttr.getValueOffset() + tagAttr.getValue().length(), 0, 0);
105         }
106     }
107     
108     private void createEmbedding(String JavaDoc mimeType, int startOffset, int endOffset, int startSkipLength, int endSkipLength ) {
109         Language lang = Language.find(mimeType);
110         if(lang == null) {
111             LOGGER.log(Level.WARNING, "No " + mimeType + " language found! (" + startOffset + " - " + endOffset + ")");
112             return ; //no language found
113
}
114         
115         ((BaseDocument)doc).readLock();
116         try {
117             TokenHierarchy th = TokenHierarchy.get(doc);
118             TokenSequence ts = tokenSequence(th, scriptStart);
119             
120             ts.move(startOffset);
121             if(!ts.moveNext()) {
122                 return ; //no token
123
}
124             
125             do {
126                 Token item = ts.token();
127                 if(!ts.createEmbedding(lang, startSkipLength, endSkipLength)) {
128                     LOGGER.log(Level.WARNING, "Cannot create embedding for " + mimeType + ".");
129                 } else {
130                     LOGGER.log(Level.INFO, "Embedding for " + mimeType + " created [" + startOffset + " - " + endOffset + "] (" + item.text().toString() + ")");
131                 }
132             } while(ts.moveNext() && ts.offset() <= endOffset);
133         }finally {
134             ((BaseDocument)doc).readUnlock();
135         }
136     }
137     
138     
139     private static TokenSequence tokenSequence(TokenHierarchy hi, int offset) {
140         TokenSequence ts = hi.tokenSequence(HTMLTokenId.language());
141         if(ts == null) {
142             //HTML language is not top level one
143
ts = hi.tokenSequence();
144             ts.move(offset);
145             if(!ts.moveNext()) {
146                 return null; //no token found
147
} else {
148                 ts = ts.embedded(HTMLTokenId.language());
149             }
150         }
151         return ts;
152     }
153     
154     
155     
156 }
157
Popular Tags