テーマなんて特に無いです。多人数で同じキャンバスに絵を書くアプリで、一般的にはなんていうのかな、お絵描きチャットとでも言うんでしょうか。そんなようなものです。仕組みとしてはいたってシンプルです。Preview1をベースにプロジェクトを作成。ViewはRazorです。ここは実質ほとんど処理もなく、Webアプリケーションの構造を制御するためと、サーバーサイドでサムネイル画像を生成するくらいのシンプルな構造です。Servicesを使ってます。XMLではなくクライアントサイドのJavaScriptからJSONでデータの取得・更新・削除をRESTで行うのに、これより簡単に実装する方法はないんじゃないでしょうか。実質EFでモデルを定義し、標準テンプレートにジェネリッククラスに指定するくらいしか作業はない感じですよね。今回は少しWebGetで機能を追加してます。残るはクライアントサイドのJavaScriptで、HTML5のCanvas要素にレンダリングしたりXHRを使った通信部の実装です。テクノロジ最前線と現実解を語ろう」が、BoFのタイトルでしたよね。覚えてますか?ということで、今回のデモで使ったテクノロジは以下の通り。ServicesHTML5(Canvas)CSS3jQueryMVCの中ではViewに対してデータをほとんど送ってないです。これはつまりMVCでデータ制御をほとんど行ってないからです。Servicesで通信してるので、クライアント部をSilverlightにしたとしても、そのままデータは利用できるので、もっとリッチなキャンバスを作るのも面白いかもです。四の五の言わずにソースコードですよね。今回はCodePlexにTFSでアップしようと思って、いろいろ試したんですが...。うまくできてないです。SkyDriveに置いておきます。↑ここからダウンロードして展開してソース見てみてね!データベースのセットアップはスクリプトになってるので、MvcGraffitiという名前でデータベースを作成後(なんでもいいです)Databases\MvcGraffiti.sqlを実行してテーブルを作成してください。BoFで使ったデータもそれぞれスクリプトにしています。作ったデータベースに合わせてWeb.configのconnectionStringを適当にいじってください。うまくいかない場合は連絡いただければできる範囲で対応していきます。このエントリのコメント欄によろしくです。今回のサンプルはwebkit系ブラウザにのみ最適化して作ってます。HTML5対応してるとうたっている他の実装ではちゃんと動きません。座標の計算とかの部分がちょっとへんちくりん。PCでのお勧めはSafariではなくChrome。いうとSafariではWheelイベントが発生しなくてマウスのコロコロをつかったズームが効かない(Zoom自体はCSSのZoomを使ってます)から。SafariとしてiPhone4とiPadで動作確認してます。こちらはWheelイベントではなくTouch系イベントをハンドリングしてます。JSのソースを見てもらうとわかるんですが、PC向けのMouseInputクラスとMobile向けのTouchPanelInputという2種類のクラスを用意して入力デバイスごとの処理を記述してます。いっても、イベントのハンドリングと座標の取得方法が違うくらいですが(そこが一番面倒...)。Safariを使った場合、指2本でズームしたり、キャンバスをドラッグできるようになってるので試してみてください。この辺、意外と知られてないと思いますが、イベントハンドリングして自分ですべて実装する必要があります。ただのHTMLに対してはそんなことしなくてもいいんですけど、今回Canvasお絵かきなので楽はできないってことですね。MVC3になって目に見えて違うのはViewDataのほかにViewModelプロパティ経由でViewにデータを渡せるようになってるところでしょうか。ModelBinderは今回のデモで使ってないので。ViewModelはdynamic型なので、データだけじゃなくFunc<T>渡せます。今回のデモの中でIPアドレスをViewで表示してるところが無駄にこの機能を使って、IPアドレスそのものではなく、IPアドレスを返すデリゲート経由でViewは表示してます。GraffitisControllerの36行目と、List.cshtmlの31行目。使い過ぎ注意ですけど(特にデータをどうのこうのするようなものには適用しないほうがいいかも)。VS2010だとしても、まだRazorに対する対応はできていないので、コードハイライトもインテリセンスも効きません。なにも設定しないと、VS2010がただのメモ帳です。コードハイライトだけでも行いたい場合は拡張しcshtmlにたいしてHTMLエディタを関連付けしてみましょう。すると↑こんな感じにはなります。Highlighter"を入れるとかでしょうか。黒バックの場合切ない表示になるので個人的には使ってないですが、白バックならきれいに表示されます。あと、Razorの構文については英語の資料になりますが、以下のサイトからダウンロードできます。Syntax200ページ越えです。Preview1のソースをダウンロードするとRazorのパーサーとWebPage関連一式のソースも含まれてる(MVC専用ソースなのがPreview1のかわいげのあるところです)ので、パーサーマニアにはたまらないでしょう。Tipsとしては困ったときの<text/>。これで囲むといったんパースのコンテキストがCodeParserからMarkupParserに切り替わるので、c#の終わりがわからない!と怒られた時には試してみましょう。Servicesと言われていたものです。大きなところではAtomPub/JSONだったのがAtomPub改であるODataに対応してるところですね。それがどううれしいかというと会場でも話しましたが、PowerPivotによるセルフサービスBIの促進による無駄エネルギー使用(レポート作成のエネルギーは顧客が使えばよろし)の撤廃です。この辺話し出すと長くなるのではしょります。デジタルナーバスシステムです。Servicesのレイヤで介入するQueryInterceptorやChangeInterceptorなんかを利用するとスマートにデータアクセスに対して機能拡張が施せます。Homeで公開されているQueryStringによるformat指定Behaviorを使ってみました。プログラム中ではまったく有効利用しません。Servicesの処理が始まる前に$format指定をリクエストヘッダ"accept"に移動させるということをしています。Servicesからすれば普通にContentTypeを指定してリクエストされたものだと判断して処理を進めてくれるので、自分でそれ以上の処理をする必要がなくなるわけですね。今のところAtom/JSONしかないですけど、多分うまいこと介入すればCSVをレンダリングとかもできるんじゃないかとにらんでます。どこかのProviderなんじゃないかな~。デモアプリケーションのJavaScriptの構造としては以下のような感じです。network部はtimerでsend/receiveをくるくる回してます。リアルタイムにはしてないです。サーバーサイドの構造としては以下のような感じです。雑にもほどがある...。あれですよ、デベロッパーたるもの「コードで語ってくれ」ですよ。九十九も「拳で語ってくれ」って言ってたじゃないですか。BoF後に「WebSocketとかもいいですよね!」と声を掛けてくれた方がいましたが、まさにその通りで、今回のようなアプリケーションの場合XHRで処理するよりWebSocketを使ったほうがより効率のいい通信ができるでしょう。あと、コードの9割がJavaScriptだし、iPad持ち出してデモしたりとMSのテクノロジがあまり使われてないじゃないか!なんて野暮なことは言いっこなしです。コード量が少なくて済むというだけです。全体比率としては少ないです。localStorageやsessionStorageなんかを使うと完全にスタンドアロンで動かすこともできるようになるので面白そうですね。SQLをベースにするかPOCOテンプレートを使うほうが使い勝手はいいと思ってます。更新系はMVCでバリデーションかけてそっちから更新する感じです(更新はUIにフィードバックしやすいほうが開発が楽だと思いますがどうでしょう?)。SQLで使いたい場合はどうするのさ、についてはストアドで書いて、DataContext/ObjectContextにはやす感じですね。カスタムなエンティティとして返すもよし、他のテーブルと同じ定義を戻すもよし、です。その後動的に条件を付ける場合はIQueryableにどんどこ追加してしまいましょう。Objectで!だいたい、こんな感じです。わからない・わかりにくい点など多々あると思うので、そんな時には質問いただければと思います。本」っていうのがあるんですが、ちょっといい感じの記述があるので紹介。付録Bの"Yahoo!JAPANが実践するWebの高速化"のB.5.1役割分担。大きく分けて3つの開発フェーズがありコンテンツの情報を設計する「インタラクションデザイン」フェーズコンテンツの見た目をデザインする「ビジュアルデザイン」フェーズコンテンツのHTML/CSSを実装する「ウェブデベロップメント」フェーズとなります。ここでWD(ウェブデベロッパー)とFEE(フロントエンドエンジニア)という役割がありまして、それぞれ担当するフェーズも違うわけですね。ここが難しいところなんですが、「デザインはデザイナー」というのが口癖のこの業界、デザインとは何を指しているのでしょう。見た目だけ?動きのある場合は動きもデザインするのがデザイナー?そもそもの情報設計はデザイナー関与せず?HTML/CSSの実装は?その辺のふわっとした垣根のおかげで、お互いが密に連携できず、特に会社が別々だったりすると誰がどこまで担当してるのかで、ごにょごにょな状態になりやすかったりね。WebMatrixはフェーズの違う部分の発生するロスを減らしていくためにフェーズをまたいだツールとしての意味もあったりするんじゃないかと勝手に妄想してます。最後に、BoFに参加してくれたたくさんの開発者の方々、いきなりキャンバス作りまくったり削除しまくったりと、想定外の操作で会場を盛り上げてくれてありがとうございました!質疑応答があまりできなくてすいませんでした。小野さん、ナオキさん、今回も声掛けてくれてありがとうございます。Techdaysのトラウマがはれそうです。WiFiルーターを貸してくれてほんとにありがとう。あれがなかったら会場に来てくれた方々は見るだけで、実際にキャンバスに描くこともできず、企画倒れになるところでした。Toolkitナオキさんに勧められたので調べてみました。公開!まずは、上記サイトからソースとAssemblyをダウンロードしてみました。名前空間がSystem.Web.Mvc.Html5というところがムフフなポイントですね。ソースがあまりにもシンプルで短いので見てみるのをお勧めします。見てみてサンプルを動かしてみました。3大派手機能のうちVideo/Audioのタグには対応。あとはCanvasも同じように作ればいいね!ベースとなるHtml5TextBoxとHtml5RangeNumberはModelStateを取り出してないから、値がバインドしてこないです。InputHelperを使ってるHtml5TextBoxForHelperはViewData.ModelState.TryGetValueでちゃんとバインドしてるから、いろいろ試しながら作ってるのか、意図的にバインドしないようにしてる感じです。type="range"もバインドしてくれていいと思うけどな~。htmlHelper.GetModelStateValueも用意してるんだし。htmlの出力じゃないけど、そんなの気にせずSafari,Chromeはちゃんとレンダリングしてくれるのがすばらしい。Preview1で使ってみましょう。作者のサイトに書かれてる通り、参照設定に追加して、Global.asaxにおまじない。Razorなので、NamespaceをWebPageからHtmlHelperへの拡張メソッドが参照できるように、Global.asaxに以下のように追記。RegisterRoutes(RouteTable.Routes);}ページに直接usingとして書いてもいいですが、すべてのページに書くのは馬鹿らしいじゃないですか。Tumblrにも書いたと思いますが、Preview1ではWeb.configのsystem.web/pages/namespacesはみてくれないです。そこはRTMまでには解決されることでしょう。前回作ったサルベージ用アプリに追加してみる。null).AsHtml()}AsHtml拡張メソッドもがある前提です。対応してるChromeだと↓こんな感じでちゃんとRangeコントローラが出てきます。Firefoxだとまだ対応してないので、type属性無視してTextboxがそのまま表示されます。お手軽でとてもいいじゃないですか!これは楽しい!あと、個人的に面白いと思うのが↓。Framework地味な感じがするけど、ASP.NETらしさ爆発じゃないですかね~。Preview1がとても興味深く、楽しそうなプロダクトで、あれやこれやいじり倒してみたいところですが、なんか忙しかったり、テンション上がらなかったりとエントリ書く気も起きないな~、なんてぼやく日曜日。昔々「オレがルールだ」なんていうブログを書いていたのを。その時のデータベースファイル(MDF)を発掘したので、そこからエントリをサルベージするってどうなんよ、と。Expressにアタッチしたのはいいけど、そのままテキストだけだと画像なんかも見れないし、なんか良く解らん状態。Razorで参照専用のWebアプリを書いてみたわけです。書くと言っても参照専用なのでほとんどすることはないんですけどね。EF4CTP1でも使おうかと思ったけど、インストールしてないし、するのも面倒だから、既にインストール済みのPOCOテンプレートを使ってみました。これまた特にすることもなく、EDMX作ってカスタムツール外して、ファイル名をttに埋め込むだけなんですけどね。MOVIE見ながらチクチクと。書いてて気がついたんですが、RazorってデフォルトHTMLEncodeかけるんですね。HTMLをそのまま出力したいときにはどうしましょう...。以下のようなヘルパーを用意しておくことで簡単に出力できるとStackoverflow.com先生が教えてくれました。</div>グダグダ前置き長くてすいません。いうわけで第1弾「もっと速く出来ると思う」です。18:52:29ここ最近Philさんのブログでホットな話題になってる名前書式化スピード競争。Cases↑このエントリで始まって、Philさんが「オレのんが速え~」って事でコードを載せてたけど、ここにきて新たな刺客登場。Redux正規表現だから遅いんじゃないぜ!といわんばかりにJamesFormatterを作成したJamesさん。Weichersさん。いずれもPhilさんの速度を超えた。通常のstring.Format(”書式化文字列”,value)の書式化では引数のインデックスを埋め込むけど、匿名クラスのパラメータ名を渡して書式化出来るようにすること。テストがちゃんと通ること。Hello!."になる。速いコードを書く事に慣れてないから苦戦すると思ったけど...。誰よりも速えーじゃねーか。※順番で不公平(なわけないけど)だ!なんて言われてもイヤなんで、最初と最後の2箇所で。そんなに難しいコードじゃなくて、テストを通すことと、書式化文字列がもっと長い場合とかは考慮せず、シンプルに書いてみた。