センサーとサウンドの処理を組み込んでアプリを完成させる
前回は、マーケットプレイスで無料公開している英語版の傾斜計アプリ「Sound Clinometer Ver.0.8」の実装内容について解説しました。今回はプログラムについて解説します。
サンプルプロジェクト一式は、会員限定特典としてダウンロードできます。記事末尾をご確認ください。
今回開発するアプリの機能とページ構成については、前回の記事を参照してください。このアプリは、Silverlightアプリケーションで、開発言語はVisual Basicです。
筆者の開発環境は以下のとおりです。
- Windows 7 Professional (32 bit) SP1
- Visual Studio 2010 Ultimate SP1 (英語版)
- Windows Phone SDK 7.1.1 (英語版)
- Expression Blend 4 (英語版)
- Expression Design 4 (英語版)
- Steinberg Cubase 5(英語版)
- 巡音ルカ、ヘルプ用の画像加工の一部にAdobe Photoshop Elements 7
動作確認はWindows Phone Emulator、実機(Windows Phone au IS12T)です。
画面キャプチャのメニューは英語ですが、日本語版も手順は同じです。
メインページ(メニュー選択)の実装
新規プロジェクトの作成とページ追加
では、早速開発方法を見ていきましょう。前回記事で述べたとおり、今回のアプリは、メインページ、処理ページ、ヘルプページの3ページで構成します。
「ファイル/ File 」「新規/ New 」「プロジェクト/ Project…」を選択し、開発言語として「Visual Basic」を選択、「Silverlight For Windows Phone」「Windows Phone Application」を選択します。プロジェクト名は、「SoundClinometer」 としておきます。「Windows Phone 7.1」を選択します。
プロジェクト名を右クリックして表示されるメニューから「追加/新規フォルダ」を選択してフォルダを追加し、名前を「Image」としておきます。このImageフォルダを右クリックして表示されるメニューから「追加/既存のアイテム」を選択して、アプリの部品の画像ファイル一式を追加しておきます。
また、「Bell」「Tweet」「Voice」という3つのフォルダを作成し、それぞれのサウンドファイルを追加しておきます(前回2ページ目、図6参照)。
※ダウンロードできるプロジェクト中には、画像ファイルおよびサウンドファイルは追加済みです
メインページ以外の2ページも、先に追加しておきましょう。ソリューションエクスプローラーのプロジェクト名を右クリックして表示される「追加/新しい項目」でPortrait Pageを追加します。名前は、「MyClinometer.xaml」とします。また、Panorama Pageを追加し、名前は「MyClinometerHelp.xaml」としておきます。
メインページのデザイン(MainPage.xaml)
まず、メインページを作成します。
ツールボックスからImageコントロールを3個レイアウトして名前を付け、Sourceには、背景画像、タイトルロゴ、ヘルプのアイコンの各画像を指定します(図1)。
図1:メインページのレイアウト(クリックで拡大) |
Imageコントロールのプロパティを調整し、完成したデザイン・コードは、リスト1になります。
リスト1 メインページのデザイン・コード(MainPage.xaml)
<phone:PhoneApplicationPage x:Class="SoundClinometer.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:phone="clr-namespace:Microsoft.Phone.Controls;assembly=Microsoft.Phone" xmlns:shell="clr-namespace:Microsoft.Phone.Shell;assembly=Microsoft.Phone" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" d:DesignWidth="480" d:DesignHeight="768" FontFamily="{StaticResource PhoneFontFamilyNormal}" FontSize="{StaticResource PhoneFontSizeNormal}" Foreground="{StaticResource PhoneForegroundBrush}" SupportedOrientations="Portrait" Orientation="Portrait" shell:SystemTray.IsVisible="True"> <!--LayoutRoot is the root grid where all page content is placed--> <Grid x:Name="LayoutRoot" Background="Transparent"> <Grid.RowDefinitions> <RowDefinition Height="Auto"/> <RowDefinition Height="*"/> </Grid.RowDefinitions> <!--ContentPanel - place additional content here--> <Grid x:Name="ContentPanel" Grid.Row="1" Margin="0,0,0,0" Background="White"> <!--■背景--> <Image Height="768" Name="SettingBackImage" Stretch="Fill" Width="480" Source="/SoundClinometer;component/Image/MainBackImage.png" Margin="0" /> <!--■ボタン--> <Image Height="280" Name="LogoIcon" Stretch="Fill" VerticalAlignment="Center" HorizontalAlignment="Center" Source="/SoundClinometer;component/Image/TopPageImage.png" Width="279" Margin="100,102,101,386" /> <Image Height="78" HorizontalAlignment="Left" Margin="70,510,0,0" Name="HelpIcon" Stretch="Fill" VerticalAlignment="Top" Width="78" Source="/SoundClinometer;component/Image/HelpIcon.png" /> </Grid> </Grid> </phone:PhoneApplicationPage>
メインページのロジック(MainPage.xaml.vb)
メインページのレイアウトができたら、ソリューションエクスプローラー中のMainPage.xamlを展開して表示されるMainPage.xaml.vbの中に処理を記述していきます(リスト2)。
ロゴの青い花がタップされた時は処理ページ「MyClinometer」に、「?」ボタンがタップされた時はヘルプページ「MyClinometerHelp」に、それぞれ移動させます。
リスト2 メインページのロジック・コード(MainPage.xaml.vb)
Option Strict On Partial Public Class MainPage Inherits PhoneApplicationPage ' Constructor Public Sub New() InitializeComponent() End Sub Private Sub LogoIcon_Tap(sender As Object, e As System.Windows.Input.GestureEventArgs) Handles LogoIcon.Tap NavigationService.Navigate(New Uri("/MyClinometer.xaml?Name=", UriKind.Relative)) End Sub Private Sub HelpIcon_Tap(sender As Object, e As System.Windows.Input.GestureEventArgs) Handles HelpIcon.Tap NavigationService.Navigate(New Uri("/MyClinometerHelp.xaml?Name=", UriKind.Relative)) End Sub End Class
処理ページのデザイン
設定画面のレイアウト(MyClinometer.xaml)
次に、処理ページをレイアウトします。このページは、設定画面と結果表示ウィンドウから成ります。
まず、設定画面のレイアウトを行います。
図2:設定画面のレイアウト(クリックで拡大) |
このページでレイアウトしたButtonコントロールのスタイルについては、次のリスト3 のコードをApp.xaml内の
リスト3 App.xaml内に追加する、ボタンのスタイル設定(App.xaml)
<!--Application Resources--> <Application.Resources> <Style x:Key="BellButtonStyle" TargetType="Button"> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="Button"> <Grid> <Image x:Name="BellButtonImage" Source="/SoundClinometer;component/Image/BellButton.png" Stretch="Fill"/> </Grid> </ControlTemplate> </Setter.Value> </Setter> </Style> <Style x:Key="TweetButtonStyle" TargetType="Button"> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="Button"> <Grid> <Image x:Name="TweetButtonImage" Source="/SoundClinometer;component/Image/TweetButton.png" Stretch="Fill"/> </Grid> </ControlTemplate> </Setter.Value> </Setter> </Style> <Style x:Key="VoiceButtonStyle" TargetType="Button"> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="Button"> <Grid> <Image x:Name="VoiceButtonImage" Source="/SoundClinometer;component/Image/VoiceButton.png" Stretch="Fill"/> </Grid> </ControlTemplate> </Setter.Value> </Setter> </Style> <Style x:Key="StartButtonStyle" TargetType="Button"> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="Button"> <Grid> <Image x:Name="StartButtonImage" Source="/SoundClinometer;component/Image/StartButtonImage.png" Stretch="Fill"/> </Grid> </ControlTemplate> </Setter.Value> </Setter> </Style> </Application.Resources>
XAML図形の描画
さらに、図2の上に、簡単な装飾をほどこしていきます。
2つのスライダーを細く白い枠で囲み、ボリュームを表す三角形を描きます。これらをVisual Studioで作図することは難しいので、Expression Blendを使います(図3)。
図3:Expression Blendで3つの図形を描く(クリックで拡大) |
ソリューションエクスプローラーのプロジェクト名を右クリックして「Expression Blendで開く」を選択します。Expression Blendが起動します(図4)。
図4:Visual Studio から、プロジェクトをExpression Blendで開く(クリックで拡大) |
まず、スライダーを囲む白い枠を、矩形で描きます。「オブジェクトとタイムライン」のLayoutRootをクリックして展開し(図5上左)、さらにContentPanelをクリックして展開した中にある「PreferencePanel」をクリックして選択状態にします(図5上中)。この「PreferencePanel」は設定画面のCanvasに付けた名前です。
ツールボックス中の矩形(Rectangle)アイコンをクリックし(図5上右)、プレス&ドラッグしながらスライダーを囲みます(図5下)。
図5:スライダーをRectangleで囲む(クリックで拡大) |
描いた矩形のプロパティを設定し、外観を整えます。名前は「SliderBorder1」とし(図6-(1))、塗り(図6-(2))は「なし」(図6-(3))に設定して、線は(図6-(4))単色とし(図6-(5))、線の色は白色にします(図6-(6))。幅、高さ、左マージン、上マージンを指定して位置を整えます(図6-(7))。
図6:Rectangleの名前とプロパティを設定する(クリックで拡大) |
プロパティが設定できたら、「オブジェクトとタイムライン」に表示されている、このRectangleに付けた名前の「SliderBorder1」をプレス&ドラッグして、「AngleSlider」の上に移動させます(図7)。これにより、白い枠はレンジ設定スライダーの背面にレイアウトされるようになります。
Expression Designのレイヤーウィンドウでは、下に表示されているものほど背面になりますが、Expression Blendの「オブジェクトとタイムライン」およびVisual StudioのXAMLコードでは、上に表示されているものほど背面になりますので、間違えないようにしてください。
図7:描いた枠の階層を変更する(クリックで拡大) |
同様に、ボリューム調整スライダーの周りにも白い矩形を描きます。これもスライダーの背面に移動させます。
次に、ボリュームを表す三角形を描きます。ツールボックスからペンツールを選択し(図8上左)、任意の3点を次々クリックして閉じたパスを描きます(図8上右)。きれいに描けなかった場合は、一度選択ツールをクリックして選択を解除し(図8下左)、アートボードの上でマウスホイールをスクロールして画面を拡大した上で、部分選択ツールをクリックして、三角形のポインタをつまんで移動させて調整します(図8下右)。
図8:ボリュームを表す三角形を描く(クリックで拡大) |
作図した三角形は、グラデーションで塗りつぶします。
三角形が選択されている状態で、塗りに(図9-(1))グラデーションを指定し(図9-(2))、開始の色として(図9-(3))「#FF0080E2」を入力します(図9-(4))。また、終了の色には(図9-(5))「#FF0C3B5C」を指定します(図9-(6))。
図9:三角形をグラデーションで塗りつぶす(クリックで拡大) |
ボリュームを大きくするほど色を濃くしたいので、グラデーションの向きを変更します。グラデーションツールを選択すると、図形の上に向きを表す矢印が表示されるので、これをドラッグして、水平方向へのグラデーションに変更します(図10)。
図10:グラデーションの向きを変える(クリックで拡大) |
このボリュームを表す三角形も、スライダーの背面になるよう階層を移動させます(図11)。
図11:描いた三角形の階層を変更する(クリックで拡大) |
「プロジェクト」の「MyClinometer.xaml」上を右クリックして表示される「Visual Studioで編集」を選択して、Visual Studioに戻ります。Expression Blendで行った作業を反映させます(図12)。
図12:Expression BlendからVisual Studioに戻る(クリックで拡大) |
以上の作業により、レンジ設定のスライダー部分には次のコードが追加されます(リスト4)。
リスト4 レンジ設定のスライダー部分に追加されるコード(MyClinometer.xaml)
<Rectangle x:Name="SliderBorder1" Height="14" Canvas.Left="116" Canvas.Top="166" Width="337" Stroke="White"/>
また、ボリューム設定のスライダー部分には次のコードが追加されます(リスト5)。
リスト5 ボリューム設定のスライダー部分に追加されるコード(MyClinometer.xaml)
<Rectangle x:Name="SliderBorder2" Height="14" Canvas.Left="116" Canvas.Top="467" Width="337" Stroke="White"/>
ボリュームを表す三角形として、次のようなコードが追加されます。ただし、描き方によって座標値は異なる場合があります(リスト6)。
リスト6 ボリューム設定のスライダー部分に追加されるコード(MyClinometer.xaml)
<Path Data="M146.93466,273.24081 L423.00073,273.3342 L423.00073,224.80177 z" Height="36" Canvas.Left="116" Stretch="Fill" Canvas.Top="431" UseLayoutRounding="False" Width="337"> <Path.Fill> <LinearGradientBrush EndPoint="0.996,0.993" StartPoint="0,1"> <GradientStop Color="#FF0080E2" Offset="0"/> <GradientStop Color="#FF0C3B5C" Offset="1"/> </LinearGradientBrush> </Path.Fill> </Path>
最後に、レンジ設定横のWindows Phoneの絵の回転処理に必要なコードを追加します(リスト7、3~5行目)。
リスト7 Windows Phoneの絵の回転処理のコード(MyClinometer.xaml)
<Image Canvas.Left="27" Canvas.Top="169" Height="85" x:Name="DrawAngle" Stretch="Fill" Width="85" Source="/SoundClinometer;component/Image/DrawAngle.png" /> <Image Canvas.Left="27" Canvas.Top="169" Height="83" x:Name="WindowsPhone" Stretch="Fill" Width="88" Source="/SoundClinometer;component/Image/WindowsPhone.png"> <Image.Projection> <PlaneProjection x:Name="myPhoneProjection" CenterOfRotationX="0" CenterOfRotationY="0" /> </Image.Projection> </Image>
「Sound Clinometer Ver.0.8」プロジェクト一式