皆さん、こんにちは。砂漠の果ての狼です。
サイトをBlazorで再構築してから1日が経ちました。Blazorでの開発は本当に便利で、空き時間にGPTやGitHubを調べながら、正規表現オンラインテストツール といくつかのオンラインミニゲーム、例えば 三目並べ、マインスイーパー などを公開しました。
以下に簡単に紹介しますので、興味やご提案があればお聞かせください。
1. 新しく追加したオンラインミニツール
1.1. 正規表現オンラインテストツール
オンラインアクセス: https://dotnet9.com/tools/regextester
このサンプルでは、Blazor Serverを使用してシンプルな正規表現オンラインテストツールを開発する方法を紹介しています。ユーザーは正規表現とテスト文字列を入力し、「テスト」ボタンをクリックすることで、正規表現がテスト文字列にマッチするかどうかをテストできます。また、このサンプルでは10以上のよく使われる正規表現も用意されており、ユーザーはリンクをクリックしてテストデータを読み込み、正規表現とテスト文字列を自動的に入力できます。

上の図の注釈の簡単な説明:
- よく使われる正規表現: クリックすると、対応する正規表現(注釈2)、テストテキスト(注釈3)が自動的に下に入力され、「テスト」(注釈4)をクリックして検証できます。
- 正規表現: 使用したい正規表現を入力します。
- テストテキスト領域: 検証・抽出したい文字列をここに入力します。
- 【テスト】ボタン: クリックすると、上の正規表現(注釈2)を適用し、テストテキスト領域(注釈3)の内容を抽出し、マッチした結果を下に表示します(注釈5)。
- マッチした結果を表示します。
コードは全部で123行で、よく使われる正規表現が含まれています。簡単ですね。
@page "/tools/regextester"
@using System.Text.RegularExpressions
<PageTitle>@_title</PageTitle>
<MApp>
<h2 style="margin-bottom: 30px; margin-top: 10px; text-align: center;">@_title</h2>
<h3>よく使われる正規表現テスト</h3>
<p>
@foreach (var item in _regexPatterns)
{
<MButton Color="lime" Class="ma-2" OnClick='() => LoadTest(item.Pattern)'>@item.Name</MButton>
}
</p>
<div>
<MTextField Label="正規表現" Type="string" TValue="string" @bind-Value="_regexPattern"/>
</div>
<div>
<MTextarea BackgroundColor="grey lighten-2" Solo
Color="orange orange-darken-4" TValue="string" @bind-Value="_testString"
Label="テスト文字列" Rows="8" style="font-size:12px;" RowHeight="15" AutoGrow/>
</div>
<div>
<MButton Color="success" class="ma-2" OnClick="TestRegex">テスト</MButton>
</div>
<div>
@if (string.IsNullOrEmpty(_regexPattern) || string.IsNullOrEmpty(_testString))
{
<p>正規表現とテスト文字列を入力し、「テスト」ボタンをクリックしてください。</p>
}
else
{
<p>マッチ結果: </p>
<ul>
@foreach (var match in _matches)
{
<li>@match</li>
}
</ul>
}
</div>
</MApp>
@code {
private const string? _title = "ツールボックス-正規表現オンラインテストツール";
private string? _regexPattern;
private string? _testString;
private string? _defaultString = @"以下はテスト例です:
history: v1.0 正規表現テストツール公開
v1.1 2023-06-23 公開直後
1. 現時点で最長のドメインサフィックス .cancerresearch
demo@qq.com
dotnet9-9@vip.qq.com
dotnet9-9@gmail.com
demo@live.com
127.0.0.1
http://dotnet9.com/
510112199901013592
https://dotnet9.com/
123456789012345
18628035382
13493532389
川AAA008
京B45698
14:22:19";
private readonly List<RegexItem> _regexPatterns = new()
{
new("メールアドレスにマッチ", @"\w[-\w.+]*@([A-Za-z0-9][-A-Za-z0-9]+\.)+[A-Za-z]{2,14}"),
new("中国語にマッチ", @"[\u4e00-\u9fa5]+"),
new("2バイト文字(漢字を含む)にマッチ", @"[^\x00-\xff]+"),
new("時刻(時:分:秒)にマッチ", @"([01]?\d|2[0-3]):[0-5]?\d:[0-5]?\d"),
new("IPアドレス(IPV4)にマッチ", @"\d{0,3}\.\d{0,3}\.\d{0,3}\.\d{0,3}"),
new("身分証番号にマッチ", @"\d{17}[0-9Xx]|\d{15}"),
new("日付(年-月-日)にマッチ", @"(([0-9]{3}[1-9]|[0-9]{2}[1-9][0-9]{1}|[0-9]{1}[1-9][0-9]{2}|[1-9][0-9]{3})-(((0[13578]|1[02])-(0[1-9]|[12][0-9]|3[01]))|((0[469]|11)-(0[1-9]|[12][0-9]|30))|(02-(0[1-9]|[1][0-9]|2[0-8]))))|((([0-9]{2})(0[48]|[2468][048]|[13579][26])|((0[48]|[2468][048]|[3579][26])00))-02-29)"),
new("正の整数にマッチ", @"[1-9]\d*"),
new("負の整数にマッチ", @"-[1-9]\d*"),
new("携帯番号にマッチ", @"(13\d|14[579]|15[^4\D]|17[^49\D]|18\d)\d{8}"),
new("ナンバープレートにマッチ", @"(([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领][A-Z](([0-9]{5}[DF])|([DF]([A-HJ-NP-Z0-9])[0-9]{4})))|([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领][A-Z][A-HJ-NP-Z0-9]{4}[A-HJ-NP-Z0-9挂学警港澳使领]))")
};
private readonly List<string> _matches = new();
private void TestRegex()
{
if (string.IsNullOrWhiteSpace(_regexPattern) || string.IsNullOrWhiteSpace(_testString))
{
return;
}
try
{
var regex = new Regex(_regexPattern);
var match = regex.Match(_testString);
_matches.Clear();
while (match.Success)
{
_matches.Add(match.Value);
match = match.NextMatch();
}
}
catch
{
_matches.Clear();
}
}
private void LoadTest(string pattern)
{
_regexPattern = pattern;
_testString = _defaultString;
}
record RegexItem(string Name, string Pattern);
}
2. オンラインミニゲームを公開
先に説明しておきますが、管理者はサイトのサーバー負荷をテストするためにミニゲームを公開しています。ミニゲームを開発する場合は、クライアントモード(WASM)を使用することをお勧めします。前者はサーバーに負荷がかかり、後者はユーザー側にかかるためです。
2.1. 数字当てゲーム
オンラインアクセス: https://dotnet9.com/games/guessing-numbers

ゲーム開始時に、1から100までのランダムな数字が目標として生成されます。プレイヤーは数字を入力して目標を推測し、システムが推測に応じたヒントを表示します。プレイヤーが正解するとゲーム終了、お祝いメッセージが表示され、新しいゲームを開始するボタンが表示されます。
このゲームはシンプルで、コードは数十行です。
@page "/games/guessing-numbers"
<PageTitle>@_title</PageTitle>
<MApp>
<h2 style="margin-bottom: 30px; margin-top: 10px; text-align: center;">@_title</h2>
@if (_isGameOver)
{
<p>@_message</p>
<p>ゲーム終了!</p>
<p>
<MButton Color="lime" Class="ma-2" OnClick='StartNewGame'>新しいゲームを開始</MButton>
</p>
}
else
{
<p>1から100までの数字を推測してください:</p>
<p>
<MTextField Label="数字" Type="string" TValue="int" @bind-Value="_guess"/>
</p>
<p>
<MButton Color="success" class="ma-2" OnClick="CheckGuess">推測!</MButton>
</p>
<p>@_message</p>
}
</MApp>
@code {
readonly string? _title = "数字当てゲーム";
private int _targetNumber;
private int _guess;
private string? _message;
private bool _isGameOver;
protected override void OnInitialized()
{
StartNewGame();
}
private void StartNewGame()
{
var random = new Random();
_targetNumber = random.Next(1, 101);
_guess = 0;
_message = "";
_isGameOver = false;
}
private void CheckGuess()
{
if (_guess == _targetNumber)
{
_message = "おめでとう、正解です!";
_isGameOver = true;
}
else if (_guess < _targetNumber)
{
_message = "小さいです!";
}
else
{
_message = "大きいです!";
}
}
}
2.2. 三目並べ
オンラインアクセス: https://dotnet9.com/games/tictactoe

シンプルな三目並べで、プレイヤーは盤上のマスをクリックして駒を置きます。ゲームはプレイヤーの勝ちまたは引き分けをチェックし、ゲーム終了時に対応するメッセージを表示します。プレイヤーは「新しいゲームを開始」ボタンをクリックして、ゲームを最初からやり直せます。
コード117行:
@page "/games/tictactoe"
<PageTitle>@_title</PageTitle>
<MApp>
<h2 style="margin-bottom: 30px; margin-top: 10px; text-align: center;">@_title</h2>
@if (_isGameOver)
{
<p>@_message</p>
<p>ゲーム終了!</p>
<MButton Color="lime" Class="ma-2" OnClick='StartNewGame'>新しいゲームを開始</MButton>
}
else
{
<div style="text-align: center;">
@for (var i = 0; i < 3; i++)
{
<div>
@for (var j = 0; j < 3; j++)
{
var i1 = i * 3 + j;
<MButton Color="lime" OnClick='() => MakeMove(i1)' Disabled='IsCellDisabled(i1)'>@_board[i1]</MButton>
}
</div>
}
</div>
<p>@_message</p>
}
</MApp>
@code {
readonly string? _title = "三目並べ";
private string?[] _board = new string[9];
private string _currentPlayer = "X";
private string? _message;
private bool _isGameOver;
private void MakeMove(int index)
{
if (_board[index] != null || _isGameOver)
{
return;
}
_board[index] = _currentPlayer;
if (CheckWin(_currentPlayer))
{
_message = $"プレイヤー {_currentPlayer} の勝利!";
_isGameOver = true;
}
else if (_board.All(cell => cell != null))
{
_message = "引き分け!";
_isGameOver = true;
}
else
{
_currentPlayer = _currentPlayer == "X" ? "O" : "X";
if (_currentPlayer == "O")
{
MakeComputerMove();
}
}
}
private void MakeComputerMove()
{
// シンプルにランダムで空いているマスを選んで打つ
var availableMoves = Enumerable.Range(0, 9).Where(i => _board[i] == null).ToList();
var random = new Random();
var randomIndex = random.Next(availableMoves.Count);
var computerMove = availableMoves[randomIndex];
_board[computerMove] = _currentPlayer;
if (CheckWin(_currentPlayer))
{
_message = $"コンピューターの勝利!";
_isGameOver = true;
}
else if (_board.All(cell => cell != null))
{
_message = "引き分け!";
_isGameOver = true;
}
else
{
_currentPlayer = _currentPlayer == "X" ? "O" : "X";
}
}
private bool CheckWin(string player)
{
// すべての勝利条件をチェック
return (_board[0] == player && _board[1] == player && _board[2] == player) ||
(_board[3] == player && _board[4] == player && _board[5] == player) ||
(_board[6] == player && _board[7] == player && _board[8] == player) ||
(_board[0] == player && _board[3] == player && _board[6] == player) ||
(_board[1] == player && _board[4] == player && _board[7] == player) ||
(_board[2] == player && _board[5] == player && _board[8] == player) ||
(_board[0] == player && _board[4] == player && _board[8] == player) ||
(_board[2] == player && _board[4] == player && _board[6] == player);
}
private bool IsCellDisabled(int index)
{
return _isGameOver || _board[index] != null;
}
private void StartNewGame()
{
_board = new string[9];
_currentPlayer = "X";
_message = null;
_isGameOver = false;
}
}
2.3. オンラインマインスイーパー
オンラインアクセス: https://dotnet9.com/games/minesweeper

このサンプルでは、プレイヤーはマスをクリックして開きます。地雷を踏むとゲームオーバーです。開いたマスの周りに地雷がある場合、マスにはその周囲の地雷の数が数字で表示されます。プレイヤーが地雷のないマスを全て開けると勝利です。
このゲームは、初期のWindows版マインスイーパーを高度に再現しています。コードは多く、オープンソースプロジェクト https://github.com/jarDotNet/BlazorMinesweeper から拝借しました。コードに興味がある方は、そのオープンソースプロジェクトをご覧いただくか、Dotnet9サイト のマインスイーパー関連部分をお読みください。

3. 最後に
もう一度言いますが、サイトのミニゲームはテスト目的のみです。Serverモードでのゲーム系機能の開発は推奨しません。それはClientモードに任せましょう。
何かツールのリクエストがあれば、コメントをお寄せください。管理者が時間のあるときに検討します。
今日はここまでです。皆さん、端午節(端午の節句)をお健やかにお過ごしください。
- サイトアドレス: https://dotnet9.com/
- サイトソースコード: https://github.com/dotnet9/Dotnet9
- .NETバージョン: .NET 8.0.0-preview.5.23280.8
- WeChat技術グループ: 管理者のWeChat(codewf)を追加し、必ず【入群】の2文字を備考に記入してください。
- QQ技術グループ: 771992300