initial commit
This commit is contained in:
		
						commit
						2995f40d62
					
				
							
								
								
									
										100
									
								
								cards.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										100
									
								
								cards.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,100 @@
 | 
			
		||||
function cardDB() {
 | 
			
		||||
  return {
 | 
			
		||||
    // Major arcana
 | 
			
		||||
    "the fool": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 1
 | 
			
		||||
    },
 | 
			
		||||
    "the magician": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 2
 | 
			
		||||
    },
 | 
			
		||||
    "the high priestess": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 3
 | 
			
		||||
    },
 | 
			
		||||
    "the empress": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 4
 | 
			
		||||
    },
 | 
			
		||||
    "the emperor": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 5
 | 
			
		||||
    },
 | 
			
		||||
    "the hierophant": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 6
 | 
			
		||||
    },
 | 
			
		||||
    "the lovers": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 7
 | 
			
		||||
    },
 | 
			
		||||
    "the chariot": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 8
 | 
			
		||||
    },
 | 
			
		||||
    "justice": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 9
 | 
			
		||||
    },
 | 
			
		||||
    "the hermit": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 10 
 | 
			
		||||
    },
 | 
			
		||||
    "wheel of fortune": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 11
 | 
			
		||||
    },
 | 
			
		||||
    "strength": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 12
 | 
			
		||||
    },
 | 
			
		||||
    "death": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 13
 | 
			
		||||
    },
 | 
			
		||||
    "temperance": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 14
 | 
			
		||||
    },
 | 
			
		||||
    "the devil": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 15
 | 
			
		||||
    },
 | 
			
		||||
    "the tower": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 16
 | 
			
		||||
    },
 | 
			
		||||
    "the star": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 17
 | 
			
		||||
    },
 | 
			
		||||
    "the moon": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 18
 | 
			
		||||
    },
 | 
			
		||||
    "the sun": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 19
 | 
			
		||||
    },
 | 
			
		||||
    "judgement": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 20 
 | 
			
		||||
    },
 | 
			
		||||
    "the world": {
 | 
			
		||||
      "arcana": "major",
 | 
			
		||||
      "index": 21 
 | 
			
		||||
    },
 | 
			
		||||
 | 
			
		||||
    // Minor arcana
 | 
			
		||||
    "ace of cups": {
 | 
			
		||||
      "arcana": "minor",
 | 
			
		||||
      "index": 1,
 | 
			
		||||
      "suit": "cups"
 | 
			
		||||
    },
 | 
			
		||||
 | 
			
		||||
    // TODO
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export default cardDB;
 | 
			
		||||
							
								
								
									
										32
									
								
								index.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										32
									
								
								index.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,32 @@
 | 
			
		||||
<html>
 | 
			
		||||
  <head>
 | 
			
		||||
    <title>tarot</title>
 | 
			
		||||
<style>
 | 
			
		||||
  body {
 | 
			
		||||
    background-color: black;
 | 
			
		||||
    color: white;
 | 
			
		||||
  }
 | 
			
		||||
</style>
 | 
			
		||||
  </head>
 | 
			
		||||
  <body>
 | 
			
		||||
    <h1>hermetic</h1>
 | 
			
		||||
 | 
			
		||||
    <button id="reset">reset</button>
 | 
			
		||||
    <br>
 | 
			
		||||
    <div id="deck"></div>
 | 
			
		||||
    <div id="info" style="height: 325px; width: 500px;"></div>
 | 
			
		||||
    <div id="table"></div>
 | 
			
		||||
 | 
			
		||||
    <div class="blueprint card">
 | 
			
		||||
      <pre></pre>
 | 
			
		||||
      <span></span>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <script type="module" src="main.js"></script>
 | 
			
		||||
    <style>
 | 
			
		||||
      .blueprint {
 | 
			
		||||
        display: none;
 | 
			
		||||
      }
 | 
			
		||||
    </style>
 | 
			
		||||
  </body>
 | 
			
		||||
</html>
 | 
			
		||||
							
								
								
									
										4
									
								
								main.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								main.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,4 @@
 | 
			
		||||
import Tarot from './tarot.js'
 | 
			
		||||
 | 
			
		||||
window.tarot = new Tarot();
 | 
			
		||||
window.tarot.render();
 | 
			
		||||
							
								
								
									
										171
									
								
								tarot.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										171
									
								
								tarot.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,171 @@
 | 
			
		||||
import cardDB from './cards.js';
 | 
			
		||||
 | 
			
		||||
// TODO reset state button
 | 
			
		||||
 | 
			
		||||
class Tarot {
 | 
			
		||||
  constructor() {
 | 
			
		||||
    this.cardDB = cardDB();
 | 
			
		||||
    this.deck = new CardPile();
 | 
			
		||||
    for (const cardName in this.cardDB) {
 | 
			
		||||
      this.deck.add(cardName);
 | 
			
		||||
    }
 | 
			
		||||
    this.table = new CardPile();
 | 
			
		||||
 | 
			
		||||
    const deckElem = document.querySelector("#deck");
 | 
			
		||||
    const tableElem = document.querySelector("#table");
 | 
			
		||||
    const infoElem = document.querySelector("#info");
 | 
			
		||||
    const resetElem = document.querySelector("#reset");
 | 
			
		||||
 | 
			
		||||
    // TODO bring those top level functions in as methods
 | 
			
		||||
    this.renderers = [
 | 
			
		||||
      new Renderer(
 | 
			
		||||
        deckElem,
 | 
			
		||||
        deckRender(this.deck)),
 | 
			
		||||
 | 
			
		||||
      new Renderer(
 | 
			
		||||
        tableElem,
 | 
			
		||||
        tableRender(this, this.table)),
 | 
			
		||||
      
 | 
			
		||||
      new Renderer(
 | 
			
		||||
        infoElem,
 | 
			
		||||
        infoRender(tableElem, deckElem))
 | 
			
		||||
    ];
 | 
			
		||||
 | 
			
		||||
    // handlers
 | 
			
		||||
    // TODO make it feel similar to the renderers? or just have a general way to list out events
 | 
			
		||||
    // that should trigger a render
 | 
			
		||||
    tableElem.addEventListener("mouseenter", this.render.bind(this));
 | 
			
		||||
    tableElem.addEventListener("mouseleave", this.render.bind(this));
 | 
			
		||||
    deckElem.addEventListener("click", this.drawCard.bind(this));
 | 
			
		||||
    resetElem.addEventListener("click", this.reset.bind(this));
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  reset() {
 | 
			
		||||
    let card = this.table.drawRandom();
 | 
			
		||||
    while (card != null) {
 | 
			
		||||
      this.deck.add(card);
 | 
			
		||||
      card = this.table.drawRandom();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    this.render();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  drawCard() {
 | 
			
		||||
    let cardName = this.deck.drawRandom();
 | 
			
		||||
    if (cardName === null) {
 | 
			
		||||
      this.render();
 | 
			
		||||
      return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    this.table.add(cardName);
 | 
			
		||||
    this.render();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  render() {
 | 
			
		||||
    for (const renderer of this.renderers) {
 | 
			
		||||
      renderer.render();
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function infoRender(tableElem) {
 | 
			
		||||
  return function(elem) {
 | 
			
		||||
    const cardElem = tableElem.querySelector(".card:hover");
 | 
			
		||||
    if (cardElem == null) {
 | 
			
		||||
      elem.innerHTML = "";
 | 
			
		||||
      return
 | 
			
		||||
    }
 | 
			
		||||
    elem.innerHTML = cardElem.querySelector("span").innerHTML;
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function tableRender(tarot, table) {
 | 
			
		||||
  return function(elem) {
 | 
			
		||||
    const cardsOut = elem.querySelectorAll('.card');
 | 
			
		||||
    for (let cardElem of cardsOut) {
 | 
			
		||||
      if (!table.has(cardElem.getAttribute('data-cardName'))) {
 | 
			
		||||
        cardElem.remove();
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    for (let cardName of table.cards) {
 | 
			
		||||
      const found = elem.querySelector(`[data-cardName="${cardName}"]`);
 | 
			
		||||
      if (found != null) {
 | 
			
		||||
        continue;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      let bp = document.querySelector(".card.blueprint");
 | 
			
		||||
      let cardElem = bp.cloneNode(true);
 | 
			
		||||
      cardElem.classList.remove("blueprint");
 | 
			
		||||
      cardElem.setAttribute("data-cardName", cardName)
 | 
			
		||||
      cardElem.setAttribute("style", "float:left; width: 150px; height: 250px; border: 1px solid pink;");
 | 
			
		||||
      cardElem.querySelector("span").innerHTML = cardName;
 | 
			
		||||
      cardElem.addEventListener("mouseenter", tarot.render.bind(tarot));
 | 
			
		||||
      elem.append(cardElem);
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function deckRender(deck) {
 | 
			
		||||
  return function(elem) {
 | 
			
		||||
    const width = deck.size;
 | 
			
		||||
    elem.setAttribute("style", `float:left; height: 250px; width: 150px; border-left: 1px solid white; border-top: 1px solid white; border-bottom: ${width}px solid white; border-right: ${width}px solid white`);
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function deckClick(deckElem, deck) {
 | 
			
		||||
  return function() {
 | 
			
		||||
    console.log(deckElem, deck);
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class Renderer {
 | 
			
		||||
  constructor(element, renderFn) {
 | 
			
		||||
    this.element = element;
 | 
			
		||||
    this.renderFn = renderFn;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  render() {
 | 
			
		||||
    this.renderFn(this.element);
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class CardPile {
 | 
			
		||||
  constructor() {
 | 
			
		||||
    this.cards = new Set();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  add(cardName) {
 | 
			
		||||
    this.cards.add(cardName);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  has(cardName) {
 | 
			
		||||
    return this.cards.has(cardName);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  get size() {
 | 
			
		||||
    return this.cards.size;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  drawRandom() {
 | 
			
		||||
    const size = this.cards.size
 | 
			
		||||
    if (size === 0) {
 | 
			
		||||
      return null;
 | 
			
		||||
    }
 | 
			
		||||
    const index = Math.floor(Math.random() * Math.floor(size));
 | 
			
		||||
    let i = 0;
 | 
			
		||||
    let cardName = "";
 | 
			
		||||
    for (let card of this.cards) {
 | 
			
		||||
      if (i === index) {
 | 
			
		||||
        cardName = card;
 | 
			
		||||
        break
 | 
			
		||||
      }
 | 
			
		||||
      i++;
 | 
			
		||||
    }
 | 
			
		||||
    this.cards.delete(cardName);
 | 
			
		||||
 | 
			
		||||
    return cardName;
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export default Tarot;
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user