単語クロック、言葉で時間を指示する時計を作る


This post was originally posted on The Algorithmic Cookbook under Making Word Clock, A Clock Which Tells The Time With Words

This post is also on .


見たa TikTok ここで、この男はqlocktwo w、言葉で時間を指示する時計を曲げていた.これは私を作ることを示唆a web version それは私が1晩夕方にした(そして、ここで、そして、そこで固定されました)の中で、私はこのポストを書き始めて、それで多くの問題を発見したときのようです.方法はこちら.

先行技術


時計を借りて、私はそれをオンラインで見つけようとしました.私の最初の検索用語は'単語クロック'だった、私はonline word clock by timeanddate.com . それだけでなく、言葉の時間を示して、それは、複数の都市のために、異なる言語ではありません.私が始めさえする前に、外へ出てください.

もう少し見てみると、Tiktokの時計はAと呼ばれますQlockTwo W そして、それは少なくとも800ドルかかります.

グリッドの作成


最初のチャレンジはグリッドを作りました.最善の方法はアルゴリズム的にそれを生成することです、しかし、私は方法を知っていませんでした.代わりに、手動でやった.最初はオンラインで1つリッピングしようと思っていましたが、試してみることにしました.

多くの実験の後、私はどうにかこのレイアウトを作りました.アンダースコアはランダム文字であることに注意してください.
# /_includes/js/grid.txt
a I T _ I S _ _ T W O N E _ _
b _ T H R E E L E V E N I N E 
c _ _ T W E L V E I G H T E N 
d _ F I V E _ S I X _ F O U R
e S E V E N _ T W E N T Y _ _
f T H I R T Y O H F O U R T Y
g _ F I F T Y _ _ T W O N E _
h _ F O U R T E E N _ F I V E
i T H R E E _ _ F I F T E E N
j _ S E V E N T E E N _ T E N 
k _ _ E I G H T E E N _ _ _ _
l _ _ _ N I N E T E E N _ _ _
m _ T W E L V E L E V E N _ _
n S I X T E E N _ O C L O C K
o T H I R T E E N _ _ _ _ _ _

グリッドをコードに変える


ウェブサイトを構築するためにEleventy どのように拡張可能なのでJavaScriptを介してです.私がそれを設定した方法は大きな混乱ですが、それは動作します.
グリッドを定義するために、私はそれを定義したようにグリッドを含むオブジェクトとJSファイルを作成しました.
module.exports = {
  order: ['a', 'b', ..., 'o'],
  a: ['I', 'T', ...rc(1), 'I', 'S', ...rc(2), 'T', 'W', 'O', 'N', 'E', ...rc(2)],
  b: [...rc(1), 'T', 'H', 'R', 'E', 'E', 'L', 'E', 'V', 'E', 'N', 'I', 'N', 'E'],
  ...,
  o: ['T', 'H', 'I', 'R', 'T', 'E', 'E', 'N', ...rc(6)]   
}

様々な関数呼び出しに気づくかもしれません...rc(n) . これはn個のランダム文字を生成し、spread operator . So ...rc(2) つのランダム文字を生成します.以下はランダム文字を生成するコードです.
function randChars (num) {
  const chars = []
  for (let i = 0; i < num; i++) {
    const randCharCode = 65 + Math.floor(Math.random() * 25)
    chars.push(String.fromCharCode(randCharCode))
  }
  return chars
}
const rc = randChars

For num 項目は、それは65から90までの乱数を生成しますASCII codes 対応するASCII文字をchars を返します.なぜ私はラインを追加const rc = randChars 名前変更の代わりにrandChars to rc 私はかつてそれを使用したので.
このことはひどく非効率的だが、サイトを構築するためにはあまり重要ではない.それはまだかなり速くビルドします.その後、再び、本当に遅いものが来る.
このグリッドをWebページに表示するには、_data/ グリッドを定義したスクリプトをインポートするディレクトリ.私がこれを書いていたので、私は、私がちょうどそこで始めるためにそこでそれを定義することができたと理解しました.どちらの方法でも、それは私がNunjucksテンプレートでしたウェブページに行かなければなりませんでした.
<div id="clock" aria-hidden="true">
    {%- for row in grid.order %}
        <div class="row" data-row="{{ row }}">
            {%- for col in grid[row] %}
                <span data-cell="{{ row }}{{ loop.index }}" data-lit=false>{{ col }}</span>
            {%- endfor %}
        </div>
    {%- endfor %}
</div>

このコード:
  • で定義された順序でグリッドの行をループしますorder プロパティ
  • を作成するdivdata-row 属性は現在のグリッドに設定します.
  • その中で、その行の各要素をループして
  • とのスパンでそれを置くdata-cell 属性は行と項目のインデックス、data-lit 虚偽(より多くの)と内容が手紙であること.
  • それに加えて、グリッドを定義して時間を更新する方法を指定する必要がありました.私は、すべての単語がグリッドにあるところを指定している大きな、201の線長いオブジェクトでこれをしました.の位置を指定しましたか?言葉'IT' , 'IS' . 'OH' and 'OCLOCK' , 分と時間の場所を自分のオブジェクトで定義されている.私のグリッドが設計されている方法のおかげで、私は-ティーンズと下位ティーンの前にすべての- ty番号を入れたので、私は59分のそれぞれのすべての場所を一覧表示する必要はありませんでした.
    const words = {
      IT: {
        row: 'a',
        start: 1,
        end: 2
      },
      ...,
      hours: {
        1: {
          row: 'a',
          start: 10,
          end: 12
        },
        ...
      },
      minutes: {
        1: {
          row: 'g',
          start: 11,
          end: 13
        },
        ...
      }
    
    
    これは、グリッドが2つの場所、マークアップのための1つの場所、および別の時間制御で定義されていることを意味します.そのセットで、それは時間を表示する時間ですか?

    時間を示す


    サイトのコードが含まれています.で、初期化されますinit 関数.
    function init() {
      const now = new Date()
      const nextMinIn = (60 - now.getSeconds()) * 1000 + now.getMilliseconds()
      updateTime(now)
      setTimeout(() => {
        updateTime(new Date())
        setInterval(() => {
          updateTime(new Date())
        }, 60000)
      }, nextMinIn)
    }
    
    
    このコードは、以下のようになります.
  • 現在の時刻を表示します.
  • 次の分までの時間を計算しますnextMinIn ) ミリ秒単位で
  • タイムアウトを実行するnextMinIn ミリ秒
  • 更新時刻と
  • 間隔ごとに時間を更新する間隔を設定します.
  • すべての楽しいものを開始します.updateTime , 時間がかかるtime .
    何に関してupdateTime 実際には、
    function updateTime(time, currLitElems) {
      lightTime(time, currLitElems)
      const timeElem = document.getElementById('accessTime')
      let prettyNow = time.toLocaleTimeString([], {hour12: true, hour: '2-digit', minute: '2-digit', })
      timeElem.innerHTML = `It is <time datetime="${prettyNow}">${prettyNow}</time>`
    }
    
    
    これは、両方の単語クロックとtimeElem 私はHTMLで現在の時刻のアクセス可能なバージョンを提供するために_includes/main.njk .
    <p id="accessTime" class="sr-only" aria-live="polite" aria-atomic="true"></p>
    
    
    に戻るupdateTime , があるlightTime を受け取る関数time そして、UIでそれを示します.
    function lightTime(time) {
      dimLitWords()
      const hour = time.getHours() % 12 === 0 ? 12 : time.getHours() % 12
      const hourCells = words.hours[hour]
      const minutes = time.getMinutes()
      const litElems = [words["IT"], words["IS"], hourCells]
    
      switch(true) {
        case minutes === 0:
          litElems.push(words['OCLOCK'])
          break;
        case minutes < 10:
          litElems.push(words['OH'])
        case minutes < 20:
          litElems.push(words.minutes[minutes])
          break
        default:
          const remainder = minutes % 10
          const tenny = minutes - remainder
          litElems.push(words.minutes[tenny])
          if (remainder !== 0) {
            litElems.push(words.minutes[remainder])     
          }
      }
    
      lightWords(litElems)
    }
    
    
    これは、クエリに一致するすべての点灯アイテムを見つける[data-lit="true"] 設定してオフにしますdata-lit to false . 制御data-lit 属性は、私が特定の時間を示す方法です.
    その後、私は時間の時間と分を解析し、“it”、“is”と、時間に対応するセルの位置を使用したいセルの配列を開始します.
    分については、switch文でこれをしています.
  • それが0の場合、私は' oclock 'を点灯するために追加します.
  • それが10未満であるならば、私は「OH」を押します.
  • 20未満ならば、セルの位置を押しますminutes . Aがどうあるかに注意してくださいbreak 前の声明で?それは、数が10未満であるならば、「ああ」を示したかったです、そして、それ自体は20のケースでカバーされます.これはおそらく私がしたのは初めてです.
  • そうでなければ(20以上の数字)、0より大きい場合は- ty部分と残りを押します.
  • セルを点灯するには、コードコールlightWords コールlightWord これは、セルによって指定された範囲を繰り返しますrow からstart to end ).

    その他


    当サイトの利用について11ty それはJavaScriptの統合の多くを持っているので、かなり高速です.次のように構成されています:
    word-clock/
      _data/
        grid.js
        grid.txt
      _includes/
        css/
          main.njk
          main.css
          normalize.css
        js/
          main.js
          main.njk
        partials/
          head.njk
        index.njk
      .eleventy.js
      index.md
      css.md
      js.md
    
    
    前に述べた通り._data によってレンダリングされるグリッドを保持します_includes/index.njk . index.njk グリッドでWebページテンプレートを持ちます.私はサイトのhead インpartials/head.njk , これにはSEOの記述タグが含まれています.確かにSEOはそれより複雑です.また、私が使用した193のバージョンでメタジェネレータもあります.
    The css.md and js.md CSSファイルとJSファイルをCSSファイルとJSファイルに合わせることができます.彼らはより良いasset pipeline like Hugo’s または多分私はそれをよりよく使用する方法を学ぶ必要があります.行かなければならないAndy Bell’s Eleventy Course .
    私はJSを通り抜けました、しかし、CSSは何も特別です.があるnormalize.css 私のリセットとCSS私が宣言(簡潔に楕円).
    html {
        font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, 'Open Sans', 'Helvetica Neue', sans-serif;
        font-size: 100%;
        --bg: rgb(16, 16, 16);
        --fg: white;
        --dimed: rgb(200, 200, 200);
        --lit: orange;
    }
    
    .sr-only{...}
    
    a {color: orangered;}
    a:hover, a:active {color: orange; outline: 2px dashed white;}
    a:visited {color: goldenrod;}
    
    /* Clock Row */
    .row {
        display: flex;
        justify-content: center;
        font-family: monospace;
    }
    
    /* Clock Cell */
    .row > span {
        font-size: 1.25rem;
        padding: 0.75vmin 1vmin;
        font-weight: bold;
    }
    
    [data-lit=false] {
        color: var(--dimed)
    }
    
    [data-lit=true] {
        color: var(--lit);
    }
    
    
    CSS変数を使ったのは初めてです.これらはほとんどバックグラウンドとフォアグラウンドの色、およびリンクと州の色のためですdata-lit . The sr-only スクリーンリーダーのためだけにコンテンツを表示することですaccess-time 私は以前言及した.
    クロック行は、Flexboxを使用して物事を拡散し、各セルにはいくつかのパディングと太字のモノススペースのテキストがあります.面白いことに、私は何も指定せずにmax-width sなど.があるmargin: x auto 中心のものへのトリック、しかし、それはサイトを反応させることに関する私の仕事の範囲です.
    最後のことは、いくつかの時点で私はアプリを使用してplay.js このウェブサイトを運営して、それは働いた.このトリックは、第11パッケージにフックし、サイトに自分自身を提供することです.私は、私が行動であなたにそれを示すことができたことを願います、しかし、何かは、それがもう働かないという意味で、193のバージョンを賭けました.私が持っているのは、この写真を示すものですpackage.json ファイルは、193のサーバーログとWebページは、すべて私のiPhone 7プラスに.

    アプリ自体が行くには長い方法があります(依存性の解像度はかなり最近であり、gitの操作はかなり弱いです)、私はそのプレーを望んでいる.JSチームはアプリを改善し続けます.

    結論と次は何か


    すべての私の仕事で、ここで単語クロックのようになります:

    そして、それは私がイブニングイッシュで単語クロックを作った方法です.興味深いことに、私がどのように単語クロックを作ったかについて書くことは、私が以前気づいていなかったバグを見つけるのを助けました.もっと頻繁にやるべきだ.
    次に何をしたいのか、いくつかあります.このサイトをきれいにして、若干のアニメーションをここで、そして、そこに含むように、それは痛みません.また、追加のロケールや言語をサポートするためだけでなく、グリッドジェネレータを作るためには、時間を動的にアルゴリズムを伝えるようにするのはいいでしょう.
    あなたは見つけることができますWork Clock オンラインとはsource code on GitHub .
    読書ありがとう!あなたがこのポストを楽しんだならば、あなたは私を支持することができます
  • このポストを共有する
  • になるPatron ,
  • どちらかにお金を送ってくださいPaypal , Ko-fi or Buy Me A Coffee or
  • 使用するドメインを取得するmy Namecheap affiliate link . あなたがそのリンクで買う何でも、私は核分裂を得ます.