CodeSandbox で表示されないときがある
StackBlitz とか CodeSandbox とか高機能で便利なブラウザ上で HTML や JavaScript の編集・実行ができるツールがあるけどなんだかんだシンプルな昔ながらのが安定かも

CodeSandbox はリロードしたり共有した URL を開いたりしたときに何も表示されないときがある
HTML 部分は何もレンダリングされず画面は真っ白
なのに JavaScript は実行されてるようで 要素が見つからなくてエラーが起きる

<div>
<div id="a"></a>
<script src="src/index.js"></script>
</div>

みたいに最後に JavaScript をロードしてるのでスクリプトが実行されてるならありそうなのに
devtools でみた感じでは csb-loading-screen という id の div と CodeSandbox 関係らしき script タグが複数あるくらい

構文エラーとかは出てないし なぜか数値や文字列を適当に変えたり 使わない変数を追加など何かの変更をして再保存するとかで表示されたりする

他のコード見てみるとフレームワークなどで document.body の内側は全部 JavaScript で作ってるのとか多いし気づかれてないか そもそも HTML は使う想定じゃない?(それならなんで HTML 書けるんだっていいたいけど)
git ですべてのメタ情報を表示する
git ではデフォルトだとメタデータは Author と Date くらいしか表示されません

$ git show --quiet
commit 3baa0b76cea3d44cdc72e6de322dffb55ef627e1 (HEAD -> master)
Author: NER <mail@address>
Date: Mon May 20 23:18:25 2019 +0900

test

GUI ツールでもこれくらいしか表示してないのもよく見ます
ですが実際は Author と Committer の 2 つのユーザ情報があります
通常見えないものも含めて全部の情報を表示するには --pretty=raw を指定します
raw 以外に full と fuller もあります
full は Committer が出る代わりに時刻が出ません
fuller では時刻も出ます
raw になると tree のハッシュ値も増えます

$ git show --quiet --pretty=full
commit 3baa0b76cea3d44cdc72e6de322dffb55ef627e1 (HEAD -> master)
Author: NER <mail@address>
Commit: NER <mail@address>

test

$ git show --quiet --pretty=fuller
commit 3baa0b76cea3d44cdc72e6de322dffb55ef627e1 (HEAD -> master)
Author: NER <mail@address>
AuthorDate: Mon May 20 23:18:25 2019 +0900
Commit: NER <mail@address>
CommitDate: Mon May 20 23:18:25 2019 +0900

test

$ git show --quiet --pretty=raw
commit 3baa0b76cea3d44cdc72e6de322dffb55ef627e1
tree 2ce1eef76631e82282e0f7f0cf9e6f3e9a4a0b1e
author NER <mail@address> 1558361905 +0900
committer NER <mail@address> 1558361905 +0900

test
イメージプレビュー系ライブラリ
Fancybox3
https://fancyapps.com/fancybox/3/
jQuery
良い感じだけど jQuery 依存なのだけがネック
モバイル対応や GPU アクセラレーションやマルチインスタンス対応など高機能なのでもったいない

Fullscreen Lightbox
https://fslightbox.com/javascript
VanillaJS
jQuery 依存ないし良い感じだけど無料版は基本機能だけ
ズーム・サムネ・キャプション・ツールバー など便利機能は有料版の PRO 必要

Lightbox2
https://lokeshdhakar.com/projects/lightbox2/
jQuery
これがこの系統ライブラリのスタンダード?
lightbox 系と呼ばれたりもするし元になったらライブラリぽい
jQuery 必要だし機能もシンプルで最低限だけみたいなので あえて選択はしなくていいかも

WA MediaBox
https://jiri.hybek.cz/wa-mediabox/
VanillaJS
ドキュメントみても情報少なめ(機能が自体が少なめ?)
DEMO の感じだと ZOOM とかキャプションなど高機能なものはなさそう
画像ロード遅め(DEMO の画像が重いだけかも)

PhotoSwipe
https://photoswipe.com/
VanillaJS
ツールバーやキャプションにズームなど 基本機能以上の機能があるしモバイルも対応
さらに VanillaJS ととても良さそうなのに特に聞かない名前だし ウェブサイトもシンプルでちょっと古めなイメージの見た目

lightgallery.js
https://sachinchoolur.github.io/lightgallery.js/
VanillaJS
VanillaJS ですごく高機能
ツールバーやキャプション・ズームに加えて サムネ表示やサムネにカーソル合わせたときのアニメーションもある
ウェブサイトもきれいでアニメーションやロード画面などあって PhotoSwipe よりできる感ある
久々に古い JavaScript で非同期処理を書いた
async/await ないのけっこうつらい

async function main(){
let x = 100
console.log(1)
x += 200
await new Promise(r => setTimeout(r, 1000))
console.log(2)
x += 300
await new Promise(r => setTimeout(r, 2000))
console.log(x)
}
main()
// 1
// 2
// 600

これをするのがこうなる

function main(){
var x = 100
seq([
function(n){
console.log(1)
x += 200
setTimeout(n, 1000)
},
function(n){
console.log(2)
x += 300
setTimeout(n, 2000)
},
function(n){
console.log(x)
n()
}
])
}

function seq(a){
var i = 0
function next(end){
if(end) return
var fn = a[i++]
var args = Array.prototype.slice.call(arguments)
args[0] = next
if(fn) fn.apply(null, args)
}
next()
}

main()
// 1
// 2
// 600

非同期処理用の関数を順番に実行する seq 関数を事前に準備しておく
await したい非同期処理の場所でコードを分割してそれぞれを関数にする
その関数の配列を seq に渡して実行

seq から実行される関数には引数で次の実行のための関数と前の処理から渡された値を受け取る
非同期処理のコールバック関数として 引数で受け取った次の処理を行うための関数を設定すれば await 代わりになる
途中で return したいこともあるので引数で渡される関数の第一引数に true を渡せば途中も終了できる

ローカル変数は引き継がないので seq を実行するスコープで宣言しておく
もしくは引数で受け取る関数の 2 つ目以降の引数で渡す

パッと見騙されそうな変数宣言
ネット上のコード見てたらこういうのがありました

let x, y = 100, data

⇩ のように読んでから

let x = 100
let y = data

「え JavaScript でそんな代入できたっけ?」 と二度見
⇩ みたいにする必要があったはずだけどいつのまにか新機能できてた?

let [x, y] = [100, data]

10 秒くらい考えてから x と y と data を宣言して y に 100 を代入してるだけだと理解しました
自分では宣言をまとめて書くなんてしないからパッと見では脳内パースが正しくできませんでした
Python 書いた後だと特に紛らわしいですよね
マウス乗せたときだけスクロールバーを出す
:hover で overflow を切り替えるだけ
スクロールバーデザインも変えてモバイル風味にしてみた

webkit-scrollbar 系には opacity 効かないし 背景を透明にしても裏側は見れない
-webkit-scrollbar-thumb の background は設定できるけど transition でアニメーションしない
JavaScript で徐々に背景色の alpha 値変えればいけそうだけど CSS で収めたかったのでやってない

<!doctype html>

<style>
* {
box-sizing: border-box;
}

.box {
width: 200px;
height: 300px;
border: 2px solid #c4cf8a;
overflow: hidden;
}

.box:hover {
overflow: overlay;
}

.box::-webkit-scrollbar {
width: 6px;
height: 6px;
}

.box::-webkit-scrollbar-thumb {
background: #aaa;
border-radius: 5px;
}
</style>

<div class="box"></div>

<script>
const b = document.querySelector(".box")
b.innerHTML += ("12345".repeat(10) + "<br/>").repeat(100)
</script>
lit-html でリスナの this は eventContext で設定できる
カスタムエレメント中で render にこんなオプション付きで実行

    render() {
return render(this.template, this.shadowRoot, { eventContext: this })
}

eventContext: this を render の 3 つ目の引数に設定しておくと テンプレートの HTML に @XXXX で設定したリスナ実行時の this がそのカスタムエレメントになる
なにも設定しないと this はイベントが起きた要素

    get template() {
return html`
<div @click=${this.onClickDiv}>click me</div>
`
}

onClickDiv(eve) {
console.log(this)
}

こう書いたときの this が他メソッドと同じようにカスタムエレメント自身なので見やすい

テンプレート側でこうも書けるけど見づらいし忘れがちなので render で設定するほうがおすすめ

html`<div @click=${this.onClickDiv.bind(this)}></div>`

この方法だと render のたびに bind で作った新しい関数を設定してるから毎回リスナを再設定することにもなるしね
Python でクリップボードの REPL 出力を実行できる形式に変換する
import pyperclip

text = pyperclip.paste()
lines = text.splitlines()
lines = [line[4:] if line.startswith(">>>") or line.startswith("...") else "# " + line for line in lines]
pyperclip.copy("\n".join(lines))

⇩のような REPL の出力を

>>> class A: pass
...
>>> def x():
... return 1
...
>>> x()
1
>>> A()
<__main__.A object at 0x7f64c810be48>

⇩に変換する

class A: pass

def x():
return 1

x()
# 1
A()
# <__main__.A object at 0x7f64c810be48>

現在のクリップボードのテキストを変換するので REPL 出力をコピペするときに貼り付けの前にこれを実行する
REPL のフォーマットじゃなくて実行できる正しい Python 構文にしたいときに便利
複数文まとめて再実行するときにも使える
実行にはライブラリ pyperclip が必要

これまで web ページで変換ツールにしていたけど
1)ページ開いて
2)入力ボックスに貼り付けて
3)出力ボックスをコピーして
という手順が面倒でクリップボードのデータをそのまま変更したほうが楽そうなのでやってみた

クリップボード履歴管理ツールを使ってると変更前のも残るので便利