GWTで作ってみた
Twitterのユーザー名で検索すると、その人のアイコン、名前、紹介分が表示され
その下にフォローしてる人たちのアイコン、タイムラインが表示される簡単なやつ。
なんかWindowsアプリみたいな感覚でできるのが驚き。
あと、ソースコードはutf8にしないと日本語文字化けるので気をつける。
エントリーポイント
package org.ham007.twitterviewer.client; import com.google.gwt.core.client.EntryPoint; import com.google.gwt.user.client.ui.RootPanel; public class TwitterViewer implements EntryPoint { public void onModuleLoad() { MainPage main_page = new MainPage(); main_page.setWidget(RootPanel.get("main_panel")); } }
ページクラス
package org.ham007.twitterviewer.client; public class MainPage implements KeyDownHandler, ClickHandler { //サービス private final GetTwitterUserServiceAsync sv_getuser = GWT.create(GetTwitterUserService.class); private final GetFriendTimeLineServiceAsync sv_gettimeline = GWT.create(GetFriendTimeLineService.class); //メイン private final VerticalPanel main_panel = new VerticalPanel(); //検索領域 private final HorizontalPanel search_panel = new HorizontalPanel(); private final TextBox txt_userid = new TextBox(); private final Button btn_search = new Button("Search"); //検索結果表示 private final HTML result_usr_html = new HTML(); //タイムライン private final Grid time_line_grid = new Grid(); public MainPage(){ search_panel.add(txt_userid); search_panel.add(btn_search); txt_userid.addKeyDownHandler(this); btn_search.addClickHandler(this); main_panel.add(search_panel); main_panel.add(result_usr_html); main_panel.add(time_line_grid); } public void setWidget(RootPanel root_panel){ root_panel.add(main_panel); } @Override public void onKeyDown(KeyDownEvent event) { if(event.getNativeKeyCode() == KeyCodes.KEY_ENTER) procSearch(); } @Override public void onClick(ClickEvent event) { procSearch(); } private void procSearch(){ procDispUser(); procDispTimeLine(); } private void procDispUser(){ sv_getuser.getUser(txt_userid.getText(), new AsyncCallback<TwitterUserBean>(){ @Override public void onFailure(Throwable caught) { //Todo:ダイアログボックス表示でエラーを伝える caught.printStackTrace(); } @Override public void onSuccess(TwitterUserBean result) { //Todo:やっぱりこういうのは仕方ない? StringBuilder sb = new StringBuilder(); sb.append("</br>Your Infomation</br>"); sb.append("<table border=\"1\">"); sb.append("<tr>"); sb.append("<td>"); sb.append("<img src=\"" + result.getPofileImageUrl() + "\" alt=\"アイコン\" />"); sb.append("</td>"); sb.append("<td>"); sb.append(result.getScreenName()); sb.append("</td>"); sb.append("</tr>"); sb.append("<tr>"); sb.append("<td colspan=\"2\">"); sb.append(result.getDescription()); sb.append("</td>"); sb.append("</tr>"); sb.append("</table></br>"); result_usr_html.setHTML(sb.toString()); } }); } private void procDispTimeLine(){ sv_gettimeline.getTimeLine(txt_userid.getText(), new AsyncCallback<List<TwitterStatusBean>>(){ @Override public void onFailure(Throwable caught) { //Todo:ダイアログボックス表示でエラーを伝える caught.printStackTrace(); } @Override public void onSuccess(List<TwitterStatusBean> result) { time_line_grid.resize(result.size() + 1, 2); time_line_grid.setBorderWidth(1); //ヘッダ設定 time_line_grid.setText(0, 0, "Icon"); time_line_grid.setText(0, 1, "Message"); for(int i=0;i<result.size();i++){ HTML img = new HTML(); TwitterUserBean usr = result.get(i).getUser(); img.setHTML("<a href=\"http://www.twitter.com/" + usr.getScreenName() + "\" target=\"_blank\"><img src=\"" + usr.getPofileImageUrl() + "\" alt=\"" + usr.getName() + "\" /></a>"); int row_idx = i + 1; time_line_grid.setWidget(row_idx, 0, img); time_line_grid.setText(row_idx, 1, result.get(i).getText()); } } }); } }
ユーザー情報取得サービスインターフェイス
package org.ham007.twitterviewer.client.service; @RemoteServiceRelativePath("gettwitteruser") public interface GetTwitterUserService extends RemoteService { TwitterUserBean getUser(String target_id); } public interface GetTwitterUserServiceAsync { void getUser(String target_id, AsyncCallback<TwitterUserBean> callback); }
Twitterユーザー情報取得サービスサーバー実装
外部ライブラリのtwitter4jを使用
外部ライブラリ使用時は手動で、war\WEB-INF\libフォルダにjarファイル配置する必要あり?
自環境、設定では手動で配置しないとClassNotFoundExceptionを吐いた。
package org.ham007.twitterviewer.server.service; @SuppressWarnings("serial") public class GetTwitterUserServiceImpl extends RemoteServiceServlet implements GetTwitterUserService { @Override public TwitterUserBean getUser(String target_id) { try { //MyTwitter -> シングルトンなクラス。Twitterインスタンスを取得する。 Twitter twitter = MyTwitter.get(); User user = twitter.getUserDetail(target_id); TwitterUserBean usr_bean = new TwitterUserBean(); setupTwitterUserBean(usr_bean, user); return usr_bean; } catch(TwitterException e) { e.printStackTrace(); return null; } } private void setupTwitterUserBean(TwitterUserBean bean, User org){ bean.setDescription(org.getDescription()); bean.setId(org.getId()); bean.setName(org.getName()); bean.setPofileImageUrl(org.getProfileImageURL().toString()); bean.setScreenName(org.getScreenName()); if(org.getURL() != null) bean.setUrl(org.getURL().toString()); } }
twitter4j.Userの簡易ラッパークラス。
サーバーから戻ってくるユーザー定義クラスの例
client側のパッケージに配置する必要がある。
プリミティブ型、コレクション、IsSerializable実装クラス以外は使用できない。
(コメントアウト箇所は実行時エラーになる。)
package org.ham007.twitterviewer.client; //import twitter4j.User; import com.google.gwt.user.client.rpc.IsSerializable; public class TwitterUserBean implements IsSerializable { private int id = Integer.MIN_VALUE; private String name = ""; private String screenName = ""; private String description = ""; private String profileImageUrl = ""; private String url = ""; public TwitterUserBean(){} // public TwitterUserBean(User src){ // id = src.getId(); // name = src.getName(); // screenName = src.getScreenName(); // description = src.getDescription(); // profileImageUrl = src.getProfileBackgroundImageUrl(); // // if(src.getURL() != null) // url = src.getURL().toString(); // } public int getId(){ return id; } public void setId(int id){ this.id = id; } public String getName(){ return name; } public void setName(String name){ this.name = name; } public String getScreenName(){ return screenName; } public void setScreenName(String screenName){ this.screenName = screenName; } public String getDescription(){ return description; } public void setDescription(String description){ this.description = description; } public String getPofileImageUrl(){ return profileImageUrl; } public void setPofileImageUrl(String profileImageUrl){ this.profileImageUrl = profileImageUrl; } public String getUrl(){ return url; } public void setUrl(String url){ this.url = url; } @Override public String toString() { StringBuilder sb = new StringBuilder(); sb.append("Id:"); sb.append(addWQ(Integer.toString(id))); sb.append("Name:"); sb.append(addWQ(name)); sb.append("ScreenName:"); sb.append(addWQ(screenName)); sb.append("Description:"); sb.append(addWQ(description)); sb.append("ProfileImageUrl"); sb.append(addWQ(profileImageUrl)); sb.append("Url"); sb.append(addWQ(url)); return sb.toString(); } private String addWQ(String val){ return "\"" + val + "\""; } }