連載:VS 2005でいってみようDBプログラミング

第5回 開発生産性を向上させるASP.NET 2.0のサーバ・コントロール

山田 祥寛(http://www.wings.msn.to/
2006/07/01
Page1 Page2 Page3 Page4

TreeViewコントロールでツリー・メニューを作成する

 TreeViewコントロールは、エクスプローラによく似たツリー形式のビューを作成するためのサーバ・コントロールです。

.NET TIPS:[ASP.NET]Webフォーム上でサイト・メニュー/サイト・パスを作成するには?

 SiteMapDataSourceコントロールと併せて利用すれば、「サイトマップ情報ファイル(Web.sitemap)」と呼ばれるXML形式のサイト情報を定義しておくだけで、サイト・メニューをコーディングレスで作成できます。

 サイトマップ情報ファイルはごくシンプルなフォーマットでもあり、誰でもすぐに記述することができますが、サイトが大規模になった場合には、サイト情報をXMLファイルで管理することを面倒に感じるかもしれません。

 そこで本節ではデータベース上で管理しているサイト情報をTreeViewコントロールに展開してみることにします。


図10 サイト情報をツリー表示するサンプル・アプリケーションの実行結果
データベース上で管理しているサイト情報をツリー形式で表示する。

 本節のサンプルを実行するに当たっては、以下の表7のようなsitemapテーブルを作成しておく必要があります。

フィールド名 データ型 概要
mid INT メニューコード(主キー)
url VARCHAR(255) URL
title VARCHAR(50) メニュー名
description VARCHAR(50) メニューの概要
parent INT 親メニューコード(mid列に対応。0の場合は親を持たない)
表7 sitemapテーブルの構造

 また、sitemapテーブルには以下の表8の例に従って、具体的なサイト情報を格納しておいてください。

mid url title description parent
1
~/Default.aspx 10日でおぼえるASP.NET入門教室 10日間のレッスン形式で確実にステップアップ
0
2
~/day01.aspx ASP.NETの基本的なしくみを覚えよう ASP.NETの基本を学ぶ
1
3
~/day02.aspx マスタページでアプリ共通機能を作成しよう アプリケーションの共通機能を理解する
1
4
~/day03.aspx データアクセス・コントロールで簡単 データベース連携 データベース連携
1
5
~/day01-1.aspx おぼえようASP.NETの基本のキ ASP.NETの基本
2
6
~/day01-2.aspx 数当てゲームを作成してみよう ビューステート連携
2
7
~/day01-3.aspx ファイルアップロード機能を実装しよう FileUploadコントロール
2
表8 sitemapテーブルのデータ(例)

 このsitemapテーブルでは「mid」列がメニュー項目のIDを表し、「parent」列の値はその項目の親となるメニュー項目を表しています(0はそれ以上親がないことを示します)。

 それでは、以下に具体的な手順を見ていきます。

[1]サーバ・コントロールを配置する

 新規に作成したWebフォーム「TreeView.aspx」に図11の要領で、TreeViewコントロールを配置します。


図11 TreeView.aspxのレイアウト
  TreeViewコントロール(tree)を配置。フォーマットは「MSDN」に設定。
  SqlDataSourceコントロール(sds)を配置。

 また、SqlDataSourceコントロールに対しては、表9の要領でプロパティ情報を設定しておきましょう。

プロパティ 設定値
ConnectionString MyDb
DataSourceMode DataReader
SelectQuery SELECT mid, url, title, description FROM sitemap WHERE (parent = @parent)
表9 SqlDataSourceコントロールのプロパティ設定

 SelectQueryプロパティを設定するためのクエリビルダの操作については、前節の内容を参照してください。sitemapテーブル上の各フィールドをグリッド・ペインにドラッグ&ドロップし、絞り込み条件としてparent行の[フィルタ]列に対して「=@parent」と指定します。最終的に表9に示したようなSQL命令ができていればOKです。

[2]ページ・ロード時の処理を定義する

 以上でフォーム・デザイナ上の作業は完了です。次に、TreeViewコントロールが呼び出されたときに、データベース(sitemapテーブル)の内容をツリー上に流し込むための処理をイベント・ハンドラに記述してみましょう。

 コード・エディタから以下のように記述してください。

' Loadイベント・ハンドラ
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs)
  Me.CreateNode(0, tree.Nodes)
End Sub

Private Sub CreateNode(ByVal parent As Integer, ByVal nodes As TreeNodeCollection)
  sds.SelectParameters.Clear()
  sds.SelectParameters.Add("parent", parent)
  Dim reader As IDataReader = sds.Select(DataSourceSelectArguments.Empty)

  Do While reader.Read()
    Dim node As New TreeNode()
    node.NavigateUrl = reader.GetString(1)
    node.Text = reader.GetString(2)
    Me.CreateNode(reader.GetInt32(0), node.ChildNodes) ' 再帰
    nodes.Add(node)
  Loop
End Sub
リスト3 ページ・ロード時の処理を記述したコード(TreeView.aspx)

 ここで注目していただきたいのは、Loadイベント・ハンドラ(Page_Loadメソッド)を起点に、その後、再帰的に呼び出されているCreateNodeメソッドです。

.NET TIPS:[ASP.NET]データベースからツリー・メニューを作成するには?

 CreateNodeメソッドでは、第1パラメータ「parent」で指定されたメニュー項目を親とするメニュー項目をデータベースから集め、第2パラメータ「nodes」で指定されたツリーのノード(のコレクション)に追加します。集めた各メニュー項目については再帰的にCreateNodeメソッドを呼び出すことで、さらに下位にあるノードを追加していくわけです。

 Page_Loadメソッドでは、メニュー項目のIDとして0を指定していますが、これは最初に親を持たない最上位のメニュー項目を取得することを表します。

 大まかな流れをたどることができたら、ここではSqlDataSourceコントロールでSELECT命令を実行している部分に注目してみましょう。

 SELECT命令にパラメータを引き渡すために、前節と同様、SqlDataSourceコントロールのSelectingイベント・ハンドラを利用しても構いませんが、ここではよりシンプルに、SqlDataSource.SelectParametersプロパティを使用してみます。

 SelectParametersプロパティはSqlDataSourceコントロールのパラメータ情報をParameterCollectionオブジェクトとして返します。ここではそのClearメソッドでパラメータ情報をクリアしたうえで、Addメソッドでparentの値を追加しています。

 これで、SELECT命令を発行する準備が整いましたので、あとはSelectメソッドでSELECT命令を実行するだけです。ただし、Insert/Update/Deleteメソッドと異なり、SelectメソッドはメソッドのパラメータとしてDataSourceSelectArgumentsオブジェクトを受け取る点に注意してください。

 DataSourceSelectArgumentsオブジェクトは、データ取得時にSqlDataSourceコントロールに対して引き渡す追加の情報を表します。例えば、取得する最大行数やソート式、取得開始行などを、本オブジェクトを介して指定することが可能です。ただ、このサンプルでは特に追加情報は必要ありませんので、DataSourceSelectArguments.Emptyプロパティで空(ダミー)のDataSourceSelectArgumentsオブジェクトを取得し、仮に引き渡しています。

 なお、Selectメソッドの戻り値は、DataSourceModeプロパティ*8の設定によって異なります。ここでは表9にあるように「DataReader」を指定していますので、IDataReaderオブジェクトを返しますが、例えば「DataSet」が指定された場合にはDataViewオブジェクトを返します。

*8 DataSourceModeプロパティについては第3回を参照してください。

 IDataReaderオブジェクトは、取得した結果セットの内容を前方からシーケンシャルに読み込むためのシンプルな手段を提供します。

 IDataReaderオブジェクト生成直後のデフォルトでは、読み取り位置は結果セットの先頭にありますので、Readメソッドで次の行を読み込みます。Readメソッドによって読み込まれた現在行の情報はIDataReader.GetXxxxxxメソッドによって取得が可能です。

 GetXxxxxメソッドには、取得するデータの型に応じて、GetBoolean、GetByte、GetBytes、GetChar、GetChars、GetDateTime、GetDecimal、GetDouble、GetFloat、GetInt16、GetInt32、GetInt64、GetStringなどがあります。ここではReadメソッドがFalseを返すまで(次の行が取得できない、つまり、終端を読み込むまで)Do-Whileループを繰り返すことで、結果セットの内容をすべて処理しているわけです。

 以上を理解したら、TreeView.aspxを実行してみましょう。図10のようにデータベースに設定したサイト情報がツリービューとして展開されていることが確認できれば成功です。

 以上、今回はDetailsView、Wizard、TreeViewコントロールを利用して、SqlDataSourceコントロールによるデータベース活用の具体的な例を紹介しました。サーバ・コントロールを利用することで、高度なユーザー・インターフェイスも手軽に作成できることが実感できたと思います。

 もちろん、限られたページの中では、ASP.NET 2.0で提供されている豊富なサーバ・コントロールをすべて紹介することはできませんが、まずは利用の手掛かりとしていただければ幸いです。End of Article


 INDEX
  Visual Studio 2005でいってみようDBプログラミング
  第5回 開発生産性を向上させるASP.NET 2.0のサーバ・コントロール
    1.GridView/DetailsViewコントロールで一覧/詳細マルチビューを生成する
    2.Wizardコントロールでウィザード形式の入力画面を作成する(1)
    3.Wizardコントロールでウィザード形式の入力画面を作成する(2)
  4.TreeViewコントロールでツリー・メニューを作成する
 
インデックス・ページヘ  「Visual Studio 2005でいってみようDBプログラミング」


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間