XAML(ザムル)は Extensible Application Markup Language の略で、.NETアプリの画面を「どのクラスのオブジェクトを、どのプロパティ値で、どういう親子関係で作るか」としてXMLの形で書く言語です。WPF・WinUI 3・.NET MAUIのいずれでも使われますが、名前空間やコントロール名はフレームワークごとに異なります。この記事では読み方とXMLとの違いのあと、.NET SDK 10.0.401 でビルドを確かめたWPFの例で書き方を説明し、C#だけで書いた版との比較やビルドエラーの直し方まで扱います。
まとめ:XAMLの読み方・XMLとの違い・書き方の要点
- 正式名称は Extensible Application Markup Language。英語の発音は「zammel」で、カタカナではザムルと書きます。
- XAMLは文法上は正しいXMLです。XMLとの違いは、要素名が.NETのクラスに、属性がプロパティやイベントに対応する点にあります。
- 書き方の核は、ルート要素の
xmlns宣言、属性構文、<Grid.RowDefinitions>のようなプロパティ要素、Grid.Rowのような添付プロパティ、{Binding}などのマークアップ拡張です。 - 処理はコードビハインド(
.xaml.cs)に書きます。WPFではXAMLがビルド時に.bamlと.g.csに変換されます。 - 同じ画面はC#だけでも書けます(実測でXAML版46行、C#版55行)。固定の画面はXAML、実行時まで形が決まらない部分だけC#で組みます。
- Windowsのアプリ一覧に出る「Microsoft.UI.Xaml」はWinUI 2の実行用パッケージです。WinUI 2を使うアプリが依存しているため、依存関係を確かめずに削除しないでください。
XAMLとは:正式名称・読み方と役割
XAMLの正式名称と読み方(ザムル)
XAMLは Extensible Application Markup Language の頭字語です。WPFがまだ開発コード名Avalonと呼ばれていた2004年1月のMSDN Magazineの紹介記事に「Extensible Application Markup Language (pronounced "zammel")」と発音が明記されており、日本語ではザムルと表記されます。同じ記事は、引数なしのpublicコンストラクターと設定可能なプロパティを持つクラスなら自作クラスでも要素にできることを「Extensible(拡張可能)」の理由に挙げています。WPF用の名前空間URIに今も残る winfx/2006 の WinFX は、.NET Framework 3.0 の開発時の名称です。
XAMLの役割:オブジェクト生成とプロパティ設定の宣言
Microsoft Learnの「XAML 言語の概要 – WPF」は、XAMLについて「アセンブリで定義されているバッキング型の特定のセット内のオブジェクトのインスタンス化を直接表します」と説明しています。次の1行のXAMLと1行のC#は、どちらも Button クラスのインスタンスを作り、2つのプロパティを設定するという同じ意味になります。
<Button Content="保存" Width="120"/>
var button = new Button { Content = "保存", Width = 120 };
違いは書き方の性質です。XAMLは親子関係をタグの入れ子でそのまま表せるため、画面の構造が読み取りやすくなります。一方で、.NET MAUIのXAMLの解説が挙げるとおり、XAMLにはループや条件分岐を書けず、イベントハンドラーもコードファイル側に定義する必要があります。画面の構造はXAML、処理はC#という分担が前提の言語です。
XAMLとXML・HTMLの違い
XMLとの違い:要素・属性と.NETの型の対応
.NET MAUIのドキュメントは「XAML is entirely legal XML」と書いています。XAMLはXMLの文法を一切変えておらず、XMLの上に「タグ名=クラス名」という意味づけを載せた言語です。
| 観点 | XML | XAML |
|---|---|---|
| 主な用途 | データ交換・設定ファイル | .NETのUI・オブジェクト定義 |
| 要素名の意味 | 文書ごとに自由 | .NETのクラス名 |
| 属性の意味 | 文書ごとに自由 | プロパティ・イベント |
| 名前空間の役割 | 名前の衝突回避 | 型を探すアセンブリの指定 |
| 独自の構文 | なし | プロパティ要素・添付プロパティ・マークアップ拡張 |
| 読み込み後 | ノードの木 | .NETオブジェクトの木 |
XMLとして正しいことが前提なので、タグの閉じ忘れはXAML固有のエラーではなく「XMLが無効」というエラーになります(後述のMC3000)。文字コードは、WPFでは任意のXMLエンコードを使えますが一般的なのはUTF-8で、WinUIの「XAML の概要」はUTF-8とUTF-16のみサポートと明記しています。
XAMLとHTMLの違い:大文字小文字の区別と終了タグの省略可否
見た目は似ていますが、前出の2004年の記事は「XMLをもとにしているため、XAMLの構文はHTMLより厳密で曖昧さがはるかに少ない」と書いています。HTMLはブラウザーが寛容に解釈し、タグ名の大文字小文字も区別しません。WPFのXAMLは、型を解決するときにCLRと同じ規則で大文字小文字を区別するため、TextBlock を Textblock と書いただけでビルドが止まります。HTMLは <p> や <li> の終了タグを省略できますが、XAMLはすべての要素を閉じる必要があります。スタイルも、HTMLはCSSという別の言語に分けるのに対し、XAMLは Style 要素としてXAMLの中に書きます。
XAMLの書き方:WPFの最小例で見る基本構文
次のコードは dotnet new wpf -n App1 で作ったプロジェクトの MainWindow.xaml を書き換えたものです。.NET SDK 10.0.401(net10.0-windows)で dotnet build がエラー0件・警告0件で通ることを確認しています。名前を入力すると下の行に反映され、「保存」ボタンを押すとボタンが無効になるだけの画面です。
<Window x:Class="App1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:App1"
Title="注文入力" Height="220" Width="360">
<Window.Resources>
<Style x:Key="PrimaryButton" TargetType="Button">
<Setter Property="Background" Value="#1E6FD9"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Padding" Value="12,4"/>
</Style>
</Window.Resources>
<Window.DataContext>
<local:OrderViewModel/>
</Window.DataContext>
<!-- コメントはXMLと同じ書き方 -->
<Grid Margin="16">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<TextBox Grid.Row="0" Text="{Binding CustomerName, UpdateSourceTrigger=PropertyChanged}"/>
<TextBlock Grid.Row="1" Margin="0,8" Text="{Binding Greeting}"/>
<Button Grid.Row="2" x:Name="SaveButton" Content="保存"
Style="{StaticResource PrimaryButton}"
HorizontalAlignment="Left" VerticalAlignment="Top"
Click="SaveButton_Click"/>
</Grid>
</Window>
ルート要素と名前空間(xmlns・x:・clr-namespace)
XAMLファイルのルート要素(ここでは Window)は1つだけで、そこに名前空間を宣言します。
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation":WPFのコントロール群。GridやButtonを接頭辞なしで書けるのはこの宣言のためです。xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml":XAML言語そのものの機能。x:Class・x:Name・x:Keyを使うために必要です。xmlns:local="clr-namespace:App1":自分で書いたクラス(ここではOrderViewModel)をlocal:付きで参照するための宣言です。
テンプレートが生成する xmlns:d と mc:Ignorable="d" は、デザイナー表示用の値を書くための名前空間で、実行時には無視されます。使わないなら消しても動作は変わりません。
属性構文・プロパティ要素構文・添付プロパティ
Title="注文入力" のように属性でプロパティを設定するのが基本(属性構文)です。値は文字列で書き、{ } のマークアップ拡張でなければ、プロパティやその型に指定された型コンバーターが目的の型に変換します(型コンバーターが無い場合は数値や列挙値などへの直接変換)。Margin="16" が Thickness 構造体に、Value="#1E6FD9" が色のブラシになるのはこの仕組みです。
文字列1つでは表せない値は <型名.プロパティ名> の形で子要素として書きます(プロパティ要素構文)。例の <Window.Resources> や <Grid.RowDefinitions> がこれに当たります。一方、TextBox に付けた Grid.Row="0" は、TextBox 自身ではなく親の Grid が読み取る値で、添付プロパティと呼びます。
タグの間に直接書いた中身は、そのクラスの「コンテンツプロパティ」に入ります。Grid の直下に並べた要素が Grid.Children と書かなくても子要素になるのも、<Button>保存</Button> が Content="保存" と同じ意味になるのも、この規則によるものです。
マークアップ拡張({Binding}・{StaticResource})
属性値を { } で囲むと、文字列ではなくマークアップ拡張として処理されます。例の Style="{StaticResource PrimaryButton}" は、Window.Resources に x:Key="PrimaryButton" で登録したスタイルを参照します。似た {DynamicResource} は参照の解決を値が必要になるまで遅らせるもので、テーマ切り替えのように実行中にリソースを差し替える場面で使います。変わらないリソースは StaticResource で足ります。
{Binding CustomerName} は、画面の DataContext に置いたオブジェクトのプロパティと表示をつなぎます。WPFの TextBox.Text は既定ではフォーカスが外れたときに値を書き戻す(LostFocus)ため、例では UpdateSourceTrigger=PropertyChanged を付けて1文字ごとに反映させています。
コメントと特殊文字のエスケープ
コメントはXMLと同じ <!-- --> です。属性値に < や & を入れるときは <・& と書きます。XAML固有の注意点は波かっこで、{ で始まる文字列をそのまま表示したいときは、先頭に {} を付けて Text="{}{注文番号}" のように書かないとマークアップ拡張として解釈されます。
コードビハインドとは:XAMLとC#をつなぐ仕組み
コードビハインドは、XAMLファイルと対になるC#(またはVisual Basic)のファイルで、WPFなら MainWindow.xaml に対する MainWindow.xaml.cs です。ボタンを押したときの処理のように、XAMLでは書けない手続きをここに書きます。
x:Classとpartialクラスによる結合
ルート要素の x:Class="App1.MainWindow" と、MainWindow.xaml.cs の partial class MainWindow が対になります。
using System.Windows;
namespace App1;
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private void SaveButton_Click(object sender, RoutedEventArgs e)
{
SaveButton.IsEnabled = false;
}
}
ビルド後の obj/Debug/net10.0-windows/ には MainWindow.baml(XAMLのバイナリ形式)と MainWindow.g.cs が生成されていました。MainWindow.g.cs の中身を見ると、XAMLとC#の関係がそのまま読み取れます。
x:Name="SaveButton"からinternal System.Windows.Controls.Button SaveButton;というフィールドが作られるInitializeComponent()はSystem.Windows.Application.LoadComponentを呼んでBAMLを読み込むClick="SaveButton_Click"はthis.SaveButton.Click += new System.Windows.RoutedEventHandler(this.SaveButton_Click);というイベント登録に変わる
XAMLに書いた名前やイベントはC#のコードとしてコンパイルされるため、ハンドラーの書き忘れや名前の重複はC#のエラー番号で報告されます。partialクラスの仕組みはC#のpartial(部分クラス・部分プロパティ)の解説で詳しく扱っています。
データバインディングによるC#の値の表示
例の <Window.DataContext> で設定しているのが次のクラスです。INotifyPropertyChanged の PropertyChanged イベントで変更を通知すると、{Binding} 先の表示が更新されます。
using System.ComponentModel;
using System.Runtime.CompilerServices;
namespace App1;
public class OrderViewModel : INotifyPropertyChanged
{
private string _customerName = "";
public string CustomerName
{
get => _customerName;
set
{
if (_customerName == value) return;
_customerName = value;
OnPropertyChanged();
OnPropertyChanged(nameof(Greeting));
}
}
public string Greeting => $"{CustomerName} 様の注文";
public event PropertyChangedEventHandler? PropertyChanged;
private void OnPropertyChanged([CallerMemberName] string? name = null)
=> PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(name));
}
コードビハインドにはボタンの見た目を変える程度の処理だけを残し、画面に出す値と入力の検証はこのようなクラスに寄せる設計がMVVMです。考え方はMVVMの仕組みと構成要素の解説を参照してください。WPFの {Binding} はパス名を実行時に解決するため、CustomerName を打ち間違えてもビルドは通り、画面に値が出ないだけになります。WinUI 3の {x:Bind} や.NET MAUIの x:DataType を使ったコンパイル済みバインディングは、この種の誤りをビルド時に検出できます。
同じ画面をC#だけで書く:XAMLとの対訳と使い分け
XAMLは必須ではありません。書き方の章のXAMLとまったく同じ画面を、XAMLファイルを使わずC#だけで書いたのが次のコードです。その App1 プロジェクトから MainWindow.xaml と MainWindow.xaml.cs を削除して MainWindow.cs に置き換え、OrderViewModel はそのまま使います。後述の App.xaml の変更とあわせて、.NET SDK 10.0.401でエラー0件・警告0件でビルドできることを確認しました。
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Media;
namespace App1;
public class MainWindow : Window
{
public MainWindow()
{
Title = "注文入力";
Height = 220;
Width = 360;
var primaryButton = new Style(typeof(Button));
primaryButton.Setters.Add(new Setter(BackgroundProperty, new SolidColorBrush(Color.FromRgb(0x1E, 0x6F, 0xD9))));
primaryButton.Setters.Add(new Setter(ForegroundProperty, Brushes.White));
primaryButton.Setters.Add(new Setter(PaddingProperty, new Thickness(12, 4, 12, 4)));
Resources.Add("PrimaryButton", primaryButton);
DataContext = new OrderViewModel();
var grid = new Grid { Margin = new Thickness(16) };
grid.RowDefinitions.Add(new RowDefinition { Height = GridLength.Auto });
grid.RowDefinitions.Add(new RowDefinition { Height = GridLength.Auto });
grid.RowDefinitions.Add(new RowDefinition { Height = new GridLength(1, GridUnitType.Star) });
var textBox = new TextBox();
textBox.SetBinding(TextBox.TextProperty, new Binding(nameof(OrderViewModel.CustomerName))
{
UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
});
Grid.SetRow(textBox, 0);
grid.Children.Add(textBox);
var textBlock = new TextBlock { Margin = new Thickness(0, 8, 0, 8) };
textBlock.SetBinding(TextBlock.TextProperty, new Binding(nameof(OrderViewModel.Greeting)));
Grid.SetRow(textBlock, 1);
grid.Children.Add(textBlock);
var saveButton = new Button
{
Content = "保存",
Style = (Style)Resources["PrimaryButton"],
HorizontalAlignment = HorizontalAlignment.Left,
VerticalAlignment = VerticalAlignment.Top
};
saveButton.Click += (_, _) => saveButton.IsEnabled = false;
Grid.SetRow(saveButton, 2);
grid.Children.Add(saveButton);
Content = grid;
}
}
XAMLの記法とC#の対応表
2つの版を並べると、XAMLの文字列が裏でどの型に変換されていたかが分かります。
| XAMLの書き方 | C#で書くと | XAML側の仕組み |
|---|---|---|
Margin="16" |
new Thickness(16) |
型コンバーター |
Value="#1E6FD9" |
new SolidColorBrush(Color.FromRgb(…)) |
型コンバーター |
Height="*" |
new GridLength(1, GridUnitType.Star) |
型コンバーター |
Grid.Row="2" |
Grid.SetRow(saveButton, 2) |
添付プロパティ |
<Grid> の直下に並べる |
grid.Children.Add(…) |
コンテンツプロパティ |
{Binding CustomerName} |
SetBinding(TextBox.TextProperty, …) |
マークアップ拡張 |
{StaticResource PrimaryButton} |
(Style)Resources["PrimaryButton"] |
マークアップ拡張 |
Click="SaveButton_Click" |
saveButton.Click += … |
.g.cs のイベント登録 |
行数は、XAML版が MainWindow.xaml 30行と MainWindow.xaml.cs 16行の計46行、C#版が MainWindow.cs 55行でした。差は9行ですが、C#版は親子関係が Children.Add の順序でしか読み取れず、行と列の配置も Grid.SetRow を探さないと分かりません。生成物も違い、C#版の obj には MainWindow.baml も MainWindow.g.cs も作られません。
XAML削除時の落とし穴:StartupUriの参照先とビルド検査の範囲
C#版に切り替える途中で、MainWindow.xaml を消しただけの状態でもビルドは成功しました。App.xaml の StartupUri="MainWindow.xaml" は、生成された App.g.cs の中で this.StartupUri = new System.Uri("MainWindow.xaml", System.UriKind.Relative); という文字列のURIになるだけで、ファイルの有無は確かめられないためです。C#だけで画面を作るときは App.xaml の StartupUri を Startup="App_Startup" に置き換え、App.xaml.cs で画面を開く形に変えてください。
using System.Windows;
namespace App1;
public partial class App : Application
{
private void App_Startup(object sender, StartupEventArgs e)
{
new MainWindow().Show();
}
}
XAMLで書くべき場面・C#で組むべき場面
固定のレイアウトはXAMLで書くべきです。構造がタグの入れ子で見えるうえ、XAMLエディターやホットリロード、コンパイル済みバインディングがXAMLを前提にしているためです。C#で組むのは、列の数や入力欄の種類が設定やデータベースの中身で決まり、実行するまで形が分からない部分に限ります。件数だけが変わる一覧なら ItemsControl と DataTemplate でXAMLのまま表せるので、C#で Children.Add を繰り返すのは最後の手段です。
実行時にXAMLを読み込む:XamlReaderの使い方と制約
XAMLは実行中に文字列やファイルから読み込むこともできます。WPFでは System.Windows.Markup.XamlReader の Load(ストリームや XmlReader から)または Parse(文字列から)を使います。次の例は、App1 とは別に dotnet new wpf -n App3 で作ったプロジェクトの MainWindow.xaml.cs を書き換えたもので(テンプレートの MainWindow.xaml は残します)、.NET SDK 10.0.401 でビルドが通ることまで確認しています。WPFアプリの実行にはWindowsが必要なため、画面表示は未確認です。
using System.Windows;
using System.Windows.Controls;
using System.Windows.Markup;
namespace App3;
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
// ファイルやDBから受け取ったXAML文字列を想定
const string xaml = """
<StackPanel xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<TextBlock Text="実行時に読み込んだ画面"/>
<Button x:Name="OkButton" Content="OK"/>
</StackPanel>
""";
var panel = (StackPanel)XamlReader.Parse(xaml);
var ok = (Button)panel.FindName("OkButton");
ok.Click += (_, _) => Close();
Content = panel;
}
}
x:Class と Click="…" のようなイベント属性は、ビルド時のマークアップコンパイルでコードビハインドと結び付ける仕組みです(x:Classディレクティブの解説)。実行時に読み込むXAMLにはこの工程が無いので、例のように x:Name で名前だけ付けておき、FindName で取り出してC#側でイベントを登録します。読み込みに失敗したときは、WPFの実装上、行番号と行内の位置を持った XamlParseException として報告されます。
読み込むXAMLの出どころには注意が必要です。XamlReaderのリファレンスは、完全信頼のアプリに読み込んだXAMLはホストのアプリと同じようにシステムの資源へアクセスできるとし、どのXAMLを読み込むかの信頼判断をアプリの設計側に求めています。利用者がアップロードしたXAMLをそのまま読み込む設計は避けてください。
WPF・WinUI 3・.NET MAUI・Avalonia:フレームワーク別のXAMLの違い
XAMLの文法は共通でも、ルートの名前空間とコントロールの品ぞろえはフレームワークごとに別物です。検索で見つけたサンプルがそのまま動かない原因の多くはここにあります。
| 項目 | WPF | WinUI 3 | .NET MAUI | Avalonia |
|---|---|---|---|---|
| 既定のxmlns | …/winfx/2006/xaml/presentation | WPFと同じURI | …/dotnet/2021/maui | https://github.com/avaloniaui |
| x: の名前空間 | …/winfx/2006/xaml | …/winfx/2006/xaml | …/winfx/2009/xaml | …/winfx/2006/xaml |
| 自作クラスの参照 | clr-namespace: | using: | clr-namespace: | using: と clr-namespace: |
| ファイル拡張子 | .xaml | .xaml | .xaml | .axaml |
| ボタンのクリック | Click | Click | Clicked | Click |
入力欄とボタンの部分を.NET MAUIで書くと次のようになります(Microsoft Learnの記法に沿った断片で、ビルドはWPFの例のみ確認しています)。x:DataType はバインディング元の型を伝えるだけなので、実際のデータは BindingContext に OrderViewModel を設定して渡し、OnSaveClicked はコードビハインドに定義します。入力欄は Entry、縦並びは VerticalStackLayout、クリックイベントは Clicked と、名前がWPFと一致しません。
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:MyApp"
x:Class="MyApp.MainPage"
x:DataType="local:OrderViewModel">
<VerticalStackLayout Padding="16" Spacing="8">
<Entry Text="{Binding CustomerName}"/>
<Button Text="保存" Clicked="OnSaveClicked"/>
</VerticalStackLayout>
</ContentPage>
.NET MAUIはXAMLの処理方式も違います。.NET 10の既定では、Debugビルドは実行時にXAMLを読み込み、ReleaseビルドはXAMLコンパイラ(XamlC)でILに変換します。csprojに <MauiXamlInflator>SourceGen</MauiXamlInflator> を書くとXAMLをC#コードに変換するソースジェネレーターに切り替えられ、.NET 10ではこれがオプトインです。.NET 11 Preview 1のリリースノートは、.NET 11ではすべての.NET MAUIアプリでXAMLソース生成を既定にしたと書いています。また、.NET MAUIにはビジュアルデザイナーがなく、XAMLは手書きしてホットリロードで確認します。Avaloniaは拡張子が .axaml(コードビハインドは .axaml.cs)で、NuGetでの最新安定版は12.1.4です(2026年10月23日確認)。
XAMLの文法を学ぶなら、属性構文・プロパティ要素・マークアップ拡張と.NETの型との対応を例付きで説明しているMicrosoft Learnの「XAML 言語の概要 – WPF」に沿って、WPFで書き始めるのが近道です。そのうえで、配布先がWindowsだけならWPFかWinUI 3、モバイルも含めるなら.NET MAUI、LinuxやmacOSのデスクトップも対象ならAvaloniaと選び分けてください。WPF自体の現状と採用判断はWPFの解説記事に、業務システムとしてのWindowsアプリを外部に頼む場合の相談先は業務用・Webアプリ開発の支援にまとめています。
Windowsで見かける「Microsoft.UI.Xaml」とは:WinUI 2の実行用パッケージ
Windowsの「インストールされているアプリ」の一覧やPowerShellの Get-AppxPackage の結果に、Microsoft.UI.Xaml.2.8 のような名前が出てくることがあります。これは開発者が書く.xamlファイルではなく、WinUI 2(UWPアプリ向けのUIライブラリ)の実行用パッケージです。MicrosoftのWebView2の導入手順は「Microsoft.UI.Xaml is WinUI 2.」と明記しています。NuGetでの最新版は2.8.7です(2026年10月23日確認)。
WinUI 2で作られたアプリはこのパッケージを共有します。たとえばWindows IoT Enterprise向けのWinGet手動導入手順は「WinGet CLI has a dependency on Microsoft.UI.Xaml.2.8」とし、VCLibsとUI Xamlの2つを先に入れないとWinGetのインストーラーはエラーも警告も出さずに失敗し、winget.exe が配置されないと注意しています。見覚えのない名前でも、不要なアプリとして削除しないでください。
ただし依存先は変わりつつあります。winget v1.12.350(2025年10月公開)のリリースノートでは、App InstallerがWinUI 3に移行し、WinUI 2への依存がWindows App Runtime 1.8への依存に置き換わりました。新しいApp Installerで依存関係のエラーが出たら、Windows App Runtimeの有無も確かめてください。
Windows自体の画面にもXAMLで作られた部分があります。MicrosoftはWindows開発者向けFAQで、Windows 11のエクスプローラーとフォトアプリをWinUIで作ったアプリの例に挙げています。開発者として後継のWinUI 3を選ぶかどうかはWinUI 3の解説を、WinUI 3アプリをMSIXにまとめて配布する手順はwinapp CLIの解説を参照してください。
XAMLのビルドエラーと直し方:実際のメッセージ一覧
前出のWPFの最小例を1か所ずつわざと壊し、.NET SDK 10.0.401(日本語環境)で dotnet build した結果です。
| 壊し方 | エラー | メッセージの要点 | 直し方 |
|---|---|---|---|
| xmlns:local を削除 | MC3000 | 'local' is an undeclared prefix |
ルートに xmlns:local を宣言 |
| 最後の RowDefinition の閉じ忘れ | MC3000 | start tag … does not match the end tag |
開始・終了タグを対応させる |
| TextBlock を Textblock と誤記 | MC3074 | タグ 'Textblock' は XML 名前空間にありません |
大文字小文字をクラス名に合わせる |
TargetType="Buton" |
MC3066 | 'Buton' という名前のパブリック型を見つけられません |
型名と接頭辞を確認 |
| Click先のメソッドが無い | CS1061 | 'MainWindow' に 'Missing_Click' の定義が含まれておらず |
コードビハインドにメソッドを追加 |
| x:Name を重複 | CS0102 | 既に 'SaveButton' の定義を含んでいます |
名前を一意にする |
Height="abc" |
なし | ビルドは成功する | 実行時の読み込みで失敗する |
読み方のコツは接頭辞です。MC で始まるものはXAMLのマークアップコンパイラが出すエラーで、MC3000はXMLとして壊れている、MC3074とMC3066は型が見つからない、という意味です。CS で始まるものは、.g.cs に変換されたあとでC#コンパイラが出したエラーなので、XAMLの行番号を手がかりにコードビハインドとの対応を確認します。
最も注意が必要なのは最後の行です。Height="abc" のような値の誤りはビルドを素通りし、実行してBAMLを読み込む段階で失敗します。WPFのXAMLパーサーは読み込み時の誤りを XamlParseException として送出します。{Binding} のパス名の誤りと、前述の StartupUri の指す先が無い状態も同様にビルドでは検出されません。ビルドが通っても、画面を一度表示して確かめてください。
よくある質問
XAMLはプログラミング言語ですか?
いいえ、マークアップ言語です。オブジェクトの生成とプロパティの設定は書けますが、ループや条件分岐は書けません。ボタンを押したときの処理などはC#(またはVisual Basic)のコードビハインドに書きます。
XAMLを勉強するにはどうすればいいですか?
dotnet new wpf でプロジェクトを作り、この記事の最小例のように Grid・TextBox・Button を並べて {Binding} で値を表示するところまで書くのが近道です。慣れたら同じ画面をC#だけで書き直すと、型コンバーターや添付プロパティの働きが分かります。実行にはWindowsが必要です。
.xamlファイルは何で開けますか?
中身はXMLのテキストなので、メモ帳などのテキストエディターで開けます。編集するならVisual Studioが基本で、XAMLエディターの入力補完と、入力中にエラーを波線で示す機能が使えます。
XAML Studioとは何ですか?
WinUI向けのXAMLをその場で試し書きし、Visual Studioへ貼り付けるためのプロトタイピングツールです。Microsoft Storeから入手でき、貼り付けたXAMLがその場でプレビューされ、バインディングのデバッガーも備えています。ソースコードはGitHubのdotnet/XAMLStudioでMITライセンスとして公開されており、READMEによるとmainブランチはStore版のv1.1、最新の開発はdevブランチで進んでいます。対象はWinUIのXAMLなので、WPFや.NET MAUIのXAMLを試す用途には向きません。
XAMLは今から学ぶ価値がありますか?
あります。WPF・WinUI 3・.NET MAUI・Avaloniaのいずれも画面定義にXAMLを使い、.NET MAUIは.NET 10でXAMLのソースジェネレーターを追加するなど、処理系への投資が続いています。一方、Xamarin.Formsは2024年5月1日にサポートが終了しており、旧来の http://xamarin.com/schemas/2014/forms を使う入門記事の名前空間やコントロール名をそのまま覚えないよう注意してください。