macsbug

Just another WordPress.com site

VL6180X distance sensor in ESP8266

leave a comment »

VL6180X 距離センサーを ESP8266 で動かす。          2016.09.25

機能:最大 60cm までの距離を mm単位で表示します。
構成:OLED + WeMos D1 mini Pro + VL6180X。
_  I2C接続で OLED – D1 mini – VL6180X は 4ピンソケット で接続。
_  I2C は ソケット接続すると 他の I2C も簡単に交換でき便利です。



 

VL6180X 近距離センサーのお話:
伊仏合弁 STMicroelectronics社の製品で赤外光が対象物で反射し戻るまでの
時間を測定する高精度の環境光/近接センサーです。0~60cmまで計測可能。
分解能は1mm。精度は100mmで3%。応答速度は 30ms。
精度考察:8bitセンサーで 精度0.25 で一般的基準の0.5をクリアー。
今回のスケッチは 765mm まで表示します。

スマートフォンやタブレット端末、家庭用ゲーム機のコントローラー、
家電機器、産業機器、自動車ロボットなどに使用されています。
2個使用する事により ジェスチャー機能も可能です。

VL53L0X のお話:
2016.06.10 に発売され 最大2mまでの絶対距離(単位:mm)を30ms以内に測定。
Arduino用モジュールも販売されています。


 

準備:費用合計:1582円。(低価格のOLEDで1466円)

No Nomen  Link Price Memo
1 VL6180X Board VL6180X Board 718円  ebay
2 WeMos D1 mini WeMos D1 mini 342円 $3.39
3 OLED 128 x 64 OLED 128 x 64 522円 $4.02
4 Resistor 10KΩ  –  –  2個
5 4ピンコネクター  –  –  1個
6 VL6180X Library vl6180x-arduino  –  pololu
7 OLED Library esp8266-oled-ssd1306  –  squix78

 

部品の詳細:購入先と価格。

No Nomen  Link Price Memo
1 VL6180X Board VL6180X Board:ebay  718円 ebay 4個 $28.45 ,2872円
VL6180   Board VL6180   Board:eray 1543円 1299 + 244:未調査
VL6180   Board VL6180   Board:ebay 1587円 少し高い:未調査
VL6180X Board Strawberry Linux 1580円 1200 + 380:取り付け安い
VL6180X Board SWITCHSCIENCE 1694円 1544 + 150:2.4倍 高い
VL6180X Board 朱雀技研工房ストア 1752円 1532 + 250:2.4倍 高い
2 D1 mini Pro D1 mini Pro  683円 $6.76:WeMos,16MB Flash
3 OLED 128 x 64 OLED 128 x 64  406円 $4.02:低価格:未調査
OLEDの端子配列は、VCC, GND, SCL, SDA が望ましい。
今回の VL6180X ( GY6180 ) と同一配列。
注意:電源の端子配列が逆の GND, VCC, SCL, SDA の物がある。

 

配線:
1. D1 mini と OLED は端子を重ねました。VL6180Xはコネクターで接続します。
2. D7(13)(SCL), D6(12)(SDA) 端子は 10KΩ チップ部品でプルアップします。
3. D8 は GND へ配線します。


 

技適 ( TELEC ) を不要にする方法:

今回の電子工作は電波は使用しませんので 電波の出力を停止しました。
WeMos D1 mini は TELEC の記載はありません。
この命令により 電波を出力しない場合 技適は適用しないと聞いています。
これによりESP-WROOM-02 TELEC を使用せずともは日本国内で使用できると
聞いています。さらに電波を出力しない為に省電力にする事ができます。
WiFi.mode(WIFI_OFF);


 

VL6180X:

参考:
Pololu:VL6180X Time-of-Flight Distance Sensor Carrier
_   with Voltage Regulator, 60cm max:基板の基本が書かれている。

VL6180X:Proximity and ambient light sensing (ALS) module

AN4545 Application note:VL6180X basic ranging application note:ICの基本。
_ このマニュアルは良く読む必要がある。

DT0030 Design tip:VL6180X ambient light sensing


 

配線図:
_ VL6180X ( GY6180 ) の基板(上記基板画像)を調べ 以下の図面を作成しました。
_ 基本は Polou の VL6180X ですが  GY6180 は 小型化された基板です。
_   Polou の配線図はありますが VL6180X ( GY6180 ) は未公開の様です。
_ VL6180X は 2.8V 動作です。
_ LDO ( 540L )は 2.8VOUTPUT。
_ 入力の SCL, SDA は 3.3V。
_ Transistor ( 702V ) でレベル変換し 出力は 2.8V。


 

校正:以下に校正の要領が記載されています。
UM1651 User manual:
_ VL6180X premium evaluation kit (EVK) hardware user manual


 

感想:
VL6180X:
距離:
_  scalingで x3 765 mm まで計算可能ですが実測では 561 mm まででした。
_ マニュルアルには他の値も書いてある様ですがライブラリは 1,2,3 が設定。
_ 最大10cm までの情報もありますが 今回の条件では 56cm まで可能でした。
_ データーの取得時間は 30ms と速い。この応答速度は重要ですね。
アベレージング:
_ データーの変動を軽減する為に簡単なアベレージングを加えました。
_ 効果は 1/ root ( 回数 ) です。例えば 16回ならば 4倍の精度になります。
_ この場合 速度が低下しますので 必要なければ取り除いてください。
ミスカウント:
_ 561 mm以上の距離で条件によりミスカウントする時がある。
_ ダブルバウンスも含め分析が必要である事と対策が必要かと思います。
何に使うか:
_ 今回は距離を表示するのみでケースも作りませんでした。
_ このセンサーは奥が深いので驚いています。

VL53L0X:最大 2m まで測定でき AliExpress や ebay で販売しています。
_ 応答速度が速く(30ms)ドローン等に最適と思われます。
_ 今回のVL6180X と同じく小型化したものがあり 現在ESP8266 では
_ Wdt error (1, 6) がでて動作せず 調査中です。
_ AliExpress や ebay での小型化した基板(VL6180XとVL53L0X)を比較した所
_ パターンは同じでした。違いは VL53L0Xでの LDO は 662K で 3.3V出力の
_ ものです。VL53L0X は 2.8V 仕様ですので 疑問があり中断しています。


スケッチ:


/* VL6180X. The sensor uses 1x scaling by default.
scaling to 2x or 3x : 2mm or 3 mm .*/

#include 
#include 
#include "SSD1306.h"
SSD1306 display(0x3c, 12, 13);  // SDA, SCL
#include 
#define scaling 3 // scaling factors are 1, 2, or 3.
VL6180X sensor;

void setup(){
  WiFi.mode(WIFI_OFF);
  Wire.begin(12, 13);  // SDA, SCL
  display.init();
  display.flipScreenVertically();
  display.displayOn();
  display.clear();
  sensor.init();
  sensor.configureDefault();
  sensor.setScaling(scaling);
  sensor.setTimeout(500);
}

void loop(){
  int d = 0;
  for ( int i = 0; i< 16; i++ ){   // accuracy=1/root(N)
    d = d + sensor.readRangeSingleMillimeters();
  }
  d = d / 16;
  String mm = String(d) + " mm";
  if (sensor.timeoutOccurred()){mm = " Timeout";}
  if (d == 255 * scaling){ mm = " over";}
  display.clear();
  display.setFont(ArialMT_Plain_16);
  display.setTextAlignment(TEXT_ALIGN_LEFT);
  display.drawString(0,  0, "VL6180X  scale " + String(scaling));
  display.setTextAlignment(TEXT_ALIGN_RIGHT);
  display.setFont(ArialMT_Plain_24);
  display.drawString(120, 32, mm);
  display.display();
}

Written by macsbug

9月 25, 2016 at 12:10 am

カテゴリー: ESP8266

YEN rate displayed in Pythonista3

leave a comment »

円レートを iPad に表示するアプリを Pythonista 3 で作りました。      2016.09.24

1ドルを円に換算した値を表示し ” 101.1 ” と音声で知らせ、数値の変化をグラフ表示します。



 

海外(ebay)の部品を購入する時にブラウザーで円レートを見て購入しています。
毎回 アクセスするのは面倒ですので iPad に表示するアプリを作りました。
円高のタイミングに購入し 安くできると いいかなと思っています。


 

機能:
1、1ドルに対する現在の円レートを表示し、金額を「音声」で知らせてくれます。
2、1日、5日、3ヶ月、1年、2年、5年間のグラフを順次表示します。
3、間隔を置いてリアルタイムに表示します。


 


感想:
たいしたソフトではありませんが自分で作った物が動くと楽しいものです。
基本は「為替レート変換君」のデーター取得先を使用しています。
リンク先のデーターをテキストフィールドやウエブビューに表示するものです。
音声で金額を教えてくれるのはチョットいい感じです。

 


レイアウト:Script with UI での配置です。


スクリプト:


import requests
import ui
import time
import speech
import sound

def web(url):
	re = requests.get('http://fx.monegle.com/fx.php?rate=1&q=USD')
	d1 = str(re.text)
	d2 = d1.find('Bid:')
	d3 = d1[d2+4:d2+4+8]
	v['textfield1'].text = str(round(float(d3),2))
	sound.play_effect('Ding_3')
	speech.say(str(round(float(d3),1)))
	for i in range(6):
		v['textfield2'].text = str(url[i][47:49]).upper()
		v['webview1'].load_url(url[i])
		time.sleep(5)
	v['textfield2'].text = str(url[2][47:49]).upper()
	v['webview1'].load_url(url[2])

# setup
url = ['http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=1d&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=5d&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=3m&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=1y&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=2y&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=5y&l=on&z=m&a=v&p=s&q=1',
       'http://ichart.finance.yahoo.com/z?s=USDJPY=X&t=3y&l=on&z=m&a=v&p=s&q=1']
v = ui.load_view('_en')
v.background_color = '#d3dad7'
v.present('sheet') 

# main
while True:
	web(url)
	time.sleep(60)


Written by macsbug

9月 24, 2016 at 7:50 am

カテゴリー: Apple, Pythonista

WEMOS D1 mini Pro

leave a comment »

新製品情報:WEMOS D1 mini Pro                    2016.09.01



仕様:WEMOS D1 mini Pro
– 16M bytes external antenna connector ESP8266 WIFI Internet of Things development board
1. USB UARTは CH340GからCP2104を採用。
2. FLASHを4MBから16MBにアップ。
3. AntennaをPCBからceramic antennaとExternal antennaに変更。
4. D1 miniと同じ大きさで超小型を継承。
5. LDOの変更はなし。
6. TELECはなし。
7. Price : $ 6.76 ($5.00 + $1.76 )( 2016.09.01 )


経過:
WeMos Electronic からのみの販売数が低下している中での新製品。
WeMos Electronic 単独での D1 mini の販売は 8月に総計1万個の予想があった。
WEMOS D1 mini Pro は 2016年9月1日より販売が開始された。
USB接続の安定性向上,FLASH Memoryの容量アップ,アンテナの改善がされている。


販売分析:WeMos Electronics
WeMos D1 mini は AliExpres で WeMos Electronics のみの販売であった。
世界一の販売数と伸び率を誇り 購入者の要求に合った製品である事を示している。
_ 超小型、端子配列の利便性、拡張ボード、低価格。
_ 特に価格は 2016年9月1日現在 346円で購入できる最強の製品となっている。
_ 低価格は海外での評判が良く気楽に多数の電子工作ができる事になる。
2016年7月から AliExpress や ebay で他の業者から販売が開始された。
他業者から販売された時点より WeMos Electronics のみからの販売数は低下を始めた。
他業者の販売数を調査していない為、総数は分析できていません。

WeMos Electronic:WeMos D1 mini の販売台数。2016.03.29 〜 2016.09.01

WeMos Electronic:拡張ボードの販売台数。2016.03.29 〜 2016.09.01


感想:
WEMOS D1 mini Pro:
_ WeMosは 販売戦略で最強となる あの手は打ってきませんでした。
_ FLASH メモリーの増加による効果は不勉強の為 詳細は省きました。
_ 日本国内では規制で自由度は無いですが 海外では自由度が大きく
_  外部アンテナなどは便利でしょうね。
_  海外での実験例:ESP8266 Wifi Range/Distance Tests
_   ESP8266+Ext. Antenna = 479m。
_   ESP8266+PCB Antenna = 366m
_ 弱点は 負荷を多くした場合 LDO の発熱が大きい事。
_  D1 mini はクラッシュしない程度だが 容量不足を示している。
_  この改善は実施していない。
_  この超小型の大きさにあった拡張ボードを使用する分には問題はない。
IOT:IOTの1つの側面として1個では効果が少なく楽しみも少なくなる。
_  低価格で多数作れる事により効果が発揮できる面がある。
_  D1 min1 の価格は国内同等品に対し約 1/7 という低価格である。


Written by macsbug

9月 1, 2016 at 1:00 am

カテゴリー: ESP8266

Pythonista Beginner : Part 3

leave a comment »

GitHubから repo をダウンロードする方法。「GitHubGet.py」を試す。 2016.08.28


GitHubGet.py」は、クリップボードに URL をコピーし実行 すると
自動的に目的のファイル ( 例:GitHubGet-mester ) ができます。


経緯:
Pythonista Beginner : Part 2で 使用した「github_download.py」は
クリップボードにURLをコピーして 実行しますが 入力や解凍操作が必要でした。
「GitHubGet.py」はクリップボードに URL をコピーのみでダウンロードします。


入手方法:「GitHubGet.py」を入手する。
_ 初回は直接「GitHubGet.py」をコピーするか
_ Pythonista Beginner : Part 2の「github_download.py」の方法で入手します。


事例:jsbain の Audio.py をダウンロードしてみます。
_ Audio.py の URL をコピーする。
_ GitHubGet.py を実行する。
_  メモ:Pythonista 3 の場合は 事前に Python 2 to 3 の変換を実行しておく事。
_ 2cf4998… ファイルができ ファイルの中には Audio.py ができます。



感想:
「GitHubGet」を公開された jsbain に感謝致します。
先人達が素晴らしい多くの実例やサンプルを公開されており感謝致します。
これらの実例やサンプルは ほとんど紹介されていない為に 備忘録としました。


 

Written by macsbug

8月 28, 2016 at 1:02 am

カテゴリー: Apple, Pythonista

How to install OS X

with 2 comments

OS X をインストールする方法。                2016.08.23


OS Xを HDに作成すると以下の様なメッセージがでて インストールが動作しません。
「アプリケーションを検証できません」の意味が解りません。
「ダウンロード中に破損したか不正に変更された可能性があります」には
_ ちょっと たじろぎましたが これは正しくない表示ですね。
「このアプリケーションを削除してから、Mac App Store の購入済み”ページ
_ にアクセスして新しくダウンロードしてください」
_ えっ、削除したりダウンロードしたり そんな面倒な事をするのですか。


原因:アプリケーションが真性なものであるかどうかを検証する為の証明書を
_  アップルが変えてしまった為です。

方法:
1. App Storeでもう一度ダウンロードする。
_  ダウンロードは1時間半くらいかかります。
_  購入記録から削除されている場合 この方法は実施できません。
.
2. マックの日付を変更し 次に OS X Maverics インストール(例) を使用する。
_  準備:各 OS X インストールを用意してください。(一番上の画像)
_  環境設定で日付を2016年2月1日に変更してインストールを動かします。

以上で インストールは動作し30〜50分程度で準備ができインストールできます。

インストール後は環境設定の日付を もとに戻しておきましょう。


感想:
1. OS X を HD に作る事は少ないので知りませんでした。
_  これは2016年2月頃の話なのですね。
2. App Store から DL する時に 購入記録を探し難く 迷いました。
_  友人の場合は 購入記録から削除されて DL できない状態がありました。
3. ターミナルで日付の変更をする方法がありますが 素人には分かり難いです。
4. 各バージョンの OS X インストールは保存しておいた方が良いですね。
_  私は全ての OS X インストールを保存しておき それを使用しました。
5. アップルさん 面倒な事しないで欲しいです。
6. 購入記録が削除されている場合 と OS X インストールが無い場合は
_  どうするのでしょうか。

Written by macsbug

8月 23, 2016 at 2:28 am

カテゴリー: Apple

Pythonista Beginner : Part 2

leave a comment »

GitHub の ファイル を Pythonista 3 に ダウンロード する方法。    2016.08.15



.
編集では ネット上のファイルを ダウンロードする場面が多くあります。
ダウンロードの操作方法は 手間で 時間を費やす事もあります。
xxx.py と xxx.zipスクリプトでダウンロードする方法をまとめました。
これによりファイル操作が容易になり 開発がスムーズに行えます。


概要:
1. ファイルの種類: 「xxx.py」「xxx.pyui」「xxx.zip」があります。
2. スクリプトで入手: 「github_download.py」を使用します。
3. URL: URL を入力するとファイルが ダウンロード されます。
4. 結果: xxx.py や xxx.pyui ができます。zip は xxx.zip ができます。
5. 場所: 作成されるファイルの場所は 「githib_download.py」の場所か
_      Shared Folderに出来ます。
使用環境:
_ iPad 3 iOS 9.3.3 + Pythonista 3 ( 有料:1200円)
_ iMac 27int OSX 10.8.5


 項目: 方法は以下の4つの手順です。
1. ファイルの URL を取得します。
2. github_download.py:このスクリプトでファイルをダウンロードします。
3. github_download.py を実行します
4. ダウンロードの結果と zip ファイルの解凍。


 方法:
1. ファイルの URL を取得します。
_  xxx.py を直接示す URL 又は RW ボタンを開いた時の URL です。
_  以下の様に コピーすると簡単です。URL はクリップボードに入ります。

_ zip File の場合は 以下の様に URL をコピーすると簡単です。

 


 2. github_download.py:このスクリプトでファイルをダウンロードします。
_  参考:bin フォルダー:Pythonista Beginning:
_   2. ptinstaller.py を iPad (Pythonista) に読み込む。
_   最下部に「おさらい:ptinstaller.py の入手と bin フォルダーの作成方法」
_  参考:Pythonista-Tools / Pythonista-Tools / github_download にある。

bin フォルダーの中にある
「github_download.py」
を動かします。

github_download.py の場所:
bin /
GitHub Tools /
github_download /
github_download.py

 


 3. github_download.py を実行する
_ 直前にURLをコピー済みの時は入力欄への入力は不要です。以下の様に
_ 入力済みになっています。末尾に .py や .zip がある事を確認します。
_ その後「Download」と「OK」を選択するだけになります。

方法1で既にURLをコピー済み
の場合はURL欄への入力は不要。
.
未入力の場合はURLを入力し
「Download」を選択する。
方法1で既にURLをコピー済み
の場合はURL欄への入力は不要。
.
未入力の場合は名前を入力し
「OK」を選択する。
zip は名前に「.zip」を付ける。
スクリプトは「.py」を付ける。

 4. ダウンロードの結果と zip ファイルの解凍:

master.zip が 保存されました。
zip の解凍方法:
Extract Archive… ボタンを押すと
解凍され master というフォルダー
が出来ます。フォルダーの中は
xxx.py 等が できます。

 


 補足: スクリプトのチェック方法

マークを選択。
Python 2 to 3 を選択。
変換の種類はUse 2to3 を選択。
修正の必要がある時は 線が引かれ
変更内容は緑色で表示されます。
Apply を押すと 変更されます。

 


 おさらい: ptinstaller.py の入手と bin フォルダーの作成方法。
入手方法:以下のスクリプトを記述し 実行して ptinstaller.py を DL する。
:
import requests as r
o=open(‘ptinstaller.py’,’w’)
o.write(r.get(‘https://raw.githubusercontent.com/ywangd/pythonista-tools-installer/master/ptinstaller.py’).text)
o.close()
:
bin フォルダーの作成方法:
ptinstaller.py を実行すると Fun から Utilitys のメニューがでます。
全てか Github Tools をインストールすると bin フォルダー ができます。
その bin フォルダの中に github_download.py スクリプトがあります。


 感想:
1. スクリプトを作り始めると ネットからのファイルのダウンロードが
_  意外と不便です。  ダウンロードする方法は いろいろありますが
_  スクリプトで ダウンロードする方法 が 既にありました。
_  Pythonista 3上で全てが出来ない為と 忘れる事もあり備忘録としました。
_  そして スクリプトが多くなるとフォルダーの整理が必要になってきます。
2. 課題:Pythonista 3 に組み込まれていない Module のインストール方法が
_     不明。例として matplotlib で使用してみたい Module があります。


 

Written by macsbug

8月 14, 2016 at 2:17 pm

カテゴリー: Apple, Pythonista

Display the graph on the iPad

leave a comment »

ESP8266 のセンサーを iPad でグラフ表示しました。           2016.08.08

リアルタイムにグラフ表示し変化をモニターできます。
日本語音声で「温度は27度です」とか話してくれたり 測定時の動作状況を
サウンドで教えてくれたり 離れていても耳で知ることができます。
音声やサウンドでお知らせしてくれるのは なかなか楽しいですよ。

iOSデバイス上で動作する統合開発環境の Pythonista 3 で製作しました。


機能:
1. ESP8266 BME280 温度、湿度、気圧センサーのデータを受信します。
2. 数値表示:スイッチをオンにすると日本語音声で数値を発音します。
_       温度、湿度、気圧 の必要なものを聞く事ができます。
3. グラフ :現在測定値は右端に表示し リアルタイムに左に移動します。
4. 測定間隔:左下のスイッチで「秒」「分」「時」「日」を選択します。
_       例:[分]は「3分間隔で測りますね」「今33分です」と発音。
5. 動作状態:「時」スイッチの上にあるトグルスイッチ。
_      オンにすると測定時(受信時)にサウンドが鳴ります。


準備:
1. ESP8266 と BME280 を I2C(4本) で接続。
_  ESP8266 : WeMos D1 mini with TELEC:SDA=D6(12), SCL=D7(13)
2. iPad 3 iOS 9.3.3 + Pythonista 3
3. iMac 27int OSX 10.8.5
4. パネルのデザインは画像を参照願います。


ESP2866 と iPad の信号の流れ:

1. iPad   :起動時に ESP8266 へ モード信号 (秒:”1″) を送信する。
2. ESP8266:それを受けて 6秒間隔モードに設定する。
3. ESP8266:iPadへ 6秒モードを送信する。
4. iPad   :ESP8266 からの返事(“1”)により スイッチ(秒)を点灯(緑)。
5. iPad   :EPP8266 からのデーターを受信し表示を繰り返します。

6. iPad   :測定間隔を変更:スイッチでモードをEP8266 へ送る。
7. ESP8266:測定間隔を切り替え モードの返事を iPad へ送る。
8. iPad   :ESP8266 からの返事により スイッチを緑に点灯します。

9. ESP8266:設定された時間間隔で 測定値を iPad へ送り続けます。


.
🍎 グラフを Ui 画面に表示する方法:
1. Pythonモジュール は import matplotlib.pyplot as plt を記述する。
2. 配列された x,y のデーターを用意する。例:x[1,2,3,4],y[3,2,5,7]
3. UI 編集で imageview (画像)の枠を用意する。名前は _panel とする。
4. v = ui.load_view(‘_panel’) で UI を読み込む。名前は v となる。
5. plt.plot(x,y) で Console へ抽画。( Coonsoleの表示は plt.show() )
6. plt.savefig(‘pic.png’) で Console の画像をファイルに保存する。
7. v[‘imageview1’].image = ui.Image.named(‘pic.png’)
_  で保存された画像を UI の imageview (v) に表示する。
メモ:Python の グラフ抽画は Console に表示(plt.show)されます。(5)
_  iPad は imageview に表示します。 (7)
.
🍎 日本語音声を出力する方法:
1. Pythonモジュール は import speech を記述する。
2. speech.say(‘こんにちわ’)
.
🍎 サウンド(sound) を使用する方法:あのマックのコインの音です。
1. Pythonモジュール は import sound を記述する。
2. sound.play_effect(‘Coin_1’)
.
🍎 スイッチ(Switch) の使用方法:

1. スイッチをオン( Action ) すると スイッチ操作音を出す。
_ def son(s):sound.play_effect(‘Click_1’)
_ UI の編集で Switch の「Action」項目に「son」と記述する。
_  Switch が 押されると def son に飛んで来て記述内容が動作します。
.


参考:
warning about too many open figures:pyplotで作ったデータをcloseする事。


感想:
1. Pythonista 3:7月末から始め 知識不足が多々ある中で作りました。
_  スクリプトは不十分な部分が多いと思いますのでご容赦を。
_  製作方法:ほとんどネットで調べて作りました。
_   図書館や本屋に行きましたが 使用できる場面は かなり少なかったです。

2. 問題点:
_  耐久テストが少ない為に 時間経過でクラッシュするかもしれません。
_  おそらく Matplotlib の pyplot で画像を多数作る時に問題があると予想
_  します。グラフ範囲の xlim,ylim は影響が大きく使用しない方が良い。
_  :
_  グラフを見ると言う事は iPad の電源を入れっぱなしにする事になる。
_  そうすると 充電しながらでも電源が持たないかもしれません。

3. 使用感:音声やトーンは楽しい。
_  グラフに興味はある物の 日常ではグラフを見つめ続ける事は少ない。
_  1行で簡単に音声が追加できますので楽しいですね。
_  音声によるアクションや説明は解り易く面白いものです。
_  ただし 音声は多様すると うるさく なるかもしれません。

4. Pythonista ( Python ) の命令:非常に多く大変ですが 凄さに驚くばかりです。
_  複数のグラフを重ねて表示とか目盛りを別々表示とかの機能が凄い!
_  今回のスクリプトよりも もっと良い記述の方法があるかと思います。
_  iPad の UI 機能を駆使する事がポイントですが 現在 情報が少ないです。
_  特に高速グラフィックの方法はなかなか難しそうです。


Pythonista 3:スクリプト

# ipad temp,humi,pres display : 2016.08.08 macsbug
#						rev 1 : 2016.08.11 macsbug
# phthonista 3, ios 9.3.3
import socket
import ui
import numpy as np
import matplotlib.pyplot as plt
import time
import Image
import sys
import datetime
import speech
import os
import sound
import math
from matplotlib.ticker import *

def udp_transceiver(s):					#
	tx.sendto(bytes(s, 'utf-8'), (HOST, PORT))
	
def udp_receiver(s):					#
	global d1, d2, temp, humi, pres, mode, sw
	d1 = str(rx.recv(32), 'utf-8')		# d1 = 't/1/0/0'
	d2 = d1.split('/')					# b/23.45/45.65/1008.235
	mode = d2[0]						# mode
	temp = d2[1]						# temp
	humi = d2[2]						# humi
	pres = d2[3]						# pres
	if mode == 't':sw = d2[1]			# time interval switch

def sw1(s): udp_transceiver('1')		# sw1
def sw2(s): udp_transceiver('2')		# sw2
def sw3(s): udp_transceiver('3')		# sw3
def sw4(s): udp_transceiver('4')		# sw4

def son(s): sound.play_effect('Click_1')# switch sound

def all_of_switch(s):					# button off
	v['button1'].background_color = of	# 1
	v['button2'].background_color = of	# 2
	v['button3'].background_color = of	# 3
	v['button4'].background_color = of	# 4
	
def bot(bot1, bot2, bot3, bot4):		#
	all_of_switch('')					#
	v[str(bot2)].background_color = on	#
	speech.say(str(bot4))				#
	speech.say('現在' + str(bot1) + str(bot3) + 'です')
	
def audio(a1, a2, a3): speech.say(str(a1) + str(a2) + str(a3))

def clocktime(s):						#
	global tm, clock					#
	d = datetime.datetime.today()		# clock time
	tm[4] = d.day; tm[3] = d.hour		# clock time
	tm[2] = d.minute; tm[1] = d.second	# clock time
	v['textfield5'].text = str(d)[0:19]	# datetime display
	clock = tm[int(sw)]					# clock time select
	
# start -------------------------------------------------------
# panel setup --------------------------#
v = ui.load_view('_BME_panel')			# panel install
v.background_color = '#d3dad7'			# panel color
on = '#b0ffb7';of = '#c5c5c5'			# sw on/off color
v['label7'].text = ''					# axis y
v['textfield5'].text = 'start'			# 
all_of_switch('')						# all sw off
v.present('sheet')						# panel in view

# udp setup
HOST, PORT = '192.168.100.47', 7000	# ESP8266 ip, port
rx = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
rx.bind(('', 9000))						# ipad tx port
tx = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# variavle setup -----------------------#
speech.say('こんにちわ')					# hello
temp, humi, pres, clock = 0, 0, 0, 0	#
tm = [0, 0, 0, 0, 0]					# clock
mode, d1 = 'a', 't/1/0/0'				# mode t/d, rx data
d2 = [0, 0, 0, 0]						# mode,temp(sw),humi,pres
sw = 1									# time interbal sw
x1 = 60									# x max
sound_onoff = 'off'						# sound on/off sel

# udp check ----------------------------#
udp_transceiver('1')					# ipad -> ESP8266
udp_receiver('');	c = 0				# return check
ret = mode + sw							# return check
while (ret) != 't1':					# return check
	v['textfield5'].text = str(ret)		# ret signal
	udp_transceiver('1')				# re tx
	udp_receiver(''); c = c + 1			# re rx
	vs = '接続できませんでした'			# fail
	if c > 100: speech.say(str(vs))		# fail count

x1 = 60									# sw 1
v['button1'].background_color = on		# sw 1 lamp on
sound.play_effect('Coin_1')				# rx ok

# receive data check -------------------#
udp_receiver('')						# first receive
while mode != 'd'						# return check
v['textfield5'].text = str(d1)			# rx data display
if mode == 'd':							# mode d check
	msg = str(mode) + ' : error'		# error message
	v['textfield5'].text = str(msg)		# error message
	udp_receiver('')					# re mode ck

v['textfield5'].text = str(d1)			# rx data
sound.play_effect('Coin_2')				# rx ok
ty = [temp for i in range(0, 60)]		# temp array setup
hy = [humi for i in range(0, 60)]		# humi array setup
py = [pres for i in range(0, 60)]		# pres array setup
# graph set up -------------------------#
pd = 5									# pres diff
ph = int(float(pres)) + pd				# pres hi
pl = int(float(pres)) - pd				# pres lo
xp = [i for i in range(0, 60)]			# x_line
fig = plt.figure()						# graphics setup
ax1 = fig.add_subplot(111)				# temp, hum
ax2 = ax1.twinx()						# pres axis
ax1.grid(True); ax2.grid(True)			# temp,humi,pres axis

# ==============================================================
# main routine
while True:
	udp_receiver('')					# receive
	clocktime('')						# clock time	
	# ------------------------------------------------------------
	# switch mode : time interval setup
	if mode == 't':sound.play_effect('Coin_1')
	if mode == 't' and sw == '1':
			bot(tm[1], 'button1', '秒', '6秒間隔で測ります')
			x1 = 60; xp = [i for i in range(0, x1)]
	if mode == 't' and sw == '2':
			bot(tm[2], 'button2', '分', '3分間隔で測りますね')
			x1 = 60; xp = [i for i in range(0, x1)]			
	if mode == 't' and sw == '3':
			bot(tm[3], 'button3', '時', '1時間間隔で測りますよ')
			x1 = 24; xp = [i for i in range(0, x1)]			
	if mode == 't' and sw == '4':
			bot(tm[4], 'button4', '日', '8時間毎に測りますね')
			x1 = 7; xp = [i for i in range(0, x1)]
	if mode == 't': plt.xlim(0, x1)		# x axis
		
	# ------------------------------------------------------------
	# data mode : digital display, sound on/off switch
	if mode == 'd':
		if sound_onoff == 'on': sound.play_effect('Ding_3')
		
		v['textfield1'].text = temp; ti = round(float(temp))
		v['textfield2'].text = humi; hi = round(float(humi))
		v['textfield3'].text = pres; pi = round(float(pres))
		v['textfield4'].text = str(clock)

		if v['switch1'].value: audio('温度は', ti, 'どです')
		if v['switch2'].value: audio('湿度は', hi, '%です')
		if v['switch3'].value: audio('気圧は', pi, 'ヘクトパスカルです')
		if v['switch4'].value: sound_onoff = 'on'
		else:sound_onoff = 'off'

		# -----------------------------------------------------------
		# graphics
		ty.pop(0); hy.pop(0); py.pop(0)				# left
		ty.append(temp); hy.append(humi); py.append(pres)# add data
		ph = int(float(pres)) + pd; pl = int(float(pres)) - pd
		
		ax1.plot(xp, ty, color='#2cff00', lw='1')	# temp graph
		ax1.plot(xp, hy, color='#b780ff', lw='1') 	# humi graph
		ax2.plot(xp, py, color='#2be3ff', lw='1')	# pres graph		
		ax2.plot(x1, ph, color='#ffffff', lw='0')	# pres hi
		ax2.plot(x1, pl, color='#ffffff', lw='0')	# pres lo
		
		plt.savefig('_a.png')		# save the graph on the consolen
		v['imageview1'].image = ui.Image.named('_a.png') # imageview
		plt.cla()					# clear axis
		plt.close()					# close a figure window
		fig = plt.figure()			#
		ax1 = fig.add_subplot(111)	#
		ax2 = ax1.twinx()			#
		ax1.grid(True)				#
		ax2.grid(True)				#
	
#------------------------------------------------------------

ESP8266 スケッチ:

// BME280 Temo,Humi,Pres Sensor: ESP8266 & iPad : 2016.08.01 macsbug
// ESP8266 : WeMos D1 mini with TELEC
// UDP communication
// ESP8266(ip:192.168.100.47,port:9000) transmit ---|
// ipad   (ip:192.168.100.22,port:9000) receive  <--|
//
// ipad   (ip:192.168.100.22,port:7000) transmit ---|
// ESP8266(ip:192.168.100.47,port:7000) receive  <--|

#include <ESP8266WiFi.h>                         //
#include <WiFiUDP.h>                             //
#include <Wire.h>                                //
#include <BME280_MOD_1022.h>                     //
#include <Ticker.h>                              //
extern "C" {                                     //
  #include "user_interface.h"                    //
}                                                //
static WiFiUDP UDP;                              //
const char ssid[]="xxxx";                        // wifi ssid
const char pass[]="xxxx";                        // wifi password
const char iPhoneIP[]   = "192.168.100.22";      // iPhone iP
const int  iPhoneTxPort = 7000;                  // UDP Tx port
const int  iPhoneRxPort = 9000;                  // UDP Rx port
char buff[32];                                   // rxceive buffer
Ticker ticker1;                                  // timer
long ta =  -6.5;                                 // temp adjust
long ha = +10.6;                                 // humidity adjust
long pa =  +3.5;                                 // press adjust

void setup(){                                    //
  Serial.begin(115200);                          //
  pinMode(D4, OUTPUT);digitalWrite( D4, LOW);    //
  pinMode(D3, OUTPUT);digitalWrite( D3, LOW);    //
  pinMode(D0, OUTPUT);digitalWrite( D0, LOW);    //
  //---------------------------------------------// BME280 setup
  Wire.begin(D6, D7);                            //
  BME280.readCompensationParams();               //
  BME280.writeOversamplingTemperature(os2x);     // temperature x2
  BME280.writeOversamplingHumidity(os2x);        // humidity x2
  BME280.writeOversamplingPressure(os2x);        // pressure x2
  //---------------------------------------------// WiFi setup
  WiFi.begin(ssid,pass);                         //
  while( WiFi.status() != WL_CONNECTED) {        //
    delay(500);  Serial.print(".");              //
  }                                              //
  Serial.println("WiFi Connect");                //
  UDP.begin(iPhoneTxPort);                       //
  ticker1.attach_ms(6000, report);               //
}                                                //

void loop(){                                     //         
  ESP.wdtDisable();                              //
  int rx = UDP.parsePacket();                    // packet size
  if (rx){                                       // recive
    int len = UDP.read(buff, rx);                // rx lengs
    if (len > 0){                                // rx action
      digitalWrite(D0,HIGH);                     //
      ticker1.detach();                          // timer off
      buff[len] = '\0';                	         // Termination char
      int c = buff[0];                           // header
      String r = "0";                            // No
      long t;                                    // time
      if ( c == '1' ){ r = "1"; t =     6*1000;} // 1:    3s: 60 sec
      if ( c == '2' ){ r = "2"; t =   180*1000;} // 2:  180s: 60 min
      if ( c == '3' ){ r = "3"; t =  4320*1000;} // 3: 4320s: 24 hr  1day
      if ( c == '4' ){ r = "4"; t = 30240*1000;} // 4:30240s:168 hr  7day
      //-----------------------------------------// UDP Transmitt
      String data = "t/" + r + "/0/0";           //
      UDP.beginPacket(iPhoneIP, iPhoneRxPort);   // UDP port
      UDP.print(data);                           // Tx  data
      UDP.endPacket();                           // end packet
      //-----------------------------------------// UDP Transmitt
      Serial.println(data);                      //
      digitalWrite(D0,LOW);                      //
      ticker1.attach_ms(t, report); c = '9';     // t timer set & mesure   
    }                                            //
  }                                              // 
}                                                // 

void report(){                                   //
  digitalWrite(D3,HIGH);                         //
  ESP.wdtDisable();                              //
  //---------------------------------------------// BME280 sensor
  BME280.writeMode(smForced); delay(50);         // chip goes back to sleep
  digitalWrite(D4,HIGH);                         //
  while (BME280.isMeasuring()){delay(250);}      //
  digitalWrite(D4,LOW);                          // BME280 check
  BME280.readMeasurements();                     // read out the data
  String t = String(BME280.getTemperature()+ta); // Temp
  String h = String(BME280.getHumidity()   +ha); // Humidity
  String p = String(BME280.getPressure()   +pa); // Pressure 
  String c = String(int(millis()/1000));         // count
  String data = "d/" + t + "/" + h + "/" + p;    // id+temp+html+pres
  //---------------------------------------------// UDP Transmitt
  UDP.beginPacket(iPhoneIP, iPhoneRxPort);       // UDP port
  UDP.print(data);                               // Tx  data
  UDP.endPacket();                               // end packet
  Serial.println(data);                          //
  digitalWrite(D3,LOW);                          //
  //---------------------------------------------// UDP Transmitt
}                                                //

Written by macsbug

8月 8, 2016 at 11:48 am

カテゴリー: ESP8266, Pythonista