BackacheEngineerの技術的な備忘録

技術系でいろいろ書けたらなーと

Visual Studio コードスニペットの作り方

XAMLをやるようになって便利なことを再認識したコードスニペットについてちょっとまとめる。 間違いなく1度作って終わりなタイプのものなので、忘れないうちに備忘録として・・・。 いやまぁ、MSDNをコレクションに加えてしまえばいい話なんだけどね。

目次

コードスニペットを自作する

自作とはいっても、既存のものをコピペして改造するだけである。保存場所は、自作コードスニペット用フォルダが最初っから用意されているのでそこを使う。

[ツール]メニューから、[コードスニペットマネージャー]を開いて、作りたい言語を選択してあげればいい。 フォルダパスも表示されるので、[My Code Snippet]を選択してパスをコピーして移動する。 今回作るのはXAML側とC#側の2種類。それぞれフォルダが異なるが、記法は同じ。

f:id:BackacheEngineer:20210430131938p:plain
コードスニペットマネージャーの画面

コードスニペットで使えるタグ

詳しくはMSDNに全部あるんで、そちらを。

docs.microsoft.com

よく使いそうなタグをまとめる。まとめたもの以外はまぁMSDNでいいでしょう。サンプルとしてコードそのまま載せたいんだけど、表の中にちゃんとしたコード入らんかった。なので\<と>など省略して書く。

タグ 説明
Header コードスニペットマネージャー画面で見えるところをまとめるタグ。
Shortcut コードスニペットのショートカット。これを打ち込んで Tab 2回押すとかすればコードスニペットが挿入される。Header タグ内に書く。

サンプル
Header
  Shortcut  test  Shortcut
Header
Imports Import タグを複数持つためのタグ。Snippet タグ内に書く。サンプルは Namespace タグに記載。
Import コードスニペット挿入時に一緒に入れてほしい名前空間が書ける。サンプルは Namespace タグに記載。
Namespace 名前空間を文字列で指定する。Import タグ内で使う。

サンプル
Snippet
  Imports
    Import
      Namespace System.IO Namespace
    Import
  Imports
Snippet


コードスニペット内で使えるリテラルについてまとめる。2種類しかない。どちらも1回のみ使用可能。

リテラル 説明
$end$ コードスニペット挿入後のカーソル位置を決めれる。
$selected$ コードスニペット挿入後に選択状態の箇所を作れる。


XAMLコードスニペット

XAML側で作成していくのはコメントのコードスニペットである。 < も ! も打つのめんどくさい。「comment + Tab」で「<!-- -->」が追加され、かつフォーカスが中央になるようにする。

コードスニペットファイルである「*.snippet」はVisual Studioで編集できるので、そのままVisual Studioで編集する。

できたのがこれ。

<?xml version="1.0" encoding="utf-8"?>
<CodeSnippet Format="1.0.0" xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
  <Header>
    <SnippetTypes>
      <SnippetType>Expansion</SnippetType>
      <SnippetType>SurroundsWith</SnippetType>
    </SnippetTypes>
    <Title>コメント</Title>
    <Description>新しいコメントのスニペット</Description>
    <Shortcut>comment</Shortcut>
  </Header>
  <Snippet>
    <Code Language="XAML"><![CDATA[<!-- $end$ -->]]></Code>
  </Snippet>
</CodeSnippet>

実際に使ってみる。ちゃーんとコメント書けてるのでよき。

f:id:BackacheEngineer:20210430135512g:plain
コメントのコードスニペットを使ってみた


C#コードスニペット

C#側でほしいなと思ったコードスニペットは3つ。

  • アクション(ラムダ式)の定型
  • イベントのラムダ式の定型
  • INotifyPropertyChanged を継承したViewModelで使いたいSetPropertyメソッド挿入


アクション(ラムダ式)の定型

アクションを「() => { }」で書く機会って結構あると思うので作っておく。 「action + Tab 2回」で上記の定型を出す。Func にも対応したり、引数を作れるように「()」の間にフォーカスを持ってくる。

できたのがこれ。

<?xml version="1.0" encoding="utf-8"?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
    <CodeSnippet Format="1.0.0">
        <Header>
            <Title>LambdaAction</Title>
            <Shortcut>action</Shortcut>
            <Description>action ( lambda 記法) に対するコード スニペット</Description>
            <SnippetTypes>
                <SnippetType>Expansion</SnippetType>
                <SnippetType>SurroundsWith</SnippetType>
            </SnippetTypes>
        </Header>
        <Snippet>
            <Code Language="csharp"><![CDATA[($end$$selected$) => { }]]>
            </Code>
        </Snippet>
    </CodeSnippet>
</CodeSnippets>

使ってみる。

f:id:BackacheEngineer:20210430154831g:plain
アクションのコードスニペット使ってみた


イベントのラムダ式の定型

次はイベントをラムダ式で書いてくれるコードスニペット。「(sender, e) => { }」を使う機会がちょっとだけ増えてきたんで・・・。 使い方は、「sender + Tab 2回」。

サクサク作る。

<?xml version="1.0" encoding="utf-8"?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
    <CodeSnippet Format="1.0.0">
        <Header>
            <Title>LambdaEvent</Title>
            <Shortcut>sender</Shortcut>
            <Description>event ( lambda 記法) に対するコード スニペット</Description>
            <SnippetTypes>
                <SnippetType>Expansion</SnippetType>
                <SnippetType>SurroundsWith</SnippetType>
            </SnippetTypes>
        </Header>
        <Snippet>
            <Code Language="csharp"><![CDATA[(sender, e) => { $end$ };]]>
            </Code>
        </Snippet>
    </CodeSnippet>
</CodeSnippets>

そして使う。

f:id:BackacheEngineer:20210430160231g:plain
ラムダ式のイベント追加コードスニペット使ってみた


INotifyPropertyChanged を継承したViewModelで使いたいSetPropertyメソッド挿入

最後はメソッド丸々挿入。テンプレートメソッド的なやつ。メソッドで使う名前空間も自動で using されるようにする。 使い方は「setproperty + Tab 2回」。

作る。コード部分に「// OnPropertyChanged(propertyName);」とコメントアウト部分があるのは、ここだけ確定せずにメソッド名が変わる可能性あるから。

<?xml version="1.0" encoding="utf-8"?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
    <CodeSnippet Format="1.0.0">
        <Header>
            <Title>SetProperty Method</Title>
            <Shortcut>setproperty</Shortcut>
            <Description>SetProperty メソッドに対するコード スニペット</Description>
            <SnippetTypes>
                <SnippetType>Expansion</SnippetType>
                <SnippetType>SurroundsWith</SnippetType>
            </SnippetTypes>
        </Header>
        <Snippet>
      <Imports>
        <Import>
          <Namespace>
            System.Runtime.CompilerServices
          </Namespace>
        </Import>
      </Imports>
            <Code Language="csharp">
        <![CDATA[bool SetProperty<T>(ref T storage, T value, [CallerMemberName] string propertyName = null)
        {
            if (Equals(storage, value)) return false;

            storage = value;
            // OnPropertyChanged(propertyName);
            return true;
        }$end$]]>
            </Code>
        </Snippet>
    </CodeSnippet>
</CodeSnippets>

使う。ちゃんとusingも追加されてる。

f:id:BackacheEngineer:20210430160851g:plain
メソッド挿入とusing追加のコードスニペット使う