先に完成品の紹介
USBケーブルにイライラしたことはありませんか?
というのも市販の製品に同梱されているケーブルの中には、充電のみに対応しているものが結構多くあります。
データ通信に使いたい場面で、この充電のみに対応したケーブルを使っていると、当然通信できず、イライラすることとなります。
という事で、家にあるケーブルが充電のみに対応したものなのか、データ通信もできるのかを調べたくなります。
という事で作ったのがこちらです!↓
貧者のUSBケーブルチェッカーをセルフパワー化してみた。#3Dプリンター pic.twitter.com/bRHdGMAPp1
— ina_ani@2歳児のパパ (@ina_ani) 2022年4月30日
貧者のUSBケーブルチェッカーとは
USBケーブルチェッカーと言えばこの製品が非常に有名です。 (便宜上こちらは富者のUSBケーブルチェッカー、と呼んでいます)
この商品を買えば間違いはないのですが、自分の場合は、そこまで細かいスペックを知りたいわけではなく、単に「データ線が結線されていないUSBケーブルか否か」だけがわかれば良いという要件であることに気付きました。
となれば、単に指定したピンが両端のコネクタで結線しているかだけを見ればよいので、もっとシンプルな回路でチェックできそうです。
この観点でインターネットを探してみると・・ ズバリな商品がありました。
ということで、早速これを購入してみました。
今回はこの基板の電源付きケースを設計した話です。
「この基板」では味気が無いので、私はこれを「貧者のUSBケーブルチェッカー」と呼ぶことにします。
セルフパワー化
この基板は外からUSBケーブルで電源を得るように設計されています。
そのため、テストしたいケーブルの両端に加えて、外部電源用のケーブルを接続する必要があり、利用する際にケーブルだらけとなってしまい煩雑だと感じました。
そこで基板にCR2032を取り付け直接電源を供給できるようにしました。
CR2032は3Vなので、USB電源とは電圧が違いますが、チェック用のLEDを光らせることが出来ることを確認できたので、結果オーライという事でそのまま結線しています。
基板上にテスト用のパッドが露出していたので、そこに導線をはんだ付けしました。
今回CR2032ホルダーも3Dプリンタで作ってみました。と言っても「口」の形で導線を通す穴を2つ開けただけの簡単なものです。
ここで紹介する設計手法について
私も3Dプリンター向けのデータをどうやって作るかを、まだ模索している段階なのですが、今回のやり方を文書化することで、新たな発見があるかも・・と思い記事にしてることにしました。
さらに良い方法があるよ、という方は是非教えてください。
利用するツール
今回は以下のソフトウェアを使って設計を行います
- LibreCAD
- LibreCAD - Free Open Source 2D CAD
- オープンソースの2次元CADツール
- コンパスや定規などで作図する感じで造形できます
- OpenSCAD
- OpenSCAD - The Programmers Solid 3D CAD Modeller
- オープンソースの3次元CADツール
- プログラミングで立体を造形できます
- BOSL2
- https://github.com/revarbat/BOSL2
- OpenSCADのライブラリ
- 相対的に立体物を並べることができます
設計手法の紹介
ではここから具体的な設計方法について紹介します。
LibreCADで基板の部品を書き写す
基板上のでっぱりのあるコネクタのサイズなどを測定し、LibreCADで作図をします。やはりこういう作図はマウスが利用できるGUIのツールが便利です。 (ここは行き当たりばったりでやってたのでレイヤー名とか雑ですね・・)
作図補助レイヤーで垂直・水平のガイドを作図し、でっぱり部分をレイヤーで作図します。 (図で緑色と黄色の線が作図補助のための直線です。)
基板外形、でっぱりの高さが異なる部分は別のレイヤーにします。
OpenSCADではDXFファイルのレイヤーを指定してインポートできるので、便利です。
OpenSCADで作図する
今回はBOSL2というライブラリを使います。
このライブラリは、立体物にアンカーを設定して、そこに他の図形をアタッチする形で立体物を作成する機能を提供してくれます。
DXFファイルからレイヤーを指定して読み込む場合には以下のように書きます。
import (file = "board.dxf", layer = "rect-board");
論理演算で穴をあけるための造形物は以下のように書きます。(モジュール化もしています)
module hole() linear_extrude(height=3) import (file = "board.dxf", layer = "hole"); module hole2() linear_extrude(height=7) import (file = "board.dxf", layer = "hole2");
ケースの上部分はこのように書きます。
baseW = 57; // 基板外形 幅 baseL = 46; // 基板外形 奥行き boardThickness = 1.6; // 基板厚 baseThickness = 2; // 底厚 baseSideThickness = 5; // 横壁厚 topH = 8; //ケース高さ render() // ちらつき防止 diff("cut") // cutというtagの図形を切り抜く yrot(180) // y軸中心に180度回転させる cube([baseW, baseL, topH], anchor=[0,0,1]){ // 底面にアンカーを設定したケース外形の直方体を作成 force_tags("cut"){ // 切り抜く部分をグループ化 position([-1, -1, -1]){ // ケース外形の左-手前-下を原点とする hole(); // 基板上のでっぱりを引き算する(高さ別に4つのデータが存在) hole2(); hole3(); hole4(); union(){ // バッテリー収納部を作図する(ここはLibreCADで作っていない) translate([44,22,0]) // 位置合わせ linear_extrude(height=topH - 1){ // バッテリー部分の壁厚は1mm circle(r = 10+1); // CR2032の半径=10mm+マージン1mmの円 rotate([0,0,-90]) square([22+4, 14], center = true); // バッテリスナップ収納の為の矩形 } translate([33,30,0]) // 位置合わせ linear_extrude(height=2) // 配線用のスペースを作図する(ここはLibreCADで作っていない) square([10,10]); } } // スナップフィットジョイントの作図 xflip_copy() // X軸に対称にコピー position([-1, 0, -1]) // ケース外形の左-中央-下を原点とする yflip_copy() // Y軸に対称にコピー up(baseH - baseThickness - boardThickness) // ジョイントの高さ位置合わせ back(10) // ジョイントの前後位置合わせ xrot(90) cyl(r=1, l=10, anchor=[0, 1, 0]); // ジョイントをシリンダで作成、アンカーは下面に設定 } }
ケース下部分はこのように書きます
baseH = 8; render() // ちらつき防止 translate([0,50,0]) // 位置合わせ diff("cut") //cutというtagの図形を切り抜く cube([baseW+0.2, baseL, baseThickness + boardThickness], anchor=[0,0,-1]){ // 底面にアンカーを設定したケース外形(スナップ用の左右はみ出し部分を除く)の直方体を作成 position([-1, -1, 1]) // ケース外形の左-手前-上を原点とする force_tags("cut") // 切り抜く部分をグループ化 zflip() linear_extrude(height=boardThickness) // 基板外形を作図(linear_extrudeの向きが期待と逆なのでzflipしている board(); //DXFから基板外形を読み込む // スナップフィットジョイントと左右はみ出し部分の作図 xflip_copy() // X軸に対称にコピー position([-1, -1, -1]) // ケース外形の左-手前-下を原点とする // 左右はみ出し部分は一部角丸の直方体として作図 cuboid([baseSideThickness, baseL, baseH], anchor=[1,-1,-1], rounding=2, edges=["Z"], except_edges=RIGHT) yflip_copy() // Y軸に対称にコピー position([1, 0, 1]) // 右-中央-奥を原点にする back(10) // ジョイントの前後位置合わせ xrot(90) cyl(r=1, l=10-1, anchor=[0, 1, 0]); // ジョイントをシリンダで作成、アンカーは下面に設定(1mm短くしてうまくハマるようにしている) }
スナップフィットジョイントと書きましたが、市販品のような矢印状のものでは無く、単にかまぼこのような形の凹凸をはめ込むだけのジョイントです。
しかしこれでも十分に固定でき、かなり力を書けないと外れないケースを作ることが出来ました。
(説明をコメントになるべく書いてみましたが、なかなかわかりづらいですね。)
BOSL2所感
とにかくアタッチができるのが有用と感じました。
直方体を定義すると、その頂点または辺の中点を簡単にアタッチ原点と設定することが出来ます。
これにより相対的な立体図形の配置が出来るようになり、OpenSCAD単体で作図していると変数だらけになってしまう問題を解消できます。 (アタッチが出来ないので辺の長さをすべて変数に逃がす必要があった)
またxflip, yflip, zflipやup, down, left, rightなど軸を1つに限定した操作も可読性が良くなり良いものだと感じました。
cuboidには角丸のオプションがあり、フィレットが苦手なOpenSCADの弱点を少しは緩和させてくれます。 (それでもやはりフィレットは苦手ですが・・)
linear_extrudeの引き延ばした先にアタッチできないのが若干惜しい気持ちになりました。
まとめ
今回初めてLibreCADとOpenSCAD、そしてBOSL2を使った作図をしてみました。
LibreCADを使うとマウスを使って簡単に直感的な作図が出来ました。
立体的な造形はマウスよりコーディングの方が保守性が高いのでOpenSCADが有用だと感じました。
そしてBOSL2というOpenSCADのライブラリを使うことで、立体物の造形を比較的直観的に実現できました。
今回は試験的にツールを組み合わせただけなので、もっと良い方法があるかもしれません。
これより良い方法を思いついた方は是非https://twitter.com/ina_ani に教えてください。