2009-07-26
While testing out the Chromium browser, I found out that my Devil's Dictionary Pyjamas project does not work with the test browser. After a bit more research, I discovered that the code doesn't work in the Chrome browser, IE8, or IE7. Having subscribed to the Pyjamas developers mailing list, I know that the browser problems are going to be fixed; and I will help the developers by testing in various browsers and submitting debugging information. However......
Since I am currently working on a production level web application, and the bug fixes for Pyjamas will take a while to implement, I need a way to make my current code run properly in as many browsers as possible. It would appear that the only option available to me is to port my code to Java and compile with GWT. Talk about an odd turn of events.
Before diving into porting my big app from Python to Java, I thought it would be a good idea to get some porting practice by converting the Pyjamas Devil's Dictionary to Java. Armed with Geany and the GWT documentation, I created the following:
Well there you have it. The compiled web application is viewable at www.jezra.net/code_examples/gwt_devil/
I won't get into the specifics of setting up a GWT development environment since the GWT website does a spectacular job of walking one through the set up process.
Having never coded in Java before, I'm sure there are a few things that could be cleaned up quite a bit, but the main take-away is that the finished product works as expected and I'll shouldn't have too much trouble porting my larger project to GWT. As a quick dabble into Java, I realized there was still much about the langauge that I need to learn even if I only plan on creating GWT web applications, and although this may sound odd, I was extremely happy that I could use a java HashMap to store data. Yea data storage makes me happy.
Moving forward, it would probably be best if I updated my development environment to use the Eclipse IDE with a GWT plugin; which should show me some of my errors before I build and test.
Since I am currently working on a production level web application, and the bug fixes for Pyjamas will take a while to implement, I need a way to make my current code run properly in as many browsers as possible. It would appear that the only option available to me is to port my code to Java and compile with GWT. Talk about an odd turn of events.
Before diving into porting my big app from Python to Java, I thought it would be a good idea to get some porting practice by converting the Pyjamas Devil's Dictionary to Java. Armed with Geany and the GWT documentation, I created the following:
package net.jezra.client; //the gwt core bits import com.google.gwt.core.client.EntryPoint; import com.google.gwt.core.client.GWT; //the handlers and events import com.google.gwt.event.dom.client.ChangeHandler; import com.google.gwt.event.dom.client.ChangeEvent; //we need to make requests import com.google.gwt.http.client.Request; import com.google.gwt.http.client.RequestBuilder; import com.google.gwt.http.client.RequestCallback; import com.google.gwt.http.client.RequestException; import com.google.gwt.http.client.Response; //the request will return XML import com.google.gwt.xml.client.XMLParser; import com.google.gwt.xml.client.Document; import com.google.gwt.xml.client.Node; import com.google.gwt.xml.client.NodeList; import com.google.gwt.xml.client.Element; import com.google.gwt.xml.client.DOMException; //the ui widgets import com.google.gwt.user.client.ui.HTML; import com.google.gwt.user.client.ui.Label; import com.google.gwt.user.client.ui.RootPanel; import com.google.gwt.user.client.ui.ListBox; import com.google.gwt.user.client.ui.VerticalPanel; import com.google.gwt.user.client.ui.HorizontalPanel; //I want to store data in a HashMap import java.util.HashMap; /* this class defines the app */ public class devil implements EntryPoint { //how are we going to store the parsed data? private final HashMap dict_words = new HashMap(); //what needs to be scoped to the class? private ListBox wordsListBox; private Label messageLabel; private Label wordLabel; private HTML definitionHTML; /* this is the start of the app */ public void onModuleLoad() { //create a vertical panel to hold most of our info final VerticalPanel vPan = new VerticalPanel(); //make a label for "devils dictionary final Label title = new Label("The Devil's Dictionary (L through Z)"); //give credit to the author final Label by = new Label("by Ambrose Bierce"); //give titles to the labels so we can style them with a CSS title.setStyleName("dd_title"); by.setStyleName("dd_by"); //add the labels to the vertical panel vPan.add(title); vPan.add(by); //create a listbox to display the words wordsListBox = new ListBox(); //make the wordslistbox a dropdownlist wordsListBox.setVisibleItemCount(20); //hide the wordslistbox wordsListBox.setVisible(false); //add the listener to the listbox wordsListBox.addChangeHandler(new ChangeHandler(){ public void onChange(ChangeEvent event) { word_list_changed(); } }); //make an HTML text thingy to hold the definition of the word definitionHTML = new HTML(""); //hide the definition definitionHTML.setVisible(false); //add the definition to the vert panel //vPan.add(definitionHTML) HorizontalPanel hPan = new HorizontalPanel(); //add some spacing for the hPan elements hPan.setSpacing(10); hPan.add(wordsListBox); VerticalPanel vPan2 = new VerticalPanel(); wordLabel = new Label(""); vPan2.add(wordLabel); vPan2.add(definitionHTML); hPan.add(vPan2); vPan.add(hPan); //make a label to pass messages to the user in case of a problem messageLabel = new Label("running..."); //set the style for the messageLabel messageLabel.getElement().setId("info_label"); //add the messageLabel to the vert panel vPan.add(messageLabel); //add the vertical panel to the rootpanel RootPanel.get("content").add(vPan); //get the dictionary file get_dictionary_xml(); } private void word_list_changed() { //get the current index of the wordslistbox int selected_index = wordsListBox.getSelectedIndex(); String word = wordsListBox.getValue(selected_index); display_definition(word); } private void display_definition(String word) { wordLabel.setText(word); String definition = (String)dict_words.get(word); definitionHTML.setHTML("<pre>"+definition+"</pre>"); definitionHTML.setVisible(true) ; } private void set_message(String message) { messageLabel.setText(message); } private void get_dictionary_xml() { //display a message set_message("retrieving XML data..."); //where does the data reside? String url = GWT.getHostPageBaseURL() + "dictionary.xml"; //create a request builder //we are doing a basic "get" RequestBuilder requester = new RequestBuilder(RequestBuilder.GET, url); //try send the request try { requester.sendRequest(null,new RequestCallback() { public void onError(Request request, Throwable exception) { set_message("Error: Couldn't retrieve file"); } public void onResponseReceived(Request request, Response response) { if (200 == response.getStatusCode()) { set_message("data received"); //parse the response text parse_response( response.getText() ); } else { set_message("Couldn't retrieve file (" + response.getStatusText()+ ")"); } } }); } catch (RequestException e) { set_message("Error: "+e.getMessage() ); } } // what do we do with the returned data? private void parse_response(String responseText) { set_message("parsing response"); try { //parse the xml Document xmldoc = XMLParser.parse(responseText); //get the elements NodeList elements = xmldoc.getElementsByTagName("element"); for(int i=0; i<elements.getLength(); i++) { Element element = (Element)elements.item(i); String word = element.getElementsByTagName("word").item(0).getFirstChild().getNodeValue(); String desc = element.getElementsByTagName("desc").item(0).getFirstChild().getNodeValue(); //put the data into the HashMap dict_words.put(word,desc); //add the word to the wordsListBox wordsListBox.addItem(word); } set_message(""); //show the wordsList wordsListBox.setVisible(true); }catch(DOMException e) { set_message("Error: "+e.getMessage() ); } } }
Well there you have it. The compiled web application is viewable at www.jezra.net/code_examples/gwt_devil/
I won't get into the specifics of setting up a GWT development environment since the GWT website does a spectacular job of walking one through the set up process.
Having never coded in Java before, I'm sure there are a few things that could be cleaned up quite a bit, but the main take-away is that the finished product works as expected and I'll shouldn't have too much trouble porting my larger project to GWT. As a quick dabble into Java, I realized there was still much about the langauge that I need to learn even if I only plan on creating GWT web applications, and although this may sound odd, I was extremely happy that I could use a java HashMap to store data. Yea data storage makes me happy.
Moving forward, it would probably be best if I updated my development environment to use the Eclipse IDE with a GWT plugin; which should show me some of my errors before I build and test.
did you get this sorted out in the end?
l.