- 投稿日:2019-05-30T23:57:38+09:00
アラフォー、Notソフトウェアエンジニアが、ポートフォリオを作った話
はじめに
タイトルは半分釣りです。
アラフォーと言っても35歳。昔は専門学校で情報工学の勉強をしておりました。
Qiita上にも何本か記事を書いています。その為、全くの未経験、という訳では無いと思います。筆者のスペック
ソフトウェア開発の経験は全くありません。
(PerlやVBAでちょっとしたプログラムを作った事はありますが、それでソフトウェアエンジニアを名乗るのも、どうかと思います。)半導体の論理設計の経験はあります。Verilog、C言語、アセンブラはやっていました。
でも、それをやっていたのは10年以上前。
それ以降は、派遣で職を転々としたり、引きこもりになったり、と言った所です。現在はプロフィールの通りです。
成果物
Github Pagesを使って公開してみました。
https://frameair.github.io/myprofile/
IE11では動きません。
IE11では、NodeListをforEach出来ないのが理由らしいです。これを書いている時に初めて知りました。ただ、chromeとfirefoxで動けば良いや、という考えなので、特に気にしない事にします。
github(ソースコード)はこちら。
https://github.com/frameair/myprofile使用言語
html5, scss, typescript
ただし、scssとtypescriptについては、特に使わなくても良かったのかなぁ、と思っています。
特にtypescriptは、殆ど使っていないようなものです。
javascriptでそのまま書いても変わらなかったと思います。技術的な解説
背景で雪に見える様なものを、下から上に飛ばしています。
このロジックについて、ソースコードを示します。const background = document.querySelector('#background'); const randNum = (center, deltaMax, deltaMin) : number => { const min = center + deltaMin; const max = center + deltaMax; const rand = Math.random(); const result = rand * ( max - min ) + min; return result; } // snowを用意する。 for (let i = 0; i <= 20; i++) { const snow = document.createElement('div'); snow.classList.add('snow'); snow.dataset.no = i.toString(); const animateDuration = 5000; const startLeft = randNum(50, 40, -40); const endLeft = randNum(startLeft, 30, -30); const endTop = randNum(0, 20, 0); const delayTime = randNum(0, 500, -500); const size = randNum(20, 10, -5); snow.style.height = `${size}px`; snow.style.width = `${size}px`; const animate_state1 = { opacity: [1, 0], top: ['100vh', `${endTop}vh`], left: [`${startLeft}vw`, `${endLeft}vw`], }; const animate_state2 = { duration: animateDuration, easing: 'linear', delay: delayTime } setTimeout((e) => { snow.animate(animate_state1, animate_state2); background.appendChild(snow); setInterval(() => { const startLeft = randNum(50, 40, -40); const endLeft = randNum(startLeft, 30, -30); const endTop = randNum(0, 20, 0); const delayTime = randNum(0, 500, -500); const size = randNum(20, 10, -5); snow.style.height = `${size}px`; snow.style.width = `${size}px`; animate_state1.top = ['100vh', `${endTop}vh`]; animate_state1.left = [`${startLeft}vw`, `${endLeft}vw`]; animate_state2.delay = delayTime; snow.animate(animate_state1, animate_state2); }, animateDuration) }, i * 500) }div要素を20個用意します。
div要素は予め、cssで◯の形にして、filter: blurでボカシをかけてあります。animationは、animateメソッドを使って実現しています。
最初は、cssのkeyframesを使って実現しようと思ったのですが、ランダムな場所に要素を移動させる方法が解らなかったので、cssを使うことは諦めました。
代替方法を探していた時に見つけたのが、animateメソッドです。使い方は割愛します。下記のMDNを見て下さい。
https://developer.mozilla.org/ja/docs/Web/API/Element/animateただし、これはEdgeをサポートしていません。
そのうちEdgeもChroniumベースになるのだからサポートしなくて良いとは思いますが……Edgeに対応させる為、ライブラリとして、web-animations.jsを使用しています。
github: https://github.com/web-animations/web-animations-jsこれを使う事で、Edgeに対応させる事が出来ました。
後、Safari(MacOS, iOS)では未検証です。
MacもiPhoneもiPadも持っていないので、検証の予定もありません。Androidでは検証してみました(Huawei P20 lite)
ただし、animationが重いです。冷静に考えたら当たり前ですよね……。終わりに
ソフトウェアの勉強をしていましたが、これまで成果物と言える様なものは、何一つ作っていませんでした。
そういう意味では、これが初めての作品なのかも知れません。これまで、プログラミングを勉強する事はあっても、成果物を作ると言う事はしてきませんでした。
しかし、この年齢になって、ようやくやる気もが少しだけ出てきた様に思います。
もうアラフォーという年齢で、プログラマーになるのは無理でしょうけど、趣味の1つとして、プログラミングと関わって行きたいと思っています。今回は技術的な部分には殆ど触れませんでした。
この次に記事を書く際には、技術的な事を書きたいと思っています。
- 投稿日:2019-05-30T23:57:38+09:00
ポートフォリオを作った話
筆者のスペック
ソフトウェア開発の経験は全くありません。
(PerlやVBAでちょっとしたプログラムを作った事はありますが、それでソフトウェアエンジニアを名乗るのも、どうかと思います。)半導体の論理設計の経験はあります。Verilog、C言語、アセンブラはやっていました。
でも、それをやっていたのは10年以上前。
それ以降は、派遣で職を転々としたり、引きこもりになったり、と言った所です。現在はプロフィールの通りです。
成果物
Github Pagesを使って公開してみました。
https://frameair.github.io/myprofile/
IE11では動きません。
IE11では、NodeListをforEach出来ないのが理由らしいです。これを書いている時に初めて知りました。ただ、chromeとfirefoxで動けば良いや、という考えなので、特に気にしない事にします。
github(ソースコード)はこちら。
https://github.com/frameair/myprofile使用言語
html5, scss, typescript
ただし、scssとtypescriptについては、特に使わなくても良かったのかなぁ、と思っています。
特にtypescriptは、殆ど使っていないようなものです。
javascriptでそのまま書いても変わらなかったと思います。技術的な解説
背景で雪に見える様なものを、下から上に飛ばしています。
このロジックについて、ソースコードを示します。const background = document.querySelector('#background'); const randNum = (center, deltaMax, deltaMin) : number => { const min = center + deltaMin; const max = center + deltaMax; const rand = Math.random(); const result = rand * ( max - min ) + min; return result; } // snowを用意する。 for (let i = 0; i <= 20; i++) { const snow = document.createElement('div'); snow.classList.add('snow'); snow.dataset.no = i.toString(); const animateDuration = 5000; const startLeft = randNum(50, 40, -40); const endLeft = randNum(startLeft, 30, -30); const endTop = randNum(0, 20, 0); const delayTime = randNum(0, 500, -500); const size = randNum(20, 10, -5); snow.style.height = `${size}px`; snow.style.width = `${size}px`; const animate_state1 = { opacity: [1, 0], top: ['100vh', `${endTop}vh`], left: [`${startLeft}vw`, `${endLeft}vw`], }; const animate_state2 = { duration: animateDuration, easing: 'linear', delay: delayTime } setTimeout((e) => { snow.animate(animate_state1, animate_state2); background.appendChild(snow); setInterval(() => { const startLeft = randNum(50, 40, -40); const endLeft = randNum(startLeft, 30, -30); const endTop = randNum(0, 20, 0); const delayTime = randNum(0, 500, -500); const size = randNum(20, 10, -5); snow.style.height = `${size}px`; snow.style.width = `${size}px`; animate_state1.top = ['100vh', `${endTop}vh`]; animate_state1.left = [`${startLeft}vw`, `${endLeft}vw`]; animate_state2.delay = delayTime; snow.animate(animate_state1, animate_state2); }, animateDuration) }, i * 500) }div要素を20個用意します。
div要素は予め、cssで◯の形にして、filter: blurでボカシをかけてあります。animationは、animateメソッドを使って実現しています。
最初は、cssのkeyframesを使って実現しようと思ったのですが、ランダムな場所に要素を移動させる方法が解らなかったので、cssを使うことは諦めました。
代替方法を探していた時に見つけたのが、animateメソッドです。使い方は割愛します。下記のMDNを見て下さい。
https://developer.mozilla.org/ja/docs/Web/API/Element/animateただし、これはEdgeをサポートしていません。
そのうちEdgeもChroniumベースになるのだからサポートしなくて良いとは思いますが……Edgeに対応させる為、ライブラリとして、web-animations.jsを使用しています。
github: https://github.com/web-animations/web-animations-jsこれを使う事で、Edgeに対応させる事が出来ました。
後、Safari(MacOS, iOS)では未検証です。
MacもiPhoneもiPadも持っていないので、検証の予定もありません。Androidでは検証してみました(Huawei P20 lite)
ただし、animationが重いです。冷静に考えたら当たり前ですよね……。終わりに
ソフトウェアの勉強をしていましたが、これまで成果物と言える様なものは、何一つ作っていませんでした。
そういう意味では、これが初めての作品なのかも知れません。これまで、プログラミングを勉強する事はあっても、成果物を作ると言う事はしてきませんでした。
しかし、この年齢になって、ようやくやる気もが少しだけ出てきた様に思います。
もうアラフォーという年齢で、プログラマーになるのは無理でしょうけど、趣味の1つとして、プログラミングと関わって行きたいと思っています。今回は技術的な部分には殆ど触れませんでした。
この次に記事を書く際には、技術的な事を書きたいと思っています。
- 投稿日:2019-05-30T17:58:33+09:00
HTML3日目
HTMLステップアップ
table
<table border="1"> <tr> --- tabel row <th>姓</th> --- table header <th>名</th> </tr> <tr> <td>田中</td> --- table data <td>花子</td> </tr> <tr> <td>山田</td> --- table data <td>太郎</td> </tr> </table>thead, tbody, tfoot
単なる意味付け。あってもなくても、何も変わらない。
<table border="1"> <thead> <tr> <th>ヘッダー1</th> <th>ヘッダー2</th> </tr> </tread> <tbody> <tr> <td>データ1</td> <td>データ2</td> </tr> </tbody> <tfoot> <tr> <td>フッター1</td> <td>フッター2</td> </tr> </tfoot> </table>フォーム
ユーザーがwebページからサーバーにデータを送信するためのもの
<form action="#", method="post"> <form>
- action → データをどこに送信するか。送信された情報を処理するプログラムのURL
- method → フォームを送信する際にブラウザーが使用するHTTPリクエストメソッド(get or post)
- head
- get
- post
- put
- delete
- connect
- options
- trace
- patch
少し詳しく
- get → サーバーからデータを取得したいときに使う
- post → サーバーへデータを送信したいと気に使う
input要素
- データを入力するための要素
- type属性を変えることで、様々な入力フォームになる。
<input type="text"> type="ここにタイプ属性を入力"実際のやつ
<form action="#" method="post"> <input type="text" name="username" placeholder="ユーザーネーム"> <input type="password" name="password" placeholder="パスワード"> <input type="submit" value="ログイン"> </form>
- name: サーバー側がwebページから送られてきたデータを識別するためにつける
- placeholder: フォーム内にデフォルトで表示される文字列
- value: submitボタンに表示される名称
いろいろ纏めてご紹介
セレクトフォーム
<select name="prefecture"> valueがサーバー側に送られるっぽい <option value="" selected>選択してください</option> <option value="hokkaido">北海道</option> <option value="tohoku">東北</option> <option value="kanto">関東</option> <option value="chubu">中部</option> <option value="kinki">近畿</option> <option value="chugoku">中国</option> <option value="sikoku">四国</option> <option value="kyusyu">九州</option> </select>ラジオボタン (nameで一括りのラジオボタン群として判断)
<th>性別</th> <td> <input type="radio" name="gender" value="male" checked>男性 <input type="radio" name="gender" value="female">女性可変長のテキストフィールド
<th>お問い合わせ内容</th> <td> <textarea name="contents"></textarea> </td> </td>チェックボタン
<th>プライバシーポリシーに同意する</th> <td> <input type="checkbox" name="pravacy" value="1">同意する </td>
- 投稿日:2019-05-30T14:44:00+09:00
HTLM二日目
今日はCSSに手を出しているはずだったのだが。。。
リスト
<ul> <li>りんご</li> ・りんご <li>みかん</li> ・みかん <li>ぶどう</li> ・ぶどう </ul> <ol> <li>りんご</li> 1. りんご <li>みかん</li> 2. みかん <li>ぶどう</li> 3. ぶどう </ol>divとspan
- 任意の範囲をグループ化
- CSSでスタイルを当てるときに使う
- タグ自身は意味を持たない
違い
CSSのプロパティ値の違い
- div: display: block
- spa: display: inline
幅と高さを指定できる?
- div: できる
- span: できない
前後に改行が入るか
- div: 入る
- span: 入らない
属性(attribute)
- タグになにかしらの設定をできる。
<tag name="value"></tag>img
- 相対パス
<img src="dog.jpg">同じディレクトリ- 絶対パス
<img src="http://~~/dog.jpg">リンク
aタグ
- リンクを貼るときに使う
<a href="https:/???">Google</a>
- 別サーバー
<a href="https://google.com" target="blank">Google</a>
別タブで開く
- 投稿日:2019-05-30T13:58:49+09:00
Javascriptで電卓を作ろう 第4回 小数点を正しく入力しよう
目次
- HTMLのマークアップ
- CSS
- Javascriptで四則演算
- 6)打った数字をコンソールに出力させよう。
- 7)打った数字と記号を変数に格納しよう。
- 8)計算結果を出力させよう。
- 8-1)「=」を押した時の処理
- 8-2) 計算結果と計算途中を、計算結果の画面に表示させよう。
- 最初に「+ ÷ - × =」が押せないようにする。
- 二回連続で計算できるようにしたい。
- Cボタン(リセットボタン)を押した時の処理
- BS(バックスペース)ボタンを使えるようにする
- 12.12.や12..12のように小数点を間違って入力できてしまう。
- 電卓と同じように「.4」と入力したら0.4としたい。
12.12.や12..12のような正しくない小数は入力できないようにする。
対処法
整数入力中、小数入力中を変数(mode)で定義します。
modeという変数を用意して、integer_mode、decimal_modeを代入して状態を管理します。
a)整数入力中(integer_mode)
- 「.」小数点を押すことができる。
b)小数入力中(decimal_mode)
- 「+ ÷ - ×」が押されるまでは、「.」小数点を押すことができない。(12.12.4や12..12とならないようにしたい)
これらを踏まえて、このこのように書いていきます。
小数点を押したら、
- 小数入力中mode==='demimal_mode'とする。
- このmodeでは、小数点は押せないようにする。
「+ ÷ - ×」、「=」「C」を押したら、
- 整数入力中mode==='integer_mode'に戻す。
'use strict' { const num_bth = document.querySelectorAll('.num_bth'); let output_sub = document.getElementById('output_sub');//計算結果を表示する場所 const output_total = document.getElementById('output_total');//計算過程を表示する場所 let total = 0;//計算式を表す変数 let state = 'start';//最初の状態を定義 // 1)計算する前の最初の状態(start) // 2)数字を入力している最中(calculation) // 3)「+ ÷ - × =」を押した直後(calBtn) // 4)「=」を教えて計算が終わった直後(finish) // 変数stateに、star,calculation, calBtn, finishを代入して状態を管理します。 let mode = 'integer_mode'; //最初は整数入力モード // 変数modeに、整数入力中integer_mode、小数入力中decimal_modeを定義します。 // 1-9の数字ボタンを押した時 const one_nine = document.querySelectorAll('.one_nine'); one_nine.forEach(index => { index.addEventListener('click', () => { if(state === 'start') { //最初:totalに打った数字を代入する total = index.dataset.indexId; }else if(state === 'finish') { //計算後:リセット処理後に、totalに打った数字を代入する reset(); total = index.dataset.indexId; }else if(state === 'calculation'){ //計算中totalに打った数字を追加して、totalに代入する。 total += index.dataset.indexId; } output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 }) //click })//forEach // 0の数字ボタンを押した時 const zero = document.getElementById('zero'); zero.addEventListener('click', () => { console.log(zero.dataset.indexId) if(total === 0) { total = zero.dataset.indexId; }else{ total += zero.dataset.indexId; } output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 }) //click // 「.」小数点ボタンを押した時 const point = document.getElementById('point'); point.addEventListener('click', () => { console.log(point.dataset.indexId) if(mode === 'decimal_mode'){ return; } if(total === 0) { total = point.dataset.indexId; }else{ total += point.dataset.indexId; } output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 mode = 'decimal_mode'; //小数入力モードに変更 }) //click //「+ ÷ - ×」ボタンを押した時 const cal = document.querySelectorAll('.cal'); cal.forEach(index => { index.addEventListener('click', () => { if(state === 'start') { return;//最初記号は押せない }else if(state === 'calculation'){ total += index.dataset.indexId;//計算中はtotalに打った記号を追加し、totalに代入する。 }else if(state === 'finish'){ //計算後は前の計算結果をtotal に代入して計算しなおす。 total = output_total.textContent; total += index.dataset.indexId; output_total.textContent = 0 } console.log(index.dataset.indexId) output_sub.textContent = total; state = 'calBtn'//演算記号を入力している状態する。 mode ='integer_mode'//整数モードに戻す }) //click })//forEach //イコールを押した時 const equal_btn = document.getElementById('equal_btn'); equal_btn.addEventListener('click',() =>{ console.log(eval(total)); output_total.textContent = eval(total); state = 'finish'//計算が終わった状態にする。 mode ='integer_mode'//整数モードに戻す }); //Cボタン(リセットボタン)を押した時の処理 const clear = document.getElementById('clear') clear.addEventListener('click', () => { reset(); }) //リセットを行う関数 function reset() { total = 0; output_sub.textContent = 0; output_total.textContent = 0; mode ='integer_mode'//整数モードに戻す } //BSボタン(バックスペース)を押した時の処理 const bs = document.getElementById('bs') bs.addEventListener('click', () => { console.log('BS') if(state ==="finish") { return;//計算後は、bsを押せない。 }else{ // 一文字目から、最後から二文字目までをtotalに代入(最後の一文字を除きtotalに代入する) total = output_sub.textContent.slice(0, -1); output_sub.textContent = total; } }) }電卓と同じように「.4」と入力したら0.4としたい。
【条件】
①
- 最初state==='start
- 計算終了後state==='finish'
の時に小数点が押されたらtotal=0とした後に
total = 0 + .とする。②
- 演算記号入力直後state==='calBtn'
の時に小終点が押されたら
total += 0とした後に
total = total + .とする。こうすることで「.」の前に0を挿入できる。
// 「.」小数点ボタンを押した時 const point = document.getElementById('point'); point.addEventListener('click', () => { console.log(point.dataset.indexId) if(mode === 'decimal_mode'){ return; //小数点入力モードではもう一度小数点を押せない } //「.4」と入力したら0.4としたい。(1)+(2)で0.4となる if(state==='start'||state==='finish') { total = 0;//(1)最初と計算終了直後なら、0を入力 }else if(state==='calBtn'){ //これを入れないと、0.4+0.4と打つと0.4+00.4となる。 if(output_sub.textContent.slice(-1)!=='0'){ total += 0;//(1')演算記号入力直後なら、今までの計算結果に0を入力 } } total += point.dataset.indexId;//(2)「.」を入力 output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 mode = 'decimal_mode'; //小数入力モードに変更 }) //click残りの課題
- 最初に0を連続で押せてしまう。
- 記号ボタン(+×÷-)を連続で押せてしまい、計算ができない。(連続で押した場合は、最後に押した記号ボタンが採用されるようにしたい。 )
- 12.12.や12..12のように小数点を正しくなく入力できてしまう。- 割り算等で小数点以下が異様に長い。
- 電卓と同じように「.4」と入力したら0.4としたい。- BSで文字を消した時、小数、整数モード、記号入力モードが切り替わらない。
現時点のコード
HTML
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>電卓</title> <link rel="stylesheet" href="style.css"> </head> <body> <div class = "container"> <!-- 計算結果を出力する場所--> <div id = "output_total" class="output ">0</div> <!-- 計算過程を出力する --> <div id = "output_sub" class="output active">0</div> <!-- ボタンを配置する場所--> <div class = 'input'> <section class = 'row'> <div id = "clear">C</div> <div class = "num_bth"></div> <div class = "num_bth" id="bs">BS</div> <div class = "num_bth cal" data-index-id= '/'>÷</div> </section> <section class = 'row'> <div class = "num_bth one_nine " data-index-id = 9 >9</div> <div class = "num_bth one_nine " data-index-id = 8 >8</div> <div class = "num_bth one_nine " data-index-id = 7 >7</div> <div class = "num_bth cal" data-index-id = '*'>×</div> </section> <section class = 'row'> <div class = "num_bth one_nine " data-index-id = 6 >6</div> <div class = "num_bth one_nine " data-index-id = 5 >5</div> <div class = "num_bth one_nine " data-index-id = 4 >4</div> <div class = "num_bth cal" data-index-id = '-'>-</div> </section> <section class = 'row'> <div class = "num_bth one_nine " data-index-id = 3 >3</div> <div class = "num_bth one_nine" data-index-id = 2 >2</div> <div class = "num_bth one_nine" data-index-id = 1 >1</div> <div class = "num_bth cal" data-index-id = '+'>+</div> </section> <section class = 'row'> <div class = "num_bth" data-index-id = 00 >00</div> <div class = "num_bth" id="zero" data-index-id = 0 >0</div> <div class = "num_bth" id="point" data-index-id = . >.</div> <div id = 'equal_btn'>=</div> </section> </div> </div> <script src="script.js"></script> </body> </html>CSS
.container { width: 200px; margin: 50px auto; border: 2px solid black; } .output { width: 200px; height: 50px; line-height: 50px; text-align: right; padding: 5px; margin-bottom: 5px; border:2px solid black; box-sizing: border-box; } .input { width:200px; border: 2px solid black; } .row { display: flex; justify-content: space-between; border: 2px solid red; width: 200px; } /*rowの範囲がわかりやすいように赤の枠を作っています。*/ .num_bth, #clear, #equal_btn{ width: 60px; height: 30px; text-align: center; line-height: 30px; border-radius: 30%; background: lightgray; cursor: pointer; margin: 5px; }Javascript
'use strict' { const num_bth = document.querySelectorAll('.num_bth'); let output_sub = document.getElementById('output_sub');//計算結果を表示する場所 const output_total = document.getElementById('output_total');//計算過程を表示する場所 let total = 0;//計算式を表す変数 let state = 'start';//最初の状態を定義 // 1)計算する前の最初の状態(start) // 2)数字を入力している最中(calculation) // 3)「+ ÷ - × =」を押した直後(calBtn) // 4)「=」を教えて計算が終わった直後(finish) // 変数stateに、star,calculation, calBtn, finishを代入して状態を管理します。 let mode = 'integer_mode'; //最初は整数入力モード // 変数modeに、整数入力中integer_mode、小数入力中decimal_modeを定義します。 // 1-9の数字ボタンを押した時 const one_nine = document.querySelectorAll('.one_nine'); one_nine.forEach(index => { index.addEventListener('click', () => { if(state === 'start') { //最初totalに打った数字を代入する total = index.dataset.indexId; }else if(state === 'finish') { //計算後は、リセット処理後に、totalに打った数字を代入する reset(); total = index.dataset.indexId; }else if(state === 'calculation'){ //計算中totalに打った数字を追加して、totalに代入する。 total += index.dataset.indexId; } output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 }) //click })//forEach // 0の数字ボタンを押した時 const zero = document.getElementById('zero'); zero.addEventListener('click', () => { console.log(zero.dataset.indexId) if(total === 0) { total = zero.dataset.indexId; }else{ total += zero.dataset.indexId; } output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 }) //click // 「.」小数点ボタンを押した時 const point = document.getElementById('point'); point.addEventListener('click', () => { console.log(point.dataset.indexId) if(mode === 'decimal_mode'){ return; //小数点入力モードではもう一度小数点を押せない } //「.4」と入力したら0.4としたい。(1)+(2)で0.4となる if(state==='start'||state==='finish') { total = 0;//(1)最初と計算終了直後なら、0を入力 }else if(state==='calBtn'){ //これを入れないと、0.4+0.4と打つと0.4+00.4となる。 if(output_sub.textContent.slice(-1)!=='0'){ total += 0;//(1')演算記号入力直後なら、今までの計算結果に0を入力 } } total += point.dataset.indexId;//(2)「.」を入力 output_sub.textContent = total; state = 'calculation'//数字を入力している状態にする。 mode = 'decimal_mode'; //小数入力モードに変更 }) //click //「+ ÷ - ×」ボタンを押した時 const cal = document.querySelectorAll('.cal'); cal.forEach(index => { index.addEventListener('click', () => { if(state === 'start') { return;//最初記号は押せない }else if(state === 'calculation'){ total += index.dataset.indexId;//計算中はtotalに打った記号を追加し、totalに代入する。 }else if(state === 'finish'){ //計算後は前の計算結果をtotal に代入して計算しなおす。 total = output_total.textContent; total += index.dataset.indexId; output_total.textContent = 0 } console.log(index.dataset.indexId) output_sub.textContent = total; state = 'calBtn'//演算記号を入力している状態する。 mode ='integer_mode'//整数モードに戻す }) //click })//forEach //イコールを押した時 const equal_btn = document.getElementById('equal_btn'); equal_btn.addEventListener('click',() =>{ console.log(eval(total)); output_total.textContent = eval(total); state = 'finish'//計算が終わった状態にする。 mode ='integer_mode'//整数モードに戻す }); //Cボタン(リセットボタン)を押した時の処理 const clear = document.getElementById('clear') clear.addEventListener('click', () => { reset(); }) //リセットを行う関数 function reset() { total = 0; output_sub.textContent = 0; output_total.textContent = 0; mode ='integer_mode'//整数モードに戻す } //BSボタン(バックスペース)を押した時の処理 const bs = document.getElementById('bs') bs.addEventListener('click', () => { console.log('BS') if(state ==="finish") { return;//計算後は、bsを押せない。 }else{ // 一文字目から、最後から二文字目までをtotalに代入(最後の一文字を除きtotalに代入する) total = output_sub.textContent.slice(0, -1); output_sub.textContent = total; } }) }
- 投稿日:2019-05-30T12:36:24+09:00
fontawesomeが使えない場合の対応方法
今回の記事では、fontawesomeという超便利なWebアイコンツールを使おうと読み込んだものの、
うまく表示されない場合の解決パターンをご紹介します。バージョンの確認
まずバージョンの確認をしましょう。
CDNを使用している場合は、リンク内にバージョンが書いてるのでそこを確認して下さい。<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.8.2/css/all.css" integrity="sha384-oS3vJWv+0UjzBfQzYUhtDYW+Pj2yciDJxpsK1OYPAYjqT085Qq/1cq5FLXAZQ7Ay" crossorigin="anonymous">この場合は「v5.8.2」です。
2019年5月時点では、このバージョンが最新になります。旧バージョンは4から始まるバージョンです。
<link href="https://maxcdn.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css" rel="stylesheet">「4.7.0」と書いています。
このバージョンの違いで、使用できるアイコンの種類と、cssでの指定方法が変わってきます。
使用できるアイコンの確認
バージョンごとの使用できるアイコンの確認する方法のご紹介です。
まず、普通にfontawesomeのページより検索した結果が、新バージョンで使えるアイコンです。トップページ下の部分の↓赤枠で囲まれているところから飛んだ先が旧バージョンで使えるアイコン一覧です。
CSS指定の確認
CSSで指定する場合、
content: "\f105";という感じで記述してあげます。
さらにfont-familyも指定する必要があるんですが、これがバージョンによって違います。新バージョン
li::before { font-family: "Font Awesome 5 Free"; content: "\f105"; }旧バージョン
li::before { font-family: FontAwesome; content: "\f105"; }Freeのアイコンか
PROと書いてあるアイコンは有料版しか使えないので、注意しましょう。
その他
他にも、font-weight の値を変えてみると表示されたりします。
この記事に書いてある方法で表示できるようになれば幸いです!
- 投稿日:2019-05-30T12:36:24+09:00
fontawesomeが表示されず◻︎(四角)になってしまう場合の対応方法
今回の記事では、fontawesomeという超便利なWebアイコンツールを使おうと読み込んだものの、
うまく表示されない場合の解決パターンをご紹介します。バージョンの確認
まずバージョンの確認をしましょう。
CDNを使用している場合は、リンク内にバージョンが書いてるのでそこを確認して下さい。<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.8.2/css/all.css" integrity="sha384-oS3vJWv+0UjzBfQzYUhtDYW+Pj2yciDJxpsK1OYPAYjqT085Qq/1cq5FLXAZQ7Ay" crossorigin="anonymous">この場合は「v5.8.2」です。
2019年5月時点では、このバージョンが最新になります。旧バージョンは4から始まるバージョンです。
<link href="https://maxcdn.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css" rel="stylesheet">「4.7.0」と書いています。
このバージョンの違いで、使用できるアイコンの種類と、cssでの指定方法が変わってきます。
使用できるアイコンの確認
バージョンごとの使用できるアイコンの確認する方法のご紹介です。
まず、普通にfontawesomeのページより検索した結果が、新バージョンで使えるアイコンです。トップページ下の部分の↓赤枠で囲まれているところから飛んだ先が旧バージョンで使えるアイコン一覧です。
CSS指定の確認
CSSで指定する場合、
content: "\f105";という感じで記述してあげます。
さらにfont-familyも指定する必要があるんですが、これがバージョンによって違います。新バージョン
li::before { font-family: "Font Awesome 5 Free"; content: "\f105"; }旧バージョン
li::before { font-family: FontAwesome; content: "\f105"; }Freeのアイコンか
PROと書いてあるアイコンは有料版しか使えないので、注意しましょう。
その他
他にも、font-weight の値を変えてみると表示されたりします。
この記事に書いてある方法で表示できるようになれば幸いです!
- 投稿日:2019-05-30T11:18:09+09:00
初めてのフロントエンド。
はじめに
私は今までバックエンドとしてサーバー周りだったり、apiがどうのこうのを主にGolangで作業をしてたのですが、この度フロントエンドをやってみることに。
表側もかなり大変ですね ~
javascriptとは
Javaとは別物の言語でオブジェクト指向型スクリプト言語だが、クラスの概念もあると。
なんだか面白そうだと思いました。
今回は引数でmethodやendopoint,パラメーター,必要なcolumn情報(DB)を渡してレスポンスを得る関数を作成しただけですので、クラス等はまた今度。
XMLHttpRequest
さて、早速調べていくのですが、早速いいもの見つけました。
XMLHttpRequestというのがあるじゃないですか。XMLHttpRequestとは。
Ajax(非同期通信)で使われる組み込みオブジェクトのことで、サーバーへ通信リクエストが送れるようになる。とのことです。
コーディング開始
もうこれ使うしかないなと思って、早速調べながらコーディングを始めました。
で、一番最初に書いたコードがこちら ...loginApiRequest.jsfunction get_login_info_response(method, endpoint, parameters) { // XMLHttpRequestオブジェクトを作成 var request = new XMLHttpRequest(); // Httpリクエストに必要な情報 request.open(method, endpoint); request.setRequestHeader('content-type', 'application/x-www-form-urlencoded;charset=UTF-8'); request.responseType = 'json'; // 実行 request.onload = function() { response_from_database = this.response; console.log(response_from_database); true_or_false = response_from_database['is_admin']; console.log(true_or_false); return true_or_false }; // Httpリクエストを送信(引数指定で特定の情報のみを送信) request.send(parameters); }「js始めて全然月日経ってないのこのコード割と使えるんじゃ!?」
って思ってましたが、色々と不備が多いです。まず一番やらかしてるのは、.onload内のスコープで返り値出そうとしていることですよね。
これは絶望的です、やっちゃってますね。これhtml側から関数呼んでも、スコープがズレてるのでコンソールには"undefined"と表示されちゃうんです。
そして、処理が一方通行です。http.statusでステータスコードを判別して処理を書くべきです。401が渡された時にエラーも何も表示されないとユーザー側は何が起こったか理解できないじゃないかと。
返り値をちゃんともらうのに結構苦労しました。
こんなコードも書きました。loginApiRequest.jsa = request.onload = function () { ... } return a血迷っちゃったんでしょうか。
.onloadで取得した結果をそのままreturnしようとしたんです ...
反省してます。いくつもの試行錯誤を重ね、最終的にたどり着いたコードが以下です。
loginApiRequest.jsfunction get_login_info_response(method, endpoint, parameters, callback) { // XMLHttpRequestオブジェクトを作成 var request = new XMLHttpRequest(); // Httpリクエストに必要な情報 request.open(method, endpoint); request.setRequestHeader('content-type', 'application/x-www-form-urlencoded;charset=UTF-8'); request.responseType = 'json'; // 実行 request.onload = function() { response_from_database = this.response; // ステータスコードによって処理を変更 if (request.status === 401) { alert("IDかパスワードが違います。"); console.log(response_from_database); } else if (request.status === 200) { true_or_false = response_from_database['is_admin']; console.log(true_or_false); } callback(true_or_false) }; // Httpリクエストを送信(引数指定で特定の情報のみを送信) request.send(parameters); }最終的にたどり着いた答えはcallback関数でした。
ここでcallback関数について書いても長くなるだけなので、
callback関数とはをご参照くださいませ。これでhtml側からうまく返り値を受け取れて、trueかfalseによってログインの処理ができるようになりました。
まとめ
割と綺麗にコードが書けたんじゃないかなと自画自賛しちゃいましたが、javascriptが達者な方から見たらどうなんでしょうか ... 気づいた方がいらっしゃいましたらお気軽にご指摘していただけると幸いです。
ご参考にさせていただいた主なサイト様
https://sbfl.net/blog/2019/02/08/javascript-callback-func/#i
https://qiita.com/sirone/items/412b2a171dccb11e1bb6
こちらの記事は特に大変参考になりましたありがとうございます。
- 投稿日:2019-05-30T11:09:05+09:00
素人によるWeb制作のいろは
少しづつ更新していく予定。
間違い等ありましたらご指摘いただけると幸いです。Webページ制作について
Web制作は大原則、Webサーバから提供されるもの。Webサーバ上にあるWebページに必要な情報(HTML、CSS、JavaScript)を使う。
Web上で利用するサービスによってはデータベース等のミドルウェアを利用する。Webページとミドルウェアだけではあるだけの為利用できない。これらに情報を橋渡しするためにpython(パイソン)やPHPと呼ばれるものを利用する。
Webページを制作するにあたり必要なもの
- Webサーバ
- Webページを表示する為の言語 → 「Webページに必要な情報とは」に記載
- ミドルウェア
Webページに必要な情報とは
Webページはgoogleなどから検索し必要なサイトをユーザが選び、選んだ先のものを表示させている。
この表示をさせるために必要なものが「Webページに必要な情報」である。これらを構成するためには3つの専用言語が必要になる。
- HTML(HyperText Markup Language)
- CSS(Cascading Style Sheets)
- JavaScript
HTML : Webページを表示させる最低限必要なもの
CSS : HTMLで作ったWebページのデザインを作るために必要なもの
JavaScript : 作ったWebページ上でYoutubeなどを再生させたりするためのものWebページとしてはHTMLは必須だが、他CSS、JavaScriptは無くても作成することができる。
※ただし、今日のWebページ全てはCSS、JavaScriptが導入されている。Webサーバについて
Webサーバは主に専用アプリケーションを導入し構築する。
主なメジャー製品は以下の模様。
Server Application Windows系 IIS Linux系 Apatch Windows系のサーバはIISを利用する。
IISはWindowsServer2012R2まではサーバ用アプリケーションであったが、WindowsServer2016/Windows10
サーバOS、クライアントOS共に利用できるようになった模様。HTMLとは
HTMLとはHyperText Markup Languageの略、今日に至るWebページの基礎を作った。
2019年現在、HTMLはVer.5。HyperTextというのは1つの文書(webページ等)から各文書へのハイパーリンクや動画の表示等するもののこと。
HTMLはその専用コンピュータ言語のこと。HTMLの目的は情報構造を定義するためのもの
このページにどういったものが必要になるか。
材料の用意になる。HTMLはファイル名に[ファイル名.html]にする。
基本的に作成するHTMLファイルの中身は以下のようになる。
HTML-Base<!DOCTYPE html> <html> <head> <title>Web Title Name</title> </head> <body> </body> </html>CSS
各サイトの見た目をどのようにするか、文字の位置や枠の幅、画像の配置を定義するもの。
CSSはHTML上、または専用のCSSファイルを作成すれば作ることが可能。
ただしCSSは記述しても機能しない
そのためHTML上から宣言し、ファイルを呼び出す必要が有る。HTML側の定義<link rel="stylesheet" href="xxx.css">資料リンク
- 投稿日:2019-05-30T08:48:00+09:00
GoogleMapへのリンクURL作成方法を調べた
サイトにGoogleMapを埋め込む場合、Googleが提供しているJavaScriptのAPIを使用するのが一般的です。
そうではなく、a要素で作るような単なるリンクを作成したい、という場合にどういう規則でURLを作成すればよいのか調べてみたものです。
やってみると意外と楽しいです。
前提
システム側で、マップを作成するための住所や緯度経度、建物名を保持していて、URLを自動生成するものとします。つまり、一つ一つの所在地をGoogleMapで調べてリンクを取得したり、短縮URLを取得していく方法は使いません。
また、下記の内容は2019年5月29日時点で調べたものです。仕様変更等はご了承ください。
公式ドキュメント
https://developers.google.com/maps/documentation/urls/guide?hl=ja
Maps URLsという文書があり、そこに書いてあります。公式ドキュメントを引用すると、簡単な解説
Using Maps URLs, you can build a universal, cross-platform URL to launch Google Maps and perform searches, get directions and navigation, and display map views and panoramic images.
Google翻訳結果
GoogleマップのURLを使用すると、Googleマップを起動して検索を実行したり、方向やナビゲーションを取得したり、マップビューやパノラマ画像を表示したりするための、ユニバーサルでクロスプラットフォームのURLを構築できます。
使用について
You don't need a Google API key to use Maps URLs.
Google翻訳結果
Maps URLを使用するのにGoogle APIキーは必要ありません。
との記述がある通り、URLを使う場合Google API keyは不要です。手間なく扱えるようです。各OSでGoogle Mapアプリがインストールされている場合どういう挙動をするか、などについても書いてあります。
以下、上記ドキュメントに基づいて記載します。
作れるリンクの種類
Search(検索)
特定の場所にピンを立てる、または一般的な検索のリクエスト
https://www.google.com/maps/search/?api=1¶metersという形式仕様上、ズーム指定できません。
Direction(道順)
指定した場所間の道順を表示するリクエスト
https://www.google.com/maps/dir/?api=1¶metersという形式Display a map(地図を表示)
SearchやDirectionと異なり、ピンや道順を表示せずに、単に地図を表示するリクエスト
https://www.google.com/maps/@?api=1&map_action=map¶metersという形式Display a Street View panorama(ストリートビュー表示)
ストリートビューのパノラマ画像表示のリクエスト
https://www.google.com/maps/@?api=1&map_action=pano¶metersという形式試してみる
東京駅をターゲットにしてみます。GoogleMapで検索すると、緯度経度は
35.6812362,139.7649361となっているので、それを使いましょう。検証には
Edgeを使っています。Search
パラメータは、
queryまたはquery_place_idです。どちらかが必須です。query_place_idの取得方法は調べ切れませんでした。https://www.google.com/maps/search/?api=1&query=東京駅
ウィンドウ小さくした影響か、ピンは隠れていますが出てきます。日本語でそのまま検索しても、一応問題なく使えます。検証は必要かと思います。
次に緯度経度です。
https://www.google.com/maps/search/?api=1&query=35.6812362,139.7649361
こちらも問題ないですね。
東京駅周りの書店、なんて指定もできます。キーワードを
+で区切ります。https://www.google.com/maps/search/?api=1&query=東京駅+書店
Direction
必須パラメーターは、
パラメーター名 意味 originスタート地点 destination目的地 です。
Searchと同じく、place_idも使えるようです。東京駅から横浜駅に行ってみます。
https://www.google.com/maps/dir/?api=1&origin=東京駅&destination=横浜駅
おお…これはすごい。ちゃんと出る。
以下、オプションのパラメーターを見ていきます。
travelmode
初期に表示される移動方法を指定できるようです。
- 車(driving)
https://www.google.com/maps/dir/?api=1&origin=東京駅&destination=横浜駅&travelmode=driving
おお…!
他にも指定できます。指定しない場合は、ルートやユーザー設定に基づいて選択されるそうです。
dir_action=navigate
経路案内してくれるパラメーターのようです。現在位置や区間に基づいて行われるようで、詳細な検証ができませんでした…。
経路案内できない場合は、このパラメーター無視するよ、と書いてあります。waypoints
経由地を加味したルート検索を行ってくれます。
waypointsに指定するのは、originやdestinationと同じく、建物名や緯度経度等になります。複数指定する場合は|で区切ります。経由地計算も、行えない場合は無視されるそうです。
Display a map
https://www.google.com/maps/@?api=1&map_action=map
と、パラメータ無しで開けます。この場合は現在地等に基づいた表示になるのだろうと思います。
以下、オプションのパラメーターを見ていきます。
center
中心点を指定します。緯度経度での指定になります。
https://www.google.com/maps/@?api=1&map_action=map¢er=35.6812362,139.7649361
東京駅が中心になりました。
zoom
地図の倍率を指定します。0~21だそうです。最大にしてみましょう。
https://www.google.com/maps/@?api=1&map_action=map¢er=35.6812362,139.7649361&zoom=21
最大は大きすぎますね。
basemap
地図タイプ指定です。roadmap(通常、未指定の場合これ)、satellite(衛星)、terrain(地形図)の三種類です。
- satellite
https://www.google.com/maps/@?api=1&map_action=map¢er=35.6812362,139.7649361&&basemap=satellite
- terrain
https://www.google.com/maps/@?api=1&map_action=map¢er=35.6812362,139.7649361&&basemap=terrain
東京で地形図を出しても、高低差が無いのであまり意味が無いですね…
Display a Street View panorama
基本URLは
https://www.google.com/maps/@?api=1&map_action=panoです。が、これ以上パラメーターを指定しない場合は単にマップが開きます。以下のいずれかが必須です。
パラメーター 内容 viewpoint表示する地点の緯度経度 panoパノラマID 両方指定した場合、
panoで指定したIDのパノラマが見つからない場合にviwepointを使用する、という挙動になるそうです。どちらでもパノラマ画像が見つからない場合は、マップのデフォルト挙動をするそうです。試してみましょう。
https://www.google.com/maps/@?api=1&map_action=pano¶meters&viewpoint=35.6812362,139.7649361
思いっきり、駅構内みたいですね。
追加パラメーターも見ていきます。
heading
デフォルトを北として、そこから何度向き直すか、という指定です。
-90だと、左を向くようです。つまりプラスだと(自分が)時計回りするイメージみたいです。
pitch
上を向くか下を向くか、という感じです。-90~90の範囲で指定します。
headingと同じ位置で45度上を向いてみました。なるほど。
fov
ズーム倍率、のようです。値が小さいほどズーム倍率が大きくなる(近くなる)ようです。
余談
これらのURLを使って、ブラウザからGoogleMapにアクセスすると、URLが別のもの(GoogleMapが使用するもの)に置き換わります。そのURLはGoogleの仕様によって変わりうると想定されます。
なので、URLを生成する場合はAPIに準拠した形で生成するほうがよさそうですね。
おためし:Geolocation APIと組み合わせる
デザインは適当です。また、細かいエラーチェック等は割愛しています。
index.html<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <button id="mapper">現在地を取得して経路を出す</button> <script src="main.js"></script> </body> </html>上のようなHTMLを用意して、
main.jsconst btn = document.getElementById("mapper"); btn.addEventListener("click", e => { if (navigator.geolocation) { //Geolocation APIを利用できる環境向けの処理 const navi = navigator.geolocation; navi.getCurrentPosition((pos) => { const latlng = `${pos.coords.latitude},${pos.coords.longitude}`; const link = `https://www.google.com/maps/dir/?api=1&origin=${latlng}&destination=東京駅`; const anchor = document.createElement("a"); anchor.text = "GoogleMapで経路を見る" anchor.target = "_blank"; anchor.href = link; document.body.appendChild(anchor); }); } else { //Geolocation APIを利用できない環境向けの処理 } });上のようなJavaScriptを用意します。すると、
ユーザーの許可を得て現在位置を取得した上で、Directionを指定してGoogleMapを呼び出す、なんてこともできますね。
使い方次第でいろいろ便利かもしれない、と思った次第です。

















