前回の記事 でお知らせした通り、フリーの高機能関数電卓ソフト「RINPn(りんぷん)」に、Web上でいつでもどこでも使える「オンライン版」が登場しました。
このRINPn オンライン版は、従来のダウンロード版と同様、オープンソースのソフトウェアです。なので、商用・非商用問わず、誰でも自由にソースコードを改造・流用できます(ライセンスはMITライセンスです)。
という事で今回は、前回の記事の続編として、RINPn オンライン版の基本構造(アーキテクチャ)と、ソースコードをちょろっと軽めに解説しておきましょう!
RINPn オンライン版は本当にすぐに起動できるので、中身の説明に入る前に、まずは一旦起動して現物を見てみましょう。
それには以下の RINPn 公式サイトにアクセスし:
ページの以下の所にある「オンライン版を起動」ボタンを押すと起動します:
画面デザインは以下のような具合で、「INPUT」欄に計算式を入力して「=」ボタンを押すと、計算が実行されます:
どうでしょう? 無事動いたでしょうか?
ものすごく古いブラウザとかだと、動かなかったりレイアウトが崩れるかもしれません。 また、スマートフォンも機種・世代などによっては同様です。 今この場では、なるべく新しめのPCでお試しください。
それでは、RINPn オンライン版の内部の話に入っていきましょう。
以下のGitHubリポジトリ上でソースコードを読めるので、適時併せてご参照ください。本文中でも所々でリンクを張ります。
まずはじめに、RINPn オンライン版の基本構造はめちゃくちゃシンプルです。
ダウンロード版(デスクトップ版)の方の RINPn は結構大がかりなんですが、オンライン版の方は、前回記事でも述べた通り、機能がかなり削減されています。
ダウンロード版と同等の機能量が必要な場面では、普通にダウンロード版を使えばいいわけなので、オンライン版はむしろ逆に、「今すぐちょっとした計算をしたい」といった即席利用時の手軽さに的を絞っている感じです。
なので基本構造は、
の合計3枚のみです。なお、TypeScriptのコード2枚は、ビルドされて1枚のJavaScriptコード「rinpn-online-bundled.js」になります。
以上の基本構造を図にすると、以下のようなイメージですかね?
それでは、ソースコードの3枚(ビルドで生成されるJavaScriptコードを除く)を、それぞれを詳しく見ていきましょう。
まずは一番表側、画面用のHTMLファイルです:
わりかし何の変哲もないHTML+CSSのコードで、ボタンが大量に並んでいるだけです。
一応は表示機器の画面サイズに応じて、電卓のサイズも変化するようになっています。1枚のHTMLファイルだけでPCもスマホもカバーするためで、いわゆるレスポンシブデザインというやつですね。
具体的には、CSSのメディアクエリ( @media (...) {...} の所 )を使って body 領域のサイズを変えて、それにフィットするように、ボタンを載せたパネル類も伸縮するような構造になっています。
ただ、スマホって画面サイズのパターンが多種多様で、OSやブラウザやバージョンも多種多様なので、モノによっては普通に崩れたり使い辛いレイアウトになったりは(まだ)すると思います。フリーで即席仕立てなので、そのあたりは現状ではもう仕方ないと割り切っています。運用しながら熟成させます。
今度は逆に、最も深い層である「式の計算処理」です。これは「exevalator.ts」というTypeScriptコードのファイルが担っています:
この「exevalator.ts」は、RINPn同様にうちで作って公開している、フリーの式計算ライブラリ「Exevalator」のTypeScript実装版です。
うちでは言語処理系の類を色々と作っているのですが、その中でもExevalatorは、式の計算のみに焦点を絞ったコンパクトなライブラリです。 コンパクトなので多言語移植が可能で、現時点で Java / Rust / C++ / C# / VB.NET / TypeScript の6言語に対応しています。その TypeScript 版を今回使っているわけですね。
Exevalatorの使い方はかなり簡単です。ちょうどすぐ後で解説する、今回の rinpn-online.ts の処理が、Exevalator の使い方のいい例にもなると思います。
なお、今回の本筋からは外れるため割愛しますが、Exevalator もオープンソースで、その内部構造や処理フローの解説記事もあります。興味をお持ちの方は、下記記事をどうぞ:
ただ、上記記事の内容は若干マニアックです。軽めの内容ですが、ある程度は言語処理系の話とかに興味がないと、読むのはきつい記事かもしれません(いま振り返って読んでみると)。
さて、最後に中心役となる rinpn-online.ts です:
このコードが行っている主要な処理は、以下の3つです:
これだけです。中心役といっても、実質やっている事は「 画面と Exevalator との仲介」みたいなもので、地味ですね。
一応参考までに、計算実行時の処理フローだけ、詳しく追っておきましょう:
calculationButton.addEventListener("click", () => {
calculate();
});
function calculate() {
...
// Exevalator をインスタンス化
let exevalator: Exevalator = new Exevalator();
// 式の中で使う関数を登録: sin(x), cos(x), tan(x), etc.
exevalator.connectFunction("sin", new SinFunction());
exevalator.connectFunction("cos", new CosFunction());
...
// 式の中で使う変数を登録: PI
exevalator.declareVariable("PI");
exevalator.writeVariable("PI", Math.PI);
...
const result: number = exevalator.eval(expression);
const formattedResult = formatResult(result);
outputField.value = formattedResult;
このような具合です。
さてさて。
アーキテクチャ解説はこのあたりで完了ですが、せっかく内部構造が把握できた所で、実際にソースコードを入手してビルド・実行してみませんか?
git と Node.js さえ入っていればすぐできます。という事でやってみましょう!
これで「 rinpn-online-bundled.js 」が生成されるんですが、リポジトリ内にも元々含まれています。一旦消して、きちんと生成できる事を確認した方がいいかもしれません。
起動するには、index.html をブラウザで開きます(普通にダブルクリックなどで)。するとブラウザ上に電卓画面が表示され、上記の「 rinpn-online-bundled.js 」が読み込まれて動作します。
改造する場合は、JavaScriptファイル(拡張子 .js)ではなく、TypeScriptファイル(拡張子 .ts)の方を編集してください。 編集後、上記手順「3.」のビルドを再び行えば、電卓の動作が更新されます。
◇
今回の内容は以上です。
ぜひ気軽に改造・流用して、みなさんのオリジナル電卓を作ったりして遊んでみてくださいね!
RINPn に関する更新情報は、今後もこのコーナーにて随時お知らせしていきます。お楽しみに!