6
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Visual C# で簡易サイネージアプリを作成してみた

Last updated at Posted at 2024-10-23

最近、Visual C#でデスクトップアプリの作成方法について勉強し始めた初心者です。
いろいろ不備あるかもしれませんが、ご了承ください。

作ったアプリの機能

このあたりの機能があるとよいので、デスクトップアプリ初心者によいかと思って作りました。

  • フォルダを選択ダイアログから指定できる。
  • そのフォルダ内の画像を全画面でスライドショーする。
  • esc キーでスライドショーを終了する。
  • スライドショー中にフォルダの内容が変わったら検知して表示に反映する。
  • 指定した時刻にPCをシャットダウンしてくれる。

バージョン

Microsoft Visual Studio Community 2022
C# : 12.0
.NET : 8.0.10

プロジェクト作成

Visual Studio から「Windows フォームアプリ」を選択してプロジェクト作成

img01.png

画面作成

フォルダ選択画面作成

位置やサイズ調整は、Visual Studio のデザインの画面でマウス操作で行いました。

img08.png

必要なコントロールを配置してプロパティウィンドウから設定をしました。

コントロール名 プロパティ名 VisualStudioで自動生成したイベント
Form Text 簡易サイネージ
TextBox (Name) textBoxFolder
ReadOnly True
Button (Name) buttonSelectFolder buttonSelectFolder_Click
Text ...
CheckBox (Name) checkBox1 checkBox1_CheckedChanged
Text シャットダウン時刻を設定する
DateTimePicker (Name) dateTimePicker1
Format Time
ShowUpDown True
Button (Name) buttonStart buttonStart_Click
Text 開始
FolderBrowserDialog (Name) folderBrowserDialog1
namespace Signage
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            // デフォルトでピクチャフォルダ選択状態にする
            string pictureFolderPath = Environment.GetFolderPath(Environment.SpecialFolder.MyPictures);
            textBoxFolder.Text = pictureFolderPath;

            // 時刻の設定を有効にするか
            changeTimeEnableByCheckBox();
        }

        private void changeTimeEnableByCheckBox()
        {
            // チェックがついていたら時刻設定を有効にする
            dateTimePicker1.Enabled = checkBox1.Checked;
        }

        private void buttonSelectFolder_Click(object sender, EventArgs e)
        {
            // 画像表示するフォルダを選択のボタンを押したときの関数

            DialogResult result = folderBrowserDialog1.ShowDialog();
            if (result != DialogResult.OK)
            {
                return;
            }

            string selectedPath = folderBrowserDialog1.SelectedPath;
            textBoxFolder.Text = selectedPath;
        }

        private void checkBox1_CheckedChanged(object sender, EventArgs e)
        {
            changeTimeEnableByCheckBox();
        }

        private void buttonStart_Click(object sender, EventArgs e)
        {
            // スライドショー用の画面ボタンを押したときの関数

            Form2 frmForm2 = new(textBoxFolder.Text, checkBox1.Checked, dateTimePicker1.Value);
            if (frmForm2.IsDisposed == false)
            {
                frmForm2.ShowDialog();
            }
        }
    }
}

スライドショー画面面作成

メニューの「プロジェクト追加」 > 「フォームの追加(Windows フォーム)」を選択

「Form2.cs」でフォームを追加しました。

img09.png

PictureBox を画面に追加して、

画像が全画面表示になるように Visual Studio のプロパティウィンドウから各コントロールを設定しました。

コントロール名 プロパティ名 VisualStudioで自動生成したイベント
Form (Name) Form2 Form2_KeyPress
FormBorderStyle None
WindowState Maximized
PictureBox Dock Fill
SizeMode Zoom
BackColor Black
Timer (Name) timer1 timer1_Tick
Interval 5000
Timer (Name) timerShutdown timerShutdown_Tick
Interval 60000
FileSystemWatcher (Name) fileSystemWatcher1

全画面の PictureBox の画面ができました。

using System.Data;
using System.Diagnostics;

namespace Signage
{
    public partial class Form2 : Form
    {
        private string textBoxFolderText;
        private bool shutdownChecked;
        private DateTime shutdownTime;

        private string[] imageFiles;
        private int i = 0;

        public Form2(
            string textBoxFolderText,
            bool shutdownChecked,
            DateTime shutdownTime
        )
        {
            InitializeComponent();

            this.textBoxFolderText = textBoxFolderText;
            this.shutdownChecked = shutdownChecked;
            this.shutdownTime = shutdownTime;

            // 指定のフォルダから画像のリストを作成する
            var res = loadImageFiles();
            if (imageFiles == null || imageFiles.Length == 0)
            {
                MessageBox.Show("画像が1枚以上あるフォルダを選択してください");
                Close();
                return;
            }

            // 監視するフォルダのパスを設定
            fileSystemWatcher1.Path = textBoxFolderText;
            // ファイル作成、変更、削除のイベントハンドラを設定
            fileSystemWatcher1.Created += onFileChanged;
            fileSystemWatcher1.Changed += onFileChanged;
            fileSystemWatcher1.Deleted += onFileChanged;
            fileSystemWatcher1.Renamed += onFileChanged;

            showImg(); // 最初の画像はすぐに表示
            timer1.Start(); // 一定間隔で画像を切り替える
            timerShutdown.Start(); // 指定時間にシャットダウンするか判定
        }


        private void onFileChanged(object sender, FileSystemEventArgs e)
        {
            var res = loadImageFiles();
            if (imageFiles == null || imageFiles.Length == 0)
            {
                timer1.Stop();
                timerShutdown.Stop();
                MessageBox.Show("画像が1枚以上あるフォルダを選択してください");
                Close();
                return;
            }
        }

        private bool loadImageFiles()
        {
            // 今回は png 画像のみで取得
            imageFiles = Directory.GetFiles(textBoxFolderText, "*.png", SearchOption.AllDirectories);

            // 画像の表示順をランダムにする
            Random rng = new Random();
            imageFiles = imageFiles.OrderBy(_ => rng.Next()).ToArray();

            return imageFiles.Length > 0;
        }

        private void timer1_Tick(object sender, EventArgs e)
        {
            // timer1に設定した定期実行の関数

            showImg();
        }

        private void showImg()
        {
            string imageFile = imageFiles[i % imageFiles.Length];
            i++;

            pictureBox1.ImageLocation = imageFile;
        }

        private void timerShutdown_Tick(object sender, EventArgs e)
        {
            // timerShutdownに設定した定期実行の関数

            if (shutdownChecked == false)
            {
                return;
            }

            // DateTimePickerコントロールから時刻を取得
            TimeSpan st = shutdownTime.TimeOfDay;

            // 現在の時刻を取得
            DateTime currentTime = DateTime.Now;
            TimeSpan ct = currentTime.TimeOfDay;

            // 現在の時刻とシャットダウン時刻を比較
            if (currentTime >= shutdownTime)
            {
                // パソコンをシャットダウン
                Process.Start("shutdown", "/s /t 0");
            }

        }

        private void Form2_KeyPress(object sender, KeyPressEventArgs e)
        {
            // フォームに設定した、esc キーを押したか判定する関数

            if (e.KeyChar == (char)Keys.Escape)
            {
                timer1.Stop();
                timerShutdown.Stop();
                Close();
            }
        }
    }
}

簡易サイネージアプリができました

設定画面のスクショ

img10.png

わかりにくいですが、全画面で画像表示してる時のスクショです

画像はいらすとやのものです。

img11.png

最後まで見ていただいてありがとうございました。


参考

Windowsアプリケーションをフルスクリーンで表示するには?
https://atmarkit.itmedia.co.jp/ait/articles/0408/27/news105.html

[C#] FolderBrowserDialogの使い方と実装方法
https://af-e.net/csharp-how-to-use-folderbrowserdialog/

[C#] ESCキーを押すことでFormを閉じる方法
https://csharp.programmer-reference.com/form-esc-close/

作って覚えるVisual C# 2022 デスクトップアプリ超入門
https://www.amazon.co.jp/%E4%BD%9C%E3%81%A3%E3%81%A6%E8%A6%9A%E3%81%88%E3%82%8BVisual-C-2022-%E3%83%87%E3%82%B9%E3%82%AF%E3%83%88%E3%83%83%E3%83%97%E3%82%A2%E3%83%97%E3%83%AA%E8%B6%85%E5%85%A5%E9%96%80-%E8%8D%BB%E5%8E%9F%E8%A3%95%E4%B9%8B/dp/4798068330

Visual C# 2022パーフェクトマスター (Perfect Master 186)
https://www.amazon.co.jp/Visual-2022%E3%83%91%E3%83%BC%E3%83%95%E3%82%A7%E3%82%AF%E3%83%88%E3%83%9E%E3%82%B9%E3%82%BF%E3%83%BC-Perfect-Master-186/dp/4798066192

6
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?