0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

【ASP .NET MVC】リアルタイムな画像キャプチャ

Last updated at Posted at 2021-04-05

概要

センサやカメラなど、リアルタイムに計測したイメージデータが撮像できるという条件のとき、そのイメージデータをブラウザ上で随時更新する処理を考えるときに、imgタグでは画像が更新されないことに気づき、ちょっと詰まった。

ASP.NETによる対処法のメモを残す。

原因と対応方法

原因を考えていたところ、ブラウザ側でキャッシュが働いていて、画像を一時保存しているため。
主な方法は2つ。両者ともにメリットがあり、設計指針によって決めればよい。

(1) "Display_20210405_130903.png"などととして、キャプチャ画像をリネームして読み込む。

メリット

  • 画像をストレージに自動的に確保でき、キャプチャした画像データを常にログとして自動で残し続けることが出来る。

  • 時系列データと画像が残っていることから、作業や管理、デバッグがしやすい。

(2) キャッシュを持たない設定にすることで対応する。

メリット

  • ブラウザのキャッシュの影響を考慮せずに、運用が出来る。例えば、メモリ制限があるPCで動かすことを考えて、キャッシュを持つ設定にすると、キャッシュ分だけ画像を残してしまう&そのキャッシュを読み取る処理が発生するので、メモリ効率が悪化してしまい、システム全体でのリアルタイムの動きに影響を与えるかも。

  • アプリの見た目上、原理的には「画像が更新されていない」という状況を防ぐことが出来る。

今回は(2)で対処することを考える。
 

注意

  • 実際にセンサやカメラを使う部分はConfidentialなので、違う画像を使って差し替えます。

  • 今のところ、オンラインで動かすことは考えていませんので、urlはローカル設定のものを使っています。ご注意を

ソースコード

(1) Razorページ(View)を以下のように定義

1秒ごとに、サーバサイドにGETリクエストを行ない、画像のみを変更する。

OPDebug/Index.cshtml

<img src="@Url.Action( "TestLoad", "OPDebug" )" id="OpTestLoadImage" />

@section Scripts{
    @Scripts.Render("~/bundles/jqueryval")
    <script>
        $(function () {
            setInterval(
                function() {
                    $('#OpTestLoadImage').attr('src', '@Url.Action("TestLoad", "OPDebug")');
                }, 1000);
        });
    </script>
}

(2) Controllersでコントローラを以下のように定義

OPDebugController.cs

using System.Drawing;
using System.Threading.Tasks;
using System.Web;
using System.Web.Helpers;
using System.Web.Mvc;

using System.Web.Services;
using OPLocal.ViewModels;


namespace OPLocal.Controllers
{
    public class OPDebugController : Controller
    {
        /* --- 既存ソースコードのため、一部省略 */
       public FileContentResult TestLoad()
        {
            /* 次の行がポイント */
            Response.Cache.SetNoStore(); 

            var img = new WebImage(Server.MapPath("..") + @"\display.png");
            return new FileContentResult(img.GetBytes(), string.Format("image/{0}", img.ImageFormat));
        }
    }
}

Response.Cache.SetNoStore();がポイントで、これによって、ブラウザ側がキャッシュを持つのを防いでくれるようになる。

(3) ソリューション直下にdisplay.pngと、"org1.png"、"org2.png"を設定。

image.png

image.png

カメラから取り込まれたデータが、display.pngとして保存されると想定するが、とりあえずダミーで、リアルタイムのカメラの動きの代わりに、org1.bmpとorg2.bmpのどちらかをリネームして表示できるようにするものとする。

実行結果

以下、他のGET命令によるルーティングを行なわない前提で検証

display.pngがない
image.png

org1.pngをdisplay.pngにリネーム
image.png

org2.pngをdisplay.pngにリネーム
image.png

予想通り動いてくれた。

この後は、リアルタイム処理中は、実際にキャプチャフォルダをローカルに設定し、そのローカルに設定したファイルのうち最新のものを保存する。それを、読み取ることで解決する予定。

0
0
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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?