Contents
前提条件
UIに凝っていたら投稿の時間が空いてしまいSEO的によろしくない為、記事を分けました。
拙稿のリンク
https://github.com/mayarin/firebase-sample
今回追加する内容
前稿での予告通り、リアルタイムチャットを実装します。
実装を行います
テキスト他データの置き場としてCloud Firestoreを作ります。
言われるがままに作ります。
なんか下手打ってた?(´・ω・`)
できた。中身にデータを格納するのは実装で行います。
https://firebase.google.com/docs/firestore/manage-data/add-data
公式を参照しながら、やはり利用するjs群に以下を追加します。
<script src="/__/firebase/7.22.0//firebase-firestore.js"></script>
プロフィール更新フォームにいったん退いてもらって、こんなフォームにしました。
<div id='chat_area'> <div id='chat_window'></div> <form id='chat_form'> <textarea class="form-control col-12" id='chat_message' placeholder='メッセージ...'></textarea> <button class="btn btn-primary" type='submit'>ポスト</button> </form> </div>
document.querySelector("#chat_form").addEventListener("submit", function(event) { var user = firebase.auth().currentUser; var db = firebase.firestore(); var date = new Date(); var datetime = date.getFullYear() + '-' + (date.getMonth() +1 ) + '-' + date.getDate() + ' ' + date.getHours() + ':' + date.getMinutes() + ':' + date.getSeconds() ; // Add a new document in collection "cities" db.collection("openchats").doc().set({ uid: user.uid, name: user.displayName, message: getElementValue('chat_message'), picture: user.photoURL, datetime : datetime }) .then(function() { console.log("Document successfully written!"); }) .catch(function(error) { console.error("Error writing document: ", error); }); event.preventDefault(); });
これらにてfirestoreに書き込まれているのを確認できました。
さてここから登録されたものをchat_windowに整形しながら取ってきます。
UI慣れないといいながらこんな感じで作りました。
ここから技を使います。
めいめいのUIのHTMLは以下のように作ってあります(CSS省略)
<span id='any_chat_parts_template'> <div class='any_chat_parts chat_parts'> <div class='chat_message col-6'>replace_to_message</div> <div class='chat_datetime col-4'>replace_to_datetime<br> <img class='profile_picture' src='./unnamed.png'><br>replace_to_name </div> </div> </span> <span id='my_chat_parts_template'> <div class='my_chat_parts chat_parts'> <div class='chat_message col-6'>replace_to_message</div> <div class='chat_datetime col-4'>replace_to_datetime<br> <img class='profile_picture' src='./unnamed.png'><br>replace_to_name </div> </div> </span>
これらをこうしてjavascriptに読み込み、画面からは削除
var any_chat_parts = getElemID('any_chat_parts_template').innerHTML; var my_chat_parts = getElemID('my_chat_parts_template').innerHTML; getElemID('any_chat_parts_template').remove(); getElemID('my_chat_parts_template').remove();
https://firebase.google.com/docs/firestore/query-data/listen?hl=ja
上記の通りリアルタイムアップデートを取得する箇所で以下の通りに当て嵌めます。
query.onSnapshot(function(snapshot) { snapshot.docChanges().forEach(function(change) { console.log(change.type); var message = change.doc.data(); console.log(change.doc.id); console.log(message.uid); var line = ''; if(message.uid == user.uid){ line = my_chat_parts; } else { line = any_chat_parts; } line = line.replace('replace_to_message', message.message); line = line.replace('replace_to_datetime', message.datetime); line = line.replace('replace_to_name', message.name); line = line.replace('./unnamed.png', message.picture); getElemID('chat_window').innerHTML += line; }); getElemID('chat_window').scrollTop = getElemID('chat_window').scrollHeight; });
よし、ラリーっぽくなりました。
ここまで満たした仕様は以下の通り。
- サインアップ
- サインイン
- サインアウト
- パスワード再設定リンク請求
- サインイン後プロフィール更新
- ログインメールアドレス変更
- ログインパスワード変更
- アカウント削除
- アカウント全体でのチャット
最終的に
- さっき隠したプロフィール更新フォームをパタパタ
- 個人間チャットを積む
- チャットメッセージが消された際のリフレッシュを行う
- アカウントが削除された際にチャットデータも削除
など細かい調整を行います。
なおfirebaseプロジェクトはこちら。
参考リンク
https://qiita.com/noobar/items/52d5c364a8e16b8b3fec
https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/String/replace