page icon

AWSとi WEBCONの連動案

 
WEB UIで例えば64×48ピクセルの画像を自由に配置出来、この画像の中に計測データを表示させ、値が設定した上限、下限閾値になった場合は画像を赤く表示させたいのですがどのようなプログラムで開発すれば良いでしょうか?
 
WEB UIで特定の条件に基づいて画像を表示・更新する機能を開発するには、以下の技術を組み合わせてJavaScriptを中心に実装するのが良いでしょう。以下に具体的な方法を示します。
使用技術
1. HTML/CSS: 画像のレイアウトやスタイルを設定。
2. JavaScript (特にReact, Vue, もしくは原生JavaScript): 計測データを受け取り、閾値のチェックや画像の状態更新を行う。
3. Canvas APIまたはSVG: 画像の色変更やデータの動的な表示に便利。
4. WebSocketやAjax: 計測データのリアルタイム取得に利用。
実装方法の流れ
 
以下に基本的な流れとサンプルコードの概略を示します。
1. HTMLで画像の配置と基本構造を作成
まず、計測データを表示する画像を配置するHTMLを用意します。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>計測データ表示</title> <style> .data-container { position: relative; width: 64px; height: 48px; } .data-image { width: 100%; height: 100%; background-color: white; /* 初期色 */ } .data-value { position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%); font-size: 12px; font-weight: bold; } </style> </head> <body> <div class="data-container"> <div id="data-image" class="data-image"></div> <div id="data-value" class="data-value">0</div> </div>
</body> </html>
2. JavaScriptで計測データの取得と閾値判定ロジック
JavaScriptで計測データを取得し、閾値を判定して色を変える処理を記述します。以下は基本的なサンプルです。
// 計測データの仮のサンプル値 let measurementData = 25; // 動的に更新される数値と仮定
// 上限・下限閾値 const upperThreshold = 50; const lowerThreshold = 10;
// DOM要素を取得 const dataImage = document.getElementById('data-image'); const dataValue = document.getElementById('data-value');
// データを監視して閾値に応じて色を変える関数 function updateDisplay(data) { dataValue.textContent = data; // データを表示
}
// 定期的にデータを更新する例 setInterval(() => { // サンプルの測定データを更新(実際はAPIやWebSocketから取得) measurementData = Math.floor(Math.random() * 100); updateDisplay(measurementData); }, 1000); // 1秒ごとに更新
3. サーバーからのリアルタイムデータ取得
リアルタイムの計測データを反映する場合は、WebSocketAjaxでサーバーと通信します。
以下はWebSocketを使用した例です。
// WebSocket接続(例:ws://example.com/data) const socket = new WebSocket('ws://your-server.com/data');
// WebSocketからデータを受信した際の処理 socket.onmessage = function(event) { const data = JSON.parse(event.data); // 受信データを解析 updateDisplay(data.measurement); // 取得データに応じて更新 };
4. 開発フレームワークの選択(任意)
もし、開発をさらに効率化したい場合、ReactVueなどのフレームワークを使うと、状態管理やUI更新が容易になります
 
任意場所への移動
画像を任意の場所に移動できるようにするためには、JavaScriptを使用してドラッグ&ドロップ機能を実装するのが一般的です。以下は、HTML/CSS/JavaScriptを使って画像を自由に移動できるようにする方法の基本的な例です。
手順
1. HTML/CSSで画像の配置と基本スタイルを設定します。
2. JavaScriptでドラッグ&ドロップの動作を実装します。
3. リアルタイムな位置情報の更新が必要であれば、位置をWebSocketなどでサーバーに送信することも可能です。
サンプルコード
以下のサンプルコードは、画像をドラッグして任意の場所に移動できるシンプルな実装例です。
1. HTMLとCSS
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>ドラッグ&ドロップで画像を移動</title> <style> /* ドラッグ可能な画像のスタイル / #draggable-image { width: 64px; height: 48px; position: absolute; cursor: move; background-color: lightblue; / 初期背景色 */ } </style> </head> <body> <!-- ドラッグ可能な画像 --> <div id="draggable-image"> <span id="data-value">0</span> </div>
</body> </html>
2. JavaScriptでドラッグ&ドロップ機能を実装
// ドラッグ対象の画像エレメントを取得 const draggableImage = document.getElementById('draggable-image');
// マウス位置とエレメントのオフセットを保持する変数 let offsetX, offsetY;
// マウスダウンイベントでドラッグを開始 draggableImage.addEventListener('mousedown', (e) => { offsetX = e.clientX - draggableImage.getBoundingClientRect().left; offsetY = e.clientY - draggableImage.getBoundingClientRect().top;
});
// マウスムーブイベントで位置を更新 function onMouseMove(e) { draggableImage.style.left = ; draggableImage.style.top = ; }
// マウスアップでドラッグを終了 document.addEventListener('mouseup', () => { document.removeEventListener('mousemove', onMouseMove); });
説明
• mousedownイベントでドラッグを開始します。この時、画像の左上隅からマウスまでのオフセットを記録します。
• mousemoveイベントで画像の位置を更新し、マウスに追従するようにします。
• mouseupイベントでドラッグを終了し、mousemoveのリスナーを削除してイベントを解放します。
画像の位置をサーバーに送信する(オプション)
もしリアルタイムで画像の位置をサーバーに送信したい場合、WebSocketを利用して位置データを送信することができます。
WebSocketを利用して位置を送信する例
// WebSocketの接続を作成 const socket = new WebSocket('ws://your-server.com');
// ドラッグが終了した際に位置をサーバーに送信 document.addEventListener('mouseup', () => { // 画像の位置を取得 const position = { left: draggableImage.style.left, top: draggableImage.style.top, };
});
注意点
位置の保持: ページを再読み込みすると位置がリセットされるため、位置を保存する場合はローカルストレージやデータベースに保存して、再表示時にその位置で画像を表示する処理が必要です。
タッチ対応: タッチスクリーン対応が必要な場合、touchstart、touchmove、touchendイベントも追加するとモバイルデバイスでも動作します。
この方法で、画像を自由に画面上でドラッグして配置することができます。
 
上記のWEB UI画像にRaspberry piのメモリに設けた計測データ、閾値データをリアルタイムに通信させ、閾値を超えたら別の画像データのgifアニメを動かし、Raspberry PiのI2Cに接続したデバイス出力をONにするなど画像間の通信プログラムを作成できますか?
はい、Raspberry Piのメモリ内に保存した計測データと閾値データをリアルタイムにWeb UIに通信し、閾値を超えた場合にGIFアニメーションを表示し、I2Cデバイスの出力を制御するプログラムを作成することは可能です。以下にその構成の概要とサンプルコードを示します。
構成
1. Raspberry Piでのサーバープログラム: 計測データを取得し、WebSocketまたはHTTP経由でWeb UIに送信するサーバープログラムをPythonで作成します。
2. Web UI: JavaScriptでリアルタイム通信を行い、計測データを受信して表示。閾値を超えた場合にGIFアニメーションを表示。
3. I2Cデバイス制御: Raspberry PiのI2C経由でデバイスを制御するプログラムをPythonで実装します。
以下に、これらの各要素のサンプルコードを示します。
1. Raspberry Piでのサーバープログラム(Python + WebSocket)
Raspberry Pi上でWebSocketサーバーを立ち上げ、計測データをリアルタイムで送信します。計測データと閾値データをメモリ上で管理し、Web UIに送信します。また、閾値超過時にI2Cデバイスを制御します。
import asyncio
import websockets
import json
import smbus  # I2C制御用
import random  # サンプルデータの生成用
# I2C初期化
bus = smbus.SMBus(1)
I2C_ADDRESS = 0x20  # I2Cデバイスのアドレス
# 閾値設定
UPPER_THRESHOLD = 50
LOWER_THRESHOLD = 10
async def send_data(websocket, path):
while True:
# サンプル計測データ(ランダム生成)
measurement_data = random.randint(0, 100)
# データ構造の準備
data = {
"measurement": measurement_data,
"threshold_exceeded": measurement_data > UPPER_THRESHOLD or measurement_data < LOWER_THRESHOLD
}
# 閾値チェック
if data["threshold_exceeded"]:
# I2Cデバイスの出力をON
bus.write_byte_data(I2C_ADDRESS, 0x01, 0xFF)  # 例として出力をONに設定
else:
# I2Cデバイスの出力をOFF
bus.write_byte_data(I2C_ADDRESS, 0x01, 0x00)
# WebSocket経由でデータ送信
await websocket.send(json.dumps(data))
await asyncio.sleep(1)  # 1秒ごとにデータ送信
# WebSocketサーバーの起動
start_server = websockets.serve(send_data, "0.0.0.0", 8765)
asyncio.get_event_loop().run_until_complete(start_server)
asyncio.get_event_loop().run_forever()
2. Web UI (HTML + JavaScript) - WebSocketによるデータ受信とGIF表示
WebSocket経由でデータを受信し、閾値を超えた場合に画像をGIFアニメーションに切り替える処理をJavaScriptで行います。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>リアルタイム計測表示</title>
<style>
#data-image {
width: 64px;
height: 48px;
}
</style>
</head>
<body>
<div>
<img id="data-image" src="normal.png" alt="Normal Image">
<div id="data-value">0</div>
</div>
<script>
const dataImage = document.getElementById('data-image');
const dataValue = document.getElementById('data-value');
// WebSocket接続を開く
const socket = new WebSocket('ws://localhost:8765');  // サーバーのIPアドレスに変更
// WebSocketからデータを受信した際の処理
socket.onmessage = function(event) {
const data = JSON.parse(event.data);
dataValue.textContent = data.measurement;
// 閾値を超えた場合、アラート用のGIFに変更
if (data.threshold_exceeded) {
dataImage.src = 'alert.gif';  // アラート用のGIFアニメーション
} else {
dataImage.src = 'normal.png';  // 通常時の画像
}
};
socket.onopen = function() {
console.log("WebSocket接続が開かれました");
};
socket.onclose = function() {
console.log("WebSocket接続が閉じられました");
};
</script>
</body>
</html>
説明
1. Raspberry Piサーバープログラム:
• 計測データをランダムに生成していますが、実際にはセンサーからのデータ取得コードに置き換えます。
• I2Cデバイスの制御にはSMBusを使用し、閾値超過時に出力をONにしています。
• WebSocketでJSONデータをリアルタイムにWeb UIに送信しています。
2. Web UI:
• JavaScriptでWebSocket接続を行い、リアルタイムに計測データを受信。
• data.threshold_exceededがtrueの場合、通常の画像をGIFアニメーションに切り替える処理を行っています。
注意事項
セキュリティ: 実装する際は、WebSocket通信を暗号化するためにWSSを使用するか、接続制限をかけるなどのセキュリティ対策を行ってください。
I2Cデバイスのアドレスと制御: 実際のデバイスに合わせてI2Cアドレスや出力設定を確認・調整してください。
サーバーとクライアントのIPアドレス: WebSocketのURLに、Raspberry Piの実際のIPアドレスを設定してください。
この構成により、計測データをリアルタイムで表示し、閾値超過時に画像を変更しつつ、Raspberry PiのI2Cデバイスも制御するWeb UIを実現できます。
 
上記をAWSと現場に設置した計測制御できるRaspiシステムで実現するための手順を教えて
AWSと現場に設置した計測・制御が可能なRaspberry Piシステムを連携させ、リアルタイムで計測データをAWSに送信し、閾値超過時にAWSからRaspberry Piの制御を行う手順は以下のようになります。これにはAWS IoT Coreの活用が効果的です。
必要な構成要素
1. AWS IoT Core: Raspberry Piからデータを送信し、AWSでデータを処理し、制御コマンドをRaspberry Piに返すためのメッセージブローカー。
2. AWS Lambda: データ処理や閾値チェックを行い、必要な場合に制御信号をRaspberry Piに送信。
3. AWS CloudWatch: データの監視やアラート設定。
4. AWS S3(任意): 計測データやログを保存するためのストレージ。
5. AWS IoT Rule: Raspberry PiからのデータをLambda関数や他のAWSサービスにルーティング。
6. Raspberry Pi: 計測デバイスとして使用し、AWS IoTと接続してデータを送信・制御信号を受信。
手順概要
1. AWS IoT Coreでデバイス(Raspberry Pi)をセットアップ
1. AWS IoT Coreにログインし、「Manage」>「Things」で新しいThing(デバイス)を作成。
2. Thing作成時にセキュリティ証明書を発行し、Raspberry Piにダウンロードします。
3. ポリシーを作成し、Thingに適用します。このポリシーは、AWS IoT CoreとRaspberry Piの双方向通信を許可します。
2. Raspberry Piでデータを取得し、AWS IoT Coreに送信するプログラムを作成
Raspberry Piから計測データを取得し、AWS IoT Coreに送信するPythonスクリプトを作成します。
Pythonスクリプト例
import json
import time
import random
from AWSIoTPythonSDK.MQTTLib import AWSIoTMQTTClient
# AWS IoT設定
client = AWSIoTMQTTClient("raspi_client")
client.configureEndpoint("your-iot-endpoint.amazonaws.com", 8883)  # エンドポイントはAWS IoT Coreのものに置き換える
client.configureCredentials("AmazonRootCA1.pem", "private.pem.key", "certificate.pem.crt")
client.configureOfflinePublishQueueing(-1)  # 無限キュー
client.configureDrainingFrequency(2)  # 2Hz
client.configureConnectDisconnectTimeout(10)
client.configureMQTTOperationTimeout(5)
# MQTT接続
client.connect()
# データ送信
while True:
# サンプルの計測データ(実際のセンサーに置き換え)
measurement_data = random.randint(0, 100)
payload = {
"device_id": "raspi_001",
"measurement": measurement_data,
"timestamp": int(time.time())
}
client.publish("raspi/measurements", json.dumps(payload), 1)
print("Data sent:", payload)
time.sleep(5)  # 5秒ごとにデータ送信
3. AWS IoT Coreでルールを作成してデータを処理
1. AWS IoT Coreの「Act」から新しいルールを作成し、raspi/measurementsトピックのデータを取得する条件を設定。
2. ルールのアクションとして「Lambda関数」を選択し、次のステップで作成するLambda関数にルーティングします。
4. Lambda関数で閾値をチェックし、制御信号を送信
1. AWS Lambdaで新しい関数を作成します。この関数は、受信した計測データを処理し、閾値を超えた場合にRaspberry Piに制御信号を送信します。
2. Lambda関数に必要なIAMロールを設定し、AWS IoTにデータをパブリッシュする権限を与えます。
Lambda関数のコード例
import json
import boto3
iot_client = boto3.client('iot-data', region_name='us-east-1')  # 使用するリージョンに合わせる
UPPER_THRESHOLD = 50
LOWER_THRESHOLD = 10
def lambda_handler(event, context):
measurement = event.get('measurement', 0)
device_id = event.get('device_id', 'unknown')
# 閾値判定
if measurement > UPPER_THRESHOLD or measurement < LOWER_THRESHOLD:
# 閾値超過時に制御信号をRaspberry Piに送信
control_payload = {
"command": "TURN_ON",
"device_id": device_id
}
response = iot_client.publish(
topic="raspi/control",
qos=1,
payload=json.dumps(control_payload)
)
print("Control command sent:", control_payload)
return {
'statusCode': 200,
'body': json.dumps('Processed')
}
5. Raspberry Piで制御信号を受信してI2Cデバイスを制御
Raspberry Pi上で、AWS IoT Coreから制御信号を受け取るスクリプトを作成します。制御信号を受信すると、I2Cデバイスの出力をONにします。
Pythonスクリプト例(制御信号の受信とデバイス制御)
import json
import smbus
from AWSIoTPythonSDK.MQTTLib import AWSIoTMQTTClient
# I2C設定
bus = smbus.SMBus(1)
I2C_ADDRESS = 0x20
# AWS IoT設定
client = AWSIoTMQTTClient("raspi_control_client")
client.configureEndpoint("your-iot-endpoint.amazonaws.com", 8883)
client.configureCredentials("AmazonRootCA1.pem", "private.pem.key", "certificate.pem.crt")
client.configureOfflinePublishQueueing(-1)
client.configureDrainingFrequency(2)
client.configureConnectDisconnectTimeout(10)
client.configureMQTTOperationTimeout(5)
# コールバック関数
def control_callback(client, userdata, message):
payload = json.loads(message.payload)
command = payload.get("command")
if command == "TURN_ON":
bus.write_byte_data(I2C_ADDRESS, 0x01, 0xFF)
print("Device turned ON")
elif command == "TURN_OFF":
bus.write_byte_data(I2C_ADDRESS, 0x01, 0x00)
print("Device turned OFF")
# トピックにサブスクライブ
client.connect()
client.subscribe("raspi/control", 1, control_callback)
# 永続的に実行
try:
while True:
pass
except KeyboardInterrupt:
print("Stopped")
まとめ
1. Raspberry Piで計測データを取得し、AWS IoT Coreに送信。
2. AWS IoT CoreでデータをLambdaにルーティングし、閾値チェックを行う。
3. 閾値を超えた場合、Lambdaから制御信号をAWS IoT Core経由でRaspberry Piに送信。
4. Raspberry Piが制御信号を受信し、I2Cデバイスの出力をON/OFFに制御。
これにより、AWSとRaspberry Pi間でリアルタイムな計測データのやり取りと制御を実現できます。
 
参考