Added old files
This commit is contained in:
parent
9ae92803ce
commit
ef3620f4f9
86 changed files with 2157 additions and 0 deletions
122
sources/scripts/board.js
Normal file
122
sources/scripts/board.js
Normal file
|
|
@ -0,0 +1,122 @@
|
|||
'use strict'
|
||||
|
||||
function Board (element) {
|
||||
this.element = element
|
||||
this.room = []
|
||||
|
||||
this.enter_room = function (starting_hand = null) {
|
||||
this.remove_cards()
|
||||
|
||||
if (donsol.deck.cards.length > 0) {
|
||||
this.add_card(0, donsol.deck.draw_card(starting_hand ? DIAMOND : null))
|
||||
setTimeout(() => {
|
||||
this.room[0].element.style.opacity = 1
|
||||
this.room[0].element.style.top = 0
|
||||
donsol.speaker.play_effect('click2')
|
||||
}, 100)
|
||||
}
|
||||
if (donsol.deck.cards.length > 0) {
|
||||
this.add_card(1, donsol.deck.draw_card(starting_hand ? CLOVE : null))
|
||||
setTimeout(() => {
|
||||
this.room[1].element.style.opacity = 1
|
||||
this.room[1].element.style.top = 0
|
||||
donsol.speaker.play_effect('click2')
|
||||
}, 150)
|
||||
}
|
||||
if (donsol.deck.cards.length > 0) {
|
||||
this.add_card(2, donsol.deck.draw_card(starting_hand ? HEART : null))
|
||||
setTimeout(() => {
|
||||
this.room[2].element.style.opacity = 1
|
||||
this.room[2].element.style.top = 0
|
||||
donsol.speaker.play_effect('click2')
|
||||
}, 200)
|
||||
}
|
||||
if (donsol.deck.cards.length > 0) {
|
||||
this.add_card(3, donsol.deck.draw_card(starting_hand ? SPADE : null))
|
||||
setTimeout(() => {
|
||||
this.room[3].element.style.opacity = 1
|
||||
this.room[3].element.style.top = 0
|
||||
donsol.speaker.play_effect('click2')
|
||||
}, 250)
|
||||
}
|
||||
|
||||
donsol.player.update()
|
||||
this.update()
|
||||
}
|
||||
|
||||
this.add_card = function (index, card) {
|
||||
this.element.appendChild(card.install())
|
||||
this.room.push(card)
|
||||
}
|
||||
|
||||
this.remove_cards = function () {
|
||||
this.room = []
|
||||
this.element.innerHTML = ''
|
||||
}
|
||||
|
||||
this.return_cards = function () {
|
||||
if (!this.room[0].is_flipped) { donsol.deck.return_card(this.room[0]) }
|
||||
if (!this.room[1].is_flipped) { donsol.deck.return_card(this.room[1]) }
|
||||
if (!this.room[2].is_flipped) { donsol.deck.return_card(this.room[2]) }
|
||||
if (!this.room[3].is_flipped) { donsol.deck.return_card(this.room[3]) }
|
||||
}
|
||||
|
||||
this.update = function () {
|
||||
// Don't draw if the player is dead
|
||||
if (donsol.player.health.value < 1) {
|
||||
return
|
||||
}
|
||||
|
||||
if (donsol.player.experience.value === donsol.player.experience.limit) {
|
||||
this.dungeon_complete()
|
||||
return
|
||||
}
|
||||
if (this.room[0].is_flipped && this.room[1].is_flipped && this.room[2].is_flipped && this.room[3].is_flipped) {
|
||||
setTimeout(function () { donsol.board.is_complete() }, 250)
|
||||
}
|
||||
}
|
||||
|
||||
// Checks
|
||||
|
||||
this.is_complete = function () {
|
||||
donsol.player.has_escaped = false
|
||||
this.enter_room()
|
||||
}
|
||||
|
||||
this.is_started = function () {
|
||||
return this.cards_flipped().length > 0
|
||||
}
|
||||
|
||||
this.has_monsters = function () {
|
||||
return this.cards_monsters().length > 0
|
||||
}
|
||||
|
||||
this.cards_flipped = function () {
|
||||
const a = []
|
||||
if (this.room[0] && this.room[0].is_flipped) { a.push(this.room[0]) }
|
||||
if (this.room[1] && this.room[1].is_flipped) { a.push(this.room[1]) }
|
||||
if (this.room[2] && this.room[2].is_flipped) { a.push(this.room[2]) }
|
||||
if (this.room[3] && this.room[3].is_flipped) { a.push(this.room[3]) }
|
||||
return a
|
||||
}
|
||||
|
||||
this.cards_monsters = function () {
|
||||
const a = []
|
||||
if (this.room[0] && this.room[0].constructor.name == 'Card_Monster' && this.room[0].is_flipped === false) { a.push(this.room[0]) }
|
||||
if (this.room[1] && this.room[1].constructor.name == 'Card_Monster' && this.room[1].is_flipped === false) { a.push(this.room[1]) }
|
||||
if (this.room[2] && this.room[2].constructor.name == 'Card_Monster' && this.room[2].is_flipped === false) { a.push(this.room[2]) }
|
||||
if (this.room[3] && this.room[3].constructor.name == 'Card_Monster' && this.room[3].is_flipped === false) { a.push(this.room[3]) }
|
||||
return a
|
||||
}
|
||||
|
||||
this.dungeon_complete = function () {
|
||||
donsol.is_complete = true
|
||||
donsol.player.escape_button.innerHTML = 'Restart'
|
||||
donsol.player.element.setAttribute('class', 'done')
|
||||
donsol.timeline.add_event('Completed dungeon!')
|
||||
}
|
||||
|
||||
this.dungeon_failed = function () {
|
||||
|
||||
}
|
||||
}
|
||||
69
sources/scripts/card.js
Normal file
69
sources/scripts/card.js
Normal file
|
|
@ -0,0 +1,69 @@
|
|||
'use strict'
|
||||
|
||||
function Card (sym, value, type, name = 'Unknown') {
|
||||
this.symbol = sym
|
||||
this.value = value
|
||||
this.type = type
|
||||
this.name = name
|
||||
|
||||
this.element = null
|
||||
this.is_flipped = false
|
||||
|
||||
this.install = function () {
|
||||
const e = document.createElement('card')
|
||||
e.setAttribute('class', this.type + ' card_' + this.value)
|
||||
|
||||
// Face
|
||||
const face = document.createElement('div')
|
||||
face.setAttribute('class', 'face')
|
||||
e.appendChild(face)
|
||||
|
||||
// Value
|
||||
const value = document.createElement('span')
|
||||
value.setAttribute('class', 'value')
|
||||
value.innerHTML = this.symbol
|
||||
face.appendChild(value)
|
||||
|
||||
const graphic = document.createElement('div')
|
||||
graphic.className = 'graphic'
|
||||
graphic.innerHTML = require('fs').readFileSync(`${__dirname}/media/${this.type}/${this.value}.svg`)
|
||||
face.appendChild(graphic)
|
||||
|
||||
// Name
|
||||
const name_element = document.createElement('span')
|
||||
name_element.setAttribute('class', 'name')
|
||||
name_element.innerHTML = this.name + ' ' + this.value
|
||||
face.appendChild(name_element)
|
||||
|
||||
// Icon
|
||||
face.appendChild(new Icon(this.type).install())
|
||||
|
||||
addClickHandler(e, this, this.value)
|
||||
|
||||
this.element = e
|
||||
|
||||
return e
|
||||
}
|
||||
|
||||
function addClickHandler (elem, object) {
|
||||
elem.addEventListener('click', function (e) { object.touch() }, false)
|
||||
}
|
||||
|
||||
this.touch = function () {
|
||||
console.log('??')
|
||||
}
|
||||
|
||||
this.flip = function () {
|
||||
donsol.speaker.play_effect('flip')
|
||||
|
||||
this.is_flipped = true
|
||||
donsol.player.experience.value += 1
|
||||
donsol.player.experience.update()
|
||||
|
||||
this.element.style.opacity = '0'
|
||||
this.element.style.top = '-5px'
|
||||
donsol.speaker.play_effect('click2')
|
||||
|
||||
donsol.player.update()
|
||||
}
|
||||
}
|
||||
13
sources/scripts/card.monster.js
Normal file
13
sources/scripts/card.monster.js
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
'use strict'
|
||||
|
||||
function Card_Monster (sym, value, type, name = 'Unknown') {
|
||||
Card.call(this, sym, value, type, name)
|
||||
|
||||
this.touch = function () {
|
||||
if (this.is_flipped) { console.log('Card is already flipped'); return }
|
||||
if (donsol.player.health.value < 1) { console.log('Player is dead'); return }
|
||||
this.flip()
|
||||
donsol.player.attack(this)
|
||||
donsol.board.update()
|
||||
}
|
||||
}
|
||||
13
sources/scripts/card.potion.js
Normal file
13
sources/scripts/card.potion.js
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
'use strict'
|
||||
|
||||
function Card_Potion (sym, value, type, name = 'Unknown') {
|
||||
Card.call(this, sym, value, type, name)
|
||||
|
||||
this.touch = function () {
|
||||
if (this.is_flipped) { console.log('Card is already flipped'); return }
|
||||
if (donsol.player.health.value < 1) { console.log('Player is dead'); return }
|
||||
this.flip()
|
||||
donsol.player.drink_potion(this.value)
|
||||
donsol.board.update()
|
||||
}
|
||||
}
|
||||
13
sources/scripts/card.shield.js
Normal file
13
sources/scripts/card.shield.js
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
'use strict'
|
||||
|
||||
function Card_Shield (sym, value, type, name = 'Unknown') {
|
||||
Card.call(this, sym, value, type, name)
|
||||
|
||||
this.touch = function () {
|
||||
if (this.is_flipped == true) { console.log('Card is already flipped'); return }
|
||||
if (donsol.player.health.value < 1) { console.log('Player is dead'); return }
|
||||
this.flip()
|
||||
donsol.player.equip_shield(this.value)
|
||||
donsol.board.update()
|
||||
}
|
||||
}
|
||||
103
sources/scripts/deck.js
Normal file
103
sources/scripts/deck.js
Normal file
|
|
@ -0,0 +1,103 @@
|
|||
'use strict'
|
||||
|
||||
function Deck () {
|
||||
this.cards = [
|
||||
new Card_Potion('A', 11, HEART, 'White Mage'),
|
||||
new Card_Potion('2', 2, HEART, 'Small Potion'),
|
||||
new Card_Potion('3', 3, HEART, 'Small Potion'),
|
||||
new Card_Potion('4', 4, HEART, 'Medium Potion'),
|
||||
new Card_Potion('5', 5, HEART, 'Medium Potion'),
|
||||
new Card_Potion('6', 6, HEART, 'Medium Potion'),
|
||||
new Card_Potion('7', 7, HEART, 'Medium Potion'),
|
||||
new Card_Potion('8', 8, HEART, 'Medium Potion'),
|
||||
new Card_Potion('9', 9, HEART, 'Large Potion'),
|
||||
new Card_Potion('10', 10, HEART, 'Large Potion'),
|
||||
new Card_Potion('V', 11, HEART, 'White Mage'),
|
||||
new Card_Potion('Q', 11, HEART, 'White Mage'),
|
||||
new Card_Potion('K', 11, HEART, 'White Mage'),
|
||||
new Card_Shield('A', 11, DIAMOND, 'Red Mage'),
|
||||
new Card_Shield('2', 2, DIAMOND, 'Buckler'),
|
||||
new Card_Shield('3', 3, DIAMOND, 'Buckler'),
|
||||
new Card_Shield('4', 4, DIAMOND, 'Shield'),
|
||||
new Card_Shield('5', 5, DIAMOND, 'Shield'),
|
||||
new Card_Shield('6', 6, DIAMOND, 'Shield'),
|
||||
new Card_Shield('7', 7, DIAMOND, 'Shield'),
|
||||
new Card_Shield('8', 8, DIAMOND, 'Shield'),
|
||||
new Card_Shield('9', 9, DIAMOND, 'Large Shield'),
|
||||
new Card_Shield('10', 10, DIAMOND, 'Large Shield'),
|
||||
new Card_Shield('V', 11, DIAMOND, 'Red Mage'),
|
||||
new Card_Shield('Q', 11, DIAMOND, 'Red Mage'),
|
||||
new Card_Shield('K', 11, DIAMOND, 'Red Mage'),
|
||||
new Card_Monster('A', 17, CLOVE, 'Empress'),
|
||||
new Card_Monster('2', 2, CLOVE, 'Rat'),
|
||||
new Card_Monster('3', 3, CLOVE, 'Bat'),
|
||||
new Card_Monster('4', 4, CLOVE, 'Imp'),
|
||||
new Card_Monster('5', 5, CLOVE, 'Goblin'),
|
||||
new Card_Monster('6', 6, CLOVE, 'Orc'),
|
||||
new Card_Monster('7', 7, CLOVE, 'Ogre'),
|
||||
new Card_Monster('8', 8, CLOVE, 'Beholder'),
|
||||
new Card_Monster('9', 9, CLOVE, 'Medusa'),
|
||||
new Card_Monster('10', 10, CLOVE, 'Demon'),
|
||||
new Card_Monster('V', 11, CLOVE, 'Consort'),
|
||||
new Card_Monster('Q', 13, CLOVE, 'Queen'),
|
||||
new Card_Monster('K', 15, CLOVE, 'Regnant'),
|
||||
new Card_Monster('A', 17, SPADE, 'Empress'),
|
||||
new Card_Monster('2', 2, SPADE, 'Slime'),
|
||||
new Card_Monster('3', 3, SPADE, 'Tunneler'),
|
||||
new Card_Monster('4', 4, SPADE, 'Fiend'),
|
||||
new Card_Monster('5', 5, SPADE, 'Drake'),
|
||||
new Card_Monster('6', 6, SPADE, 'Specter'),
|
||||
new Card_Monster('7', 7, SPADE, 'Ghost'),
|
||||
new Card_Monster('8', 8, SPADE, 'Elemental'),
|
||||
new Card_Monster('9', 9, SPADE, 'Witch'),
|
||||
new Card_Monster('10', 10, SPADE, 'Familiar'),
|
||||
new Card_Monster('V', 11, SPADE, 'Consort'),
|
||||
new Card_Monster('Q', 13, SPADE, 'Queen'),
|
||||
new Card_Monster('K', 15, SPADE, 'Regnant'),
|
||||
new Card_Monster('J', 21, JOKER, 'First Donsol'),
|
||||
new Card_Monster('J', 21, JOKER, 'Second Donsol')
|
||||
]
|
||||
|
||||
let draw_pile = []
|
||||
|
||||
this.start = function () {
|
||||
draw_pile = this.cards
|
||||
donsol.timeline.add_event(`Entered Donsol, at <b>${donsol.get_difficulty()}</b> difficulty.`)
|
||||
}
|
||||
|
||||
this.shuffle = function () {
|
||||
draw_pile = shuffle(this.cards)
|
||||
donsol.timeline.add_event(`Entered Donsol, at <b>${donsol.get_difficulty()}</b> difficulty.`)
|
||||
}
|
||||
|
||||
this.draw_card = function (type) {
|
||||
let i = 0
|
||||
switch (type) {
|
||||
case HEART:
|
||||
i = Math.floor((Math.random() * 10) + 0); break
|
||||
case DIAMOND:
|
||||
i = Math.floor((Math.random() * 10) + 13); break
|
||||
case CLOVE:
|
||||
i = Math.floor((Math.random() * 10) + 25); break
|
||||
case SPADE:
|
||||
i = Math.floor((Math.random() * 10) + 36); break
|
||||
}
|
||||
|
||||
return draw_pile.splice(i, 1)[0]
|
||||
}
|
||||
|
||||
this.return_card = function (card) {
|
||||
draw_pile.push(card)
|
||||
draw_pile = shuffle(draw_pile)
|
||||
}
|
||||
|
||||
function shuffle (array) {
|
||||
for (let i = array.length - 1; i > 0; i--) {
|
||||
const j = Math.floor(Math.random() * (i + 1))
|
||||
const temp = array[i]
|
||||
array[i] = array[j]
|
||||
array[j] = temp
|
||||
}
|
||||
return array
|
||||
}
|
||||
}
|
||||
91
sources/scripts/donsol.js
Normal file
91
sources/scripts/donsol.js
Normal file
|
|
@ -0,0 +1,91 @@
|
|||
'use strict'
|
||||
|
||||
const HEART = 'heart'
|
||||
const DIAMOND = 'diamond'
|
||||
const CLOVE = 'clove'
|
||||
const SPADE = 'spade'
|
||||
const JOKER = 'joker'
|
||||
|
||||
function Donsol () {
|
||||
const defaultTheme = {
|
||||
background: '#000000',
|
||||
f_high: '#000000',
|
||||
f_med: '#a93232',
|
||||
f_low: '#aaaaaa',
|
||||
f_inv: '#ffffff',
|
||||
b_high: '#ffffff',
|
||||
b_med: '#cccccc',
|
||||
b_low: '#333333',
|
||||
b_inv: '#a93232'
|
||||
}
|
||||
|
||||
this.theme = new Theme(defaultTheme)
|
||||
|
||||
this.deck = new Deck()
|
||||
this.board = new Board()
|
||||
this.player = new Player()
|
||||
this.timeline = new Timeline()
|
||||
this.controller = new Controller()
|
||||
this.speaker = new Speaker()
|
||||
this.walkthrough = new Walkthrough()
|
||||
|
||||
this.is_complete = false
|
||||
this.difficulty = 1
|
||||
|
||||
this.install = function (host = document.body) {
|
||||
this.theme.install(host)
|
||||
}
|
||||
|
||||
this.start = function () {
|
||||
donsol.board.element = document.getElementById('board')
|
||||
donsol.player.element = document.getElementById('player')
|
||||
|
||||
this.theme.start()
|
||||
this.deck.start()
|
||||
this.player.install()
|
||||
donsol.timeline.install(donsol.player.element)
|
||||
this.player.start()
|
||||
|
||||
this.board.enter_room(true)
|
||||
donsol.deck.shuffle()
|
||||
|
||||
this.update()
|
||||
}
|
||||
|
||||
this.new_game = function () {
|
||||
this.deck = new Deck()
|
||||
this.deck.start()
|
||||
|
||||
this.player.start()
|
||||
this.board.enter_room(true)
|
||||
donsol.deck.shuffle()
|
||||
|
||||
this.update()
|
||||
}
|
||||
|
||||
this.toggle_difficulty = function () {
|
||||
this.difficulty = this.difficulty < 3 ? this.difficulty + 1 : 0
|
||||
donsol.new_game()
|
||||
}
|
||||
|
||||
this.set_difficulty = function (id) {
|
||||
this.difficulty = id
|
||||
donsol.new_game()
|
||||
}
|
||||
|
||||
this.get_difficulty = function () {
|
||||
return this.difficulty == 3 ? 'Expert' : this.difficulty == 2 ? 'Hard' : this.difficulty == 1 ? 'Normal' : 'Easy'
|
||||
}
|
||||
|
||||
this.update = function () {
|
||||
console.log('Difficulty', this.get_difficulty())
|
||||
}
|
||||
|
||||
this.skip = function () {
|
||||
if (donsol.player.experience.value < 1) {
|
||||
donsol.new_game()
|
||||
} else {
|
||||
donsol.player.escape_room()
|
||||
}
|
||||
}
|
||||
}
|
||||
15
sources/scripts/gage.health.js
Normal file
15
sources/scripts/gage.health.js
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
'use strict'
|
||||
|
||||
function Gage_Health (name, limit, color) {
|
||||
Gage.call(this, name, limit, color)
|
||||
|
||||
this.update = function () {
|
||||
this.progress.update(this.value, this.limit)
|
||||
|
||||
if (donsol.player.can_drink === false) {
|
||||
this.value_element.innerHTML = `<span>${this.value}</span> <span class='unit'>HP</span>`
|
||||
} else {
|
||||
this.value_element.innerHTML = `${this.value} <span class='unit'>HP</span>`
|
||||
}
|
||||
}
|
||||
}
|
||||
66
sources/scripts/gage.js
Normal file
66
sources/scripts/gage.js
Normal file
|
|
@ -0,0 +1,66 @@
|
|||
'use strict'
|
||||
|
||||
function Gage (name, limit, color) {
|
||||
this.name = name
|
||||
this.color = color
|
||||
this.limit = limit
|
||||
this.value = limit
|
||||
this.value_element = null
|
||||
this.event_element = null
|
||||
this.element = document.createElement('div')
|
||||
this.progress = new Progress(15, color)
|
||||
|
||||
this.show_limit = true
|
||||
this.units = ''
|
||||
|
||||
this.start = function () {
|
||||
this.install()
|
||||
}
|
||||
|
||||
this.install = function () {
|
||||
this.element.setAttribute('class', 'gage ' + this.name.toLowerCase())
|
||||
|
||||
this.value_element = document.createElement('span')
|
||||
this.value_element.setAttribute('class', 'value')
|
||||
this.value_element.innerHTML = this.value + '(' + this.limit + ')'
|
||||
this.element.appendChild(this.value_element)
|
||||
|
||||
this.event_element = document.createElement('span')
|
||||
this.event_element.setAttribute('class', 'event')
|
||||
this.element.appendChild(this.event_element)
|
||||
|
||||
this.element.appendChild(this.progress.install())
|
||||
|
||||
return this.element
|
||||
}
|
||||
|
||||
this.update = function (value) {
|
||||
this.value = typeof value === 'number' ? value : this.value
|
||||
if (this.value > this.limit) { this.value = this.limit }
|
||||
if (this.value < 0) { this.value = 0 }
|
||||
|
||||
this.progress.update(this.value, this.limit)
|
||||
|
||||
if (this.name == 'Shield' && this.value == 0) {
|
||||
this.value_element.innerHTML = "0<span class='unit'>DP</span>"
|
||||
} else if (this.name == 'Shield' && this.limit == 25) {
|
||||
this.value_element.innerHTML = this.value + "<span class='unit'>DP</span>"
|
||||
} else {
|
||||
this.value_element.innerHTML = this.show_limit ? this.value + ' < ' + this.limit + "<span class='unit'>" + this.units + '</span>' : this.value + " <span class='unit'>" + this.units + '</span>'
|
||||
}
|
||||
}
|
||||
|
||||
this.add_event = function (value) {
|
||||
this.event_element.innerHTML = "<span class='name'>" + value + '</span>'
|
||||
this.event_element.style.marginTop = '5px'
|
||||
this.event_element.style.opacity = '0'
|
||||
setTimeout(() => {
|
||||
this.event_element.style.marginTop = '0px'
|
||||
this.event_element.style.opacity = 1
|
||||
}, 250)
|
||||
}
|
||||
|
||||
this.clear_event = function () {
|
||||
this.event_element.innerHTML = ''
|
||||
}
|
||||
}
|
||||
29
sources/scripts/gage.progress.js
Normal file
29
sources/scripts/gage.progress.js
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
'use strict'
|
||||
|
||||
function Progress (radius = 15) {
|
||||
this.wrapper = null
|
||||
this.progress_bar = null
|
||||
|
||||
this.install = function () {
|
||||
this.wrapper = document.createElement('div')
|
||||
this.wrapper.setAttribute('class', 'progress')
|
||||
|
||||
this.progress_bar = document.createElement('div')
|
||||
this.progress_bar.setAttribute('class', 'bar')
|
||||
|
||||
this.wrapper.appendChild(this.progress_bar)
|
||||
|
||||
return this.wrapper
|
||||
}
|
||||
|
||||
this.update = function (value, limit = 0) {
|
||||
if (limit === 0) { value = 0; limit = 1 }
|
||||
const min = 0
|
||||
const max = 130
|
||||
const pixels = Math.floor(((value / limit) * max) + min)
|
||||
const ratio = (value / limit)
|
||||
const perc = ratio * 100
|
||||
|
||||
this.progress_bar.style.width = `${perc}%`
|
||||
}
|
||||
}
|
||||
25
sources/scripts/gage.shield.js
Normal file
25
sources/scripts/gage.shield.js
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
'use strict'
|
||||
|
||||
function Gage_Shield (name, limit, color) {
|
||||
Gage.call(this, name, limit, color)
|
||||
|
||||
this.break_limit = null
|
||||
|
||||
this.update = function () {
|
||||
if (this.is_damaged() === true) {
|
||||
this.value_element.innerHTML = `${this.break_limit - 1}/${this.value} <span class='unit'>DP</span>`
|
||||
this.progress.update(this.value < this.break_limit ? this.value : this.break_limit - 1, 11)
|
||||
} else if (this.value == 0) {
|
||||
this.value_element.innerHTML = "0 <span class='unit'>DP</span>"
|
||||
this.progress.update(0, 11)
|
||||
} else {
|
||||
this.value_element.innerHTML = '<span>' + this.value + "</span> <span class='unit'>DP</span>"
|
||||
this.progress.update(this.value, 11)
|
||||
}
|
||||
}
|
||||
|
||||
this.is_damaged = function () {
|
||||
if (this.break_limit === null) { return false }
|
||||
return true
|
||||
}
|
||||
}
|
||||
105
sources/scripts/icon.js
Normal file
105
sources/scripts/icon.js
Normal file
|
|
@ -0,0 +1,105 @@
|
|||
'use strict'
|
||||
|
||||
function Icon (type) {
|
||||
this.type = type
|
||||
|
||||
this.install = function () {
|
||||
switch (this.type) {
|
||||
case HEART:
|
||||
return this.heart()
|
||||
case DIAMOND:
|
||||
return this.diamond()
|
||||
case CLOVE:
|
||||
return this.clove()
|
||||
case SPADE:
|
||||
return this.spade()
|
||||
case JOKER:
|
||||
return this.joker()
|
||||
}
|
||||
}
|
||||
|
||||
this.heart = function () {
|
||||
const e = document.createElementNS('http://www.w3.org/2000/svg', 'svg')
|
||||
e.setAttribute('class', 'icon')
|
||||
|
||||
const s = document.createElementNS('http://www.w3.org/2000/svg', 'path')
|
||||
s.setAttribute('d', 'M0,15 a15,15 0 0,1 30,0 l-15,15 l-15,-15')
|
||||
s.setAttribute('class', 'fill_red')
|
||||
|
||||
e.appendChild(s)
|
||||
return e
|
||||
}
|
||||
|
||||
this.diamond = function () {
|
||||
const e = document.createElementNS('http://www.w3.org/2000/svg', 'svg')
|
||||
e.setAttribute('class', 'icon')
|
||||
|
||||
const s = document.createElementNS('http://www.w3.org/2000/svg', 'path')
|
||||
s.setAttribute('d', 'M15 0 L 30 15 L 15 30 L 0 15')
|
||||
s.setAttribute('class', 'fill_red')
|
||||
|
||||
e.appendChild(s)
|
||||
return e
|
||||
}
|
||||
|
||||
this.clove = function () {
|
||||
const e = document.createElementNS('http://www.w3.org/2000/svg', 'svg')
|
||||
e.setAttribute('class', 'icon')
|
||||
|
||||
const s = document.createElementNS('http://www.w3.org/2000/svg', 'circle')
|
||||
s.setAttribute('cx', '15px')
|
||||
s.setAttribute('cy', '6px')
|
||||
s.setAttribute('r', '5px')
|
||||
s.setAttribute('class', 'fill_black')
|
||||
e.appendChild(s)
|
||||
|
||||
const s2 = document.createElementNS('http://www.w3.org/2000/svg', 'circle')
|
||||
s2.setAttribute('cx', '24px')
|
||||
s2.setAttribute('cy', '15px')
|
||||
s2.setAttribute('r', '5px')
|
||||
s2.setAttribute('class', 'fill_black')
|
||||
e.appendChild(s2)
|
||||
|
||||
const s3 = document.createElementNS('http://www.w3.org/2000/svg', 'circle')
|
||||
s3.setAttribute('cx', '6px')
|
||||
s3.setAttribute('cy', '15px')
|
||||
s3.setAttribute('r', '5px')
|
||||
s3.setAttribute('class', 'fill_black')
|
||||
e.appendChild(s3)
|
||||
|
||||
const s4 = document.createElementNS('http://www.w3.org/2000/svg', 'circle')
|
||||
s4.setAttribute('cx', '15px')
|
||||
s4.setAttribute('cy', '24px')
|
||||
s4.setAttribute('r', '5px')
|
||||
s4.setAttribute('class', 'fill_black')
|
||||
e.appendChild(s4)
|
||||
|
||||
return e
|
||||
}
|
||||
|
||||
this.spade = function () {
|
||||
const e = document.createElementNS('http://www.w3.org/2000/svg', 'svg')
|
||||
e.setAttribute('class', 'icon')
|
||||
|
||||
const s = document.createElementNS('http://www.w3.org/2000/svg', 'path')
|
||||
s.setAttribute('d', 'M15,0 L0,15 a15,15 0 0,1 15,15 a15,15 0 0,1 15,-15')
|
||||
s.setAttribute('class', 'fill_black')
|
||||
|
||||
e.appendChild(s)
|
||||
return e
|
||||
}
|
||||
|
||||
this.joker = function () {
|
||||
const e = document.createElementNS('http://www.w3.org/2000/svg', 'svg')
|
||||
e.setAttribute('class', 'icon')
|
||||
|
||||
const s = document.createElementNS('http://www.w3.org/2000/svg', 'circle')
|
||||
s.setAttribute('cx', '15px')
|
||||
s.setAttribute('cy', '15px')
|
||||
s.setAttribute('r', '15px')
|
||||
s.setAttribute('class', 'fill_black')
|
||||
e.appendChild(s)
|
||||
|
||||
return e
|
||||
}
|
||||
}
|
||||
185
sources/scripts/lib/controller.js
Normal file
185
sources/scripts/lib/controller.js
Normal file
|
|
@ -0,0 +1,185 @@
|
|||
'use strict'
|
||||
|
||||
function Controller () {
|
||||
this.menu = { default: {} }
|
||||
this.mode = 'default'
|
||||
|
||||
this.app = require('electron').remote.app
|
||||
|
||||
this.start = function () {
|
||||
}
|
||||
|
||||
this.add = function (mode, cat, label, fn, accelerator) {
|
||||
if (!this.menu[mode]) { this.menu[mode] = {} }
|
||||
if (!this.menu[mode][cat]) { this.menu[mode][cat] = {} }
|
||||
this.menu[mode][cat][label] = { fn: fn, accelerator: accelerator }
|
||||
console.log(`${mode}/${cat}/${label} <${accelerator}>`)
|
||||
}
|
||||
|
||||
this.add_role = function (mode, cat, label) {
|
||||
if (!this.menu[mode]) { this.menu[mode] = {} }
|
||||
if (!this.menu[mode][cat]) { this.menu[mode][cat] = {} }
|
||||
this.menu[mode][cat][label] = { role: label }
|
||||
}
|
||||
|
||||
this.set = function (mode = 'default') {
|
||||
this.mode = mode
|
||||
this.commit()
|
||||
}
|
||||
|
||||
this.format = function () {
|
||||
const f = []
|
||||
const m = this.menu[this.mode]
|
||||
for (const cat in m) {
|
||||
const submenu = []
|
||||
for (name in m[cat]) {
|
||||
const option = m[cat][name]
|
||||
if (option.role) {
|
||||
submenu.push({ role: option.role })
|
||||
} else {
|
||||
submenu.push({ label: name, accelerator: option.accelerator, click: option.fn })
|
||||
}
|
||||
}
|
||||
f.push({ label: cat, submenu: submenu })
|
||||
}
|
||||
return f
|
||||
}
|
||||
|
||||
this.commit = function () {
|
||||
this.app.inject_menu(this.format())
|
||||
}
|
||||
|
||||
this.docs = function () {
|
||||
console.log('Generating docs..')
|
||||
const svg = this.generate_svg(this.format())
|
||||
const txt = this.documentation(this.format())
|
||||
dialog.showSaveDialog((fileName) => {
|
||||
if (fileName === undefined) { return }
|
||||
fileName = fileName.substr(-4, 4) != '.svg' ? fileName + '.svg' : fileName
|
||||
fs.writeFile(fileName, svg)
|
||||
fs.writeFile(fileName.replace('.svg', '.md'), txt)
|
||||
})
|
||||
}
|
||||
|
||||
this.generate_svg = function (m) {
|
||||
let svg_html = ''
|
||||
|
||||
for (id in this.layout) {
|
||||
const key = this.layout[id]
|
||||
const acc = this.accelerator_for_key(key.name, m)
|
||||
svg_html += `<rect x="${key.x + 1}" y="${key.y + 1}" width="${key.width - 2}" height="${key.height - 2}" rx="4" ry="4" title="${key.name}" stroke="#ccc" fill="none" stroke-width="1"/>`
|
||||
svg_html += `<rect x="${key.x + 3}" y="${key.y + 3}" width="${key.width - 6}" height="${key.height - 12}" rx="3" ry="3" title="${key.name}" stroke="${acc.basic ? '#000' : acc.ctrl ? '#ccc' : '#fff'}" fill="${acc.basic ? '#000' : acc.ctrl ? '#ccc' : '#fff'}" stroke-width="1"/>`
|
||||
svg_html += `<text x="${key.x + 10}" y="${key.y + 20}" font-size='11' font-family='Input Mono' stroke-width='0' fill='${acc.basic ? '#fff' : '#000'}'>${key.name.toUpperCase()}</text>`
|
||||
svg_html += acc && acc.basic ? `<text x="${key.x + 10}" y="${key.y + 35}" font-size='7' font-family='Input Mono' stroke-width='0' fill='#fff'>${acc.basic}</text>` : ''
|
||||
svg_html += acc && acc.ctrl ? `<text x="${key.x + 10}" y="${key.y + 45}" font-size='7' font-family='Input Mono' stroke-width='0' fill='#000'>${acc.ctrl}</text>` : ''
|
||||
}
|
||||
return `<?xml version="1.0" encoding="UTF-8" standalone="no"?><svg xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:cc="http://creativecommons.org/ns#" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" width="900" height="300" version="1.0" style="fill:none;stroke:black;stroke-width:2px;">${svg_html}</svg>`
|
||||
}
|
||||
|
||||
this.documentation = function () {
|
||||
let txt = ''
|
||||
|
||||
txt += this.documentation_for_mode('default', this.menu.default)
|
||||
|
||||
for (name in this.menu) {
|
||||
if (name == 'default') { continue }
|
||||
txt += this.documentation_for_mode(name, this.menu[name])
|
||||
}
|
||||
return txt
|
||||
}
|
||||
|
||||
this.documentation_for_mode = function (name, mode) {
|
||||
let txt = `## ${name} Mode\n\n`
|
||||
|
||||
for (id in mode) {
|
||||
if (id == '*') { continue }
|
||||
txt += `### ${id}\n`
|
||||
for (name in mode[id]) {
|
||||
const option = mode[id][name]
|
||||
txt += `- ${name}: \`${option.accelerator}\`\n`
|
||||
}
|
||||
txt += '\n'
|
||||
}
|
||||
|
||||
return txt + '\n'
|
||||
}
|
||||
|
||||
this.accelerator_for_key = function (key, menu) {
|
||||
const acc = { basic: null, ctrl: null }
|
||||
for (cat in menu) {
|
||||
const options = menu[cat]
|
||||
for (id in options.submenu) {
|
||||
const option = options.submenu[id]; if (option.role) { continue }
|
||||
acc.basic = (option.accelerator.toLowerCase() == key.toLowerCase()) ? option.label.toUpperCase().replace('TOGGLE ', '').substr(0, 8).trim() : acc.basic
|
||||
acc.ctrl = (option.accelerator.toLowerCase() == ('CmdOrCtrl+' + key).toLowerCase()) ? option.label.toUpperCase().replace('TOGGLE ', '').substr(0, 8).trim() : acc.ctrl
|
||||
}
|
||||
}
|
||||
return acc
|
||||
}
|
||||
|
||||
this.layout = [
|
||||
{ x: 0, y: 0, width: 60, height: 60, name: 'esc' },
|
||||
{ x: 60, y: 0, width: 60, height: 60, name: '1' },
|
||||
{ x: 120, y: 0, width: 60, height: 60, name: '2' },
|
||||
{ x: 180, y: 0, width: 60, height: 60, name: '3' },
|
||||
{ x: 240, y: 0, width: 60, height: 60, name: '4' },
|
||||
{ x: 300, y: 0, width: 60, height: 60, name: '5' },
|
||||
{ x: 360, y: 0, width: 60, height: 60, name: '6' },
|
||||
{ x: 420, y: 0, width: 60, height: 60, name: '7' },
|
||||
{ x: 480, y: 0, width: 60, height: 60, name: '8' },
|
||||
{ x: 540, y: 0, width: 60, height: 60, name: '9' },
|
||||
{ x: 600, y: 0, width: 60, height: 60, name: '0' },
|
||||
{ x: 660, y: 0, width: 60, height: 60, name: '-' },
|
||||
{ x: 720, y: 0, width: 60, height: 60, name: 'plus' },
|
||||
{ x: 780, y: 0, width: 120, height: 60, name: 'backspace' },
|
||||
{ x: 0, y: 60, width: 90, height: 60, name: 'tab' },
|
||||
{ x: 90, y: 60, width: 60, height: 60, name: 'q' },
|
||||
{ x: 150, y: 60, width: 60, height: 60, name: 'w' },
|
||||
{ x: 210, y: 60, width: 60, height: 60, name: 'e' },
|
||||
{ x: 270, y: 60, width: 60, height: 60, name: 'r' },
|
||||
{ x: 330, y: 60, width: 60, height: 60, name: 't' },
|
||||
{ x: 390, y: 60, width: 60, height: 60, name: 'y' },
|
||||
{ x: 450, y: 60, width: 60, height: 60, name: 'u' },
|
||||
{ x: 510, y: 60, width: 60, height: 60, name: 'i' },
|
||||
{ x: 570, y: 60, width: 60, height: 60, name: 'o' },
|
||||
{ x: 630, y: 60, width: 60, height: 60, name: 'p' },
|
||||
{ x: 690, y: 60, width: 60, height: 60, name: '[' },
|
||||
{ x: 750, y: 60, width: 60, height: 60, name: ']' },
|
||||
{ x: 810, y: 60, width: 90, height: 60, name: '|' },
|
||||
{ x: 0, y: 120, width: 105, height: 60, name: 'caps' },
|
||||
{ x: 105, y: 120, width: 60, height: 60, name: 'a' },
|
||||
{ x: 165, y: 120, width: 60, height: 60, name: 's' },
|
||||
{ x: 225, y: 120, width: 60, height: 60, name: 'd' },
|
||||
{ x: 285, y: 120, width: 60, height: 60, name: 'f' },
|
||||
{ x: 345, y: 120, width: 60, height: 60, name: 'g' },
|
||||
{ x: 405, y: 120, width: 60, height: 60, name: 'h' },
|
||||
{ x: 465, y: 120, width: 60, height: 60, name: 'j' },
|
||||
{ x: 525, y: 120, width: 60, height: 60, name: 'k' },
|
||||
{ x: 585, y: 120, width: 60, height: 60, name: 'l' },
|
||||
{ x: 645, y: 120, width: 60, height: 60, name: ';' },
|
||||
{ x: 705, y: 120, width: 60, height: 60, name: "'" },
|
||||
{ x: 765, y: 120, width: 135, height: 60, name: 'enter' },
|
||||
{ x: 0, y: 180, width: 135, height: 60, name: 'shift' },
|
||||
{ x: 135, y: 180, width: 60, height: 60, name: 'z' },
|
||||
{ x: 195, y: 180, width: 60, height: 60, name: 'x' },
|
||||
{ x: 255, y: 180, width: 60, height: 60, name: 'c' },
|
||||
{ x: 315, y: 180, width: 60, height: 60, name: 'v' },
|
||||
{ x: 375, y: 180, width: 60, height: 60, name: 'b' },
|
||||
{ x: 435, y: 180, width: 60, height: 60, name: 'n' },
|
||||
{ x: 495, y: 180, width: 60, height: 60, name: 'm' },
|
||||
{ x: 555, y: 180, width: 60, height: 60, name: ',' },
|
||||
{ x: 615, y: 180, width: 60, height: 60, name: '.' },
|
||||
{ x: 675, y: 180, width: 60, height: 60, name: '/' },
|
||||
{ x: 735, y: 180, width: 165, height: 60, name: 'capslock' },
|
||||
{ x: 0, y: 240, width: 90, height: 60, name: 'ctrl' },
|
||||
{ x: 90, y: 240, width: 90, height: 60, name: 'cmd' },
|
||||
{ x: 180, y: 240, width: 90, height: 60, name: 'alt' },
|
||||
{ x: 270, y: 240, width: 270, height: 60, name: 'space' },
|
||||
{ x: 810, y: 240, width: 90, height: 60, name: 'ctrl' },
|
||||
{ x: 720, y: 240, width: 90, height: 60, name: 'pn' },
|
||||
{ x: 630, y: 240, width: 90, height: 60, name: 'fn' },
|
||||
{ x: 540, y: 240, width: 90, height: 60, name: 'alt' }
|
||||
]
|
||||
}
|
||||
|
||||
module.exports = new Controller()
|
||||
128
sources/scripts/lib/theme.js
Normal file
128
sources/scripts/lib/theme.js
Normal file
|
|
@ -0,0 +1,128 @@
|
|||
'use strict'
|
||||
|
||||
function Theme (_default) {
|
||||
const themer = this
|
||||
|
||||
this.active = _default
|
||||
|
||||
this.el = document.createElement('style')
|
||||
this.el.type = 'text/css'
|
||||
|
||||
this.install = function (host = document.body, callback) {
|
||||
console.log('Theme', 'Installing..')
|
||||
host.appendChild(this.el)
|
||||
this.callback = callback
|
||||
}
|
||||
|
||||
this.start = function () {
|
||||
console.log('Theme', 'Starting..')
|
||||
if (isJson(localStorage.theme)) {
|
||||
const storage = JSON.parse(localStorage.theme)
|
||||
if (validate(storage)) {
|
||||
console.log('Theme', 'Found theme in localStorage!')
|
||||
this.load(storage)
|
||||
return
|
||||
}
|
||||
}
|
||||
this.load(_default)
|
||||
}
|
||||
|
||||
this.load = function (data) {
|
||||
const theme = parse(data)
|
||||
if (!validate(theme)) { console.warn('Theme', 'Not a theme', theme); return }
|
||||
console.log('Theme', `Loading theme with background ${theme.background}.`)
|
||||
this.el.innerHTML = `:root { --background: ${theme.background}; --f_high: ${theme.f_high}; --f_med: ${theme.f_med}; --f_low: ${theme.f_low}; --f_inv: ${theme.f_inv}; --b_high: ${theme.b_high}; --b_med: ${theme.b_med}; --b_low: ${theme.b_low}; --b_inv: ${theme.b_inv}; }`
|
||||
localStorage.setItem('theme', JSON.stringify(theme))
|
||||
this.active = theme
|
||||
if (this.callback) {
|
||||
this.callback()
|
||||
}
|
||||
}
|
||||
|
||||
this.reset = function () {
|
||||
this.load(_default)
|
||||
}
|
||||
|
||||
function parse (any) {
|
||||
if (any && any.background) { return any } else if (any && any.data) { return any.data } else if (any && isJson(any)) { return JSON.parse(any) } else if (any && isHtml(any)) { return extract(any) }
|
||||
return null
|
||||
}
|
||||
|
||||
// Drag
|
||||
|
||||
this.drag = function (e) {
|
||||
e.stopPropagation()
|
||||
e.preventDefault()
|
||||
e.dataTransfer.dropEffect = 'copy'
|
||||
}
|
||||
|
||||
this.drop = function (e) {
|
||||
e.preventDefault()
|
||||
e.stopPropagation()
|
||||
const file = e.dataTransfer.files[0]
|
||||
if (!file || !file.name) { console.warn('Theme', 'Unnamed file.'); return }
|
||||
if (file.name.indexOf('.thm') < 0 && file.name.indexOf('.svg') < 0) { console.warn('Theme', 'Skipped, not a theme'); return }
|
||||
const reader = new FileReader()
|
||||
reader.onload = function (e) {
|
||||
themer.load(e.target.result)
|
||||
}
|
||||
reader.readAsText(file)
|
||||
}
|
||||
|
||||
this.open = function () {
|
||||
const fs = require('fs')
|
||||
const { dialog, app } = require('electron').remote
|
||||
const paths = dialog.showOpenDialog(app.win, { properties: ['openFile'], filters: [{ name: 'Themes', extensions: ['svg'] }] })
|
||||
if (!paths) { console.log('Nothing to load') }
|
||||
fs.readFile(paths[0], 'utf8', function (err, data) {
|
||||
if (err) throw err
|
||||
themer.load(data)
|
||||
})
|
||||
}
|
||||
|
||||
window.addEventListener('dragover', this.drag)
|
||||
window.addEventListener('drop', this.drop)
|
||||
|
||||
// Helpers
|
||||
|
||||
function validate (json) {
|
||||
if (!json) { return false }
|
||||
if (!json.background) { return false }
|
||||
if (!json.f_high) { return false }
|
||||
if (!json.f_med) { return false }
|
||||
if (!json.f_low) { return false }
|
||||
if (!json.f_inv) { return false }
|
||||
if (!json.b_high) { return false }
|
||||
if (!json.b_med) { return false }
|
||||
if (!json.b_low) { return false }
|
||||
if (!json.b_inv) { return false }
|
||||
return true
|
||||
}
|
||||
|
||||
function extract (text) {
|
||||
const svg = new DOMParser().parseFromString(text, 'text/xml')
|
||||
try {
|
||||
return {
|
||||
background: svg.getElementById('background').getAttribute('fill'),
|
||||
f_high: svg.getElementById('f_high').getAttribute('fill'),
|
||||
f_med: svg.getElementById('f_med').getAttribute('fill'),
|
||||
f_low: svg.getElementById('f_low').getAttribute('fill'),
|
||||
f_inv: svg.getElementById('f_inv').getAttribute('fill'),
|
||||
b_high: svg.getElementById('b_high').getAttribute('fill'),
|
||||
b_med: svg.getElementById('b_med').getAttribute('fill'),
|
||||
b_low: svg.getElementById('b_low').getAttribute('fill'),
|
||||
b_inv: svg.getElementById('b_inv').getAttribute('fill')
|
||||
}
|
||||
} catch (err) {
|
||||
console.warn('Theme', 'Incomplete SVG Theme', err)
|
||||
}
|
||||
}
|
||||
|
||||
function isJson (text) {
|
||||
try { JSON.parse(text); return true } catch (error) { return false }
|
||||
}
|
||||
|
||||
function isHtml (text) {
|
||||
try { new DOMParser().parseFromString(text, 'text/xml'); return true } catch (error) { return false }
|
||||
}
|
||||
}
|
||||
209
sources/scripts/player.js
Normal file
209
sources/scripts/player.js
Normal file
|
|
@ -0,0 +1,209 @@
|
|||
'use strict'
|
||||
|
||||
function Player () {
|
||||
this.element = null
|
||||
this.health = new Gage_Health('Health', 21, '#ff0000')
|
||||
this.shield = new Gage_Shield('Shield', 0, '#72dec2')
|
||||
this.experience = new Gage('Experience', 0, '#ffffff')
|
||||
|
||||
this.can_drink = true
|
||||
this.has_escaped = false
|
||||
this.escape_button = document.createElement('a')
|
||||
this.timeline_element = document.createElement('div')
|
||||
|
||||
this.escape_button.addEventListener('mousedown', () => { donsol.player.escape_room() })
|
||||
|
||||
this.start = function () {
|
||||
this.health.show_limit = false
|
||||
this.health.units = 'HP'
|
||||
this.shield.units = 'DP'
|
||||
this.experience.units = 'XP'
|
||||
this.experience.show_limit = false
|
||||
|
||||
this.health.value = 21
|
||||
this.shield.value = 0
|
||||
this.shield.break_limit = null
|
||||
this.experience.limit = 54
|
||||
this.experience.value = 0
|
||||
|
||||
this.can_drink = true
|
||||
this.has_escaped = false
|
||||
|
||||
this.update()
|
||||
}
|
||||
|
||||
this.install = function () {
|
||||
this.element.appendChild(this.experience.install())
|
||||
this.element.appendChild(this.shield.install())
|
||||
this.element.appendChild(this.health.install())
|
||||
|
||||
this.escape_button.setAttribute('class', 'escape')
|
||||
this.escape_button.innerHTML = 'Escape'
|
||||
this.element.appendChild(this.escape_button)
|
||||
this.timeline_element.setAttribute('class', 'timeline')
|
||||
this.timeline_element.innerHTML = ''
|
||||
this.update()
|
||||
}
|
||||
|
||||
this.attack = function (card) {
|
||||
console.log('<attack>' + card.value)
|
||||
const attack_value = card.value
|
||||
let damages = attack_value
|
||||
let shield_event = ''
|
||||
|
||||
// Shield
|
||||
if (this.shield.value > 0) {
|
||||
// Damaged shield
|
||||
if (this.shield.is_damaged() === true && attack_value >= this.shield.break_limit) {
|
||||
this.shield.value = 0
|
||||
this.shield.break_limit = null
|
||||
shield_event = 'your shield broke'
|
||||
} else {
|
||||
this.shield.break_limit = attack_value
|
||||
damages = attack_value > this.shield.value ? Math.abs(attack_value - this.shield.value) : 0
|
||||
shield_event = `your shield absorbed ${damages < 1 ? 'everything' : attack_value > this.shield.value ? this.shield.value : attack_value}`
|
||||
}
|
||||
}
|
||||
|
||||
// Damages went through
|
||||
if (damages > 0) {
|
||||
this.health.value -= damages
|
||||
}
|
||||
|
||||
// Timeline
|
||||
if (this.health.value < 1) {
|
||||
donsol.player.health.add_event('-' + damages)
|
||||
donsol.timeline.add_event('<span>The ' + card.name + ' killed you!</span>')
|
||||
donsol.board.dungeon_failed()
|
||||
this.update()
|
||||
} else {
|
||||
donsol.timeline.add_event(`${damages > 0 ? 'Battled' : 'Killed'} the ${card.name}${shield_event !== '' ? ', ' + shield_event : ''}.`)
|
||||
}
|
||||
|
||||
// Experience
|
||||
donsol.player.experience.add_event('+1')
|
||||
|
||||
this.can_drink = true
|
||||
donsol.is_complete = false
|
||||
this.shield.update()
|
||||
this.health.update()
|
||||
}
|
||||
|
||||
this.equip_shield = function (shield_value) {
|
||||
console.log('<shield>' + shield_value)
|
||||
|
||||
this.shield.value = shield_value
|
||||
this.shield.break_limit = null
|
||||
|
||||
// donsol.player.shield.add_event(shield_value);
|
||||
donsol.player.experience.add_event('+1')
|
||||
donsol.timeline.add_event('Equipped shield ' + shield_value + '.')
|
||||
this.can_drink = true
|
||||
donsol.is_complete = false
|
||||
this.shield.update()
|
||||
this.health.update()
|
||||
}
|
||||
|
||||
this.drink_potion = function (potion_value) {
|
||||
console.log('<potion>' + potion_value)
|
||||
|
||||
if (this.can_drink === false) {
|
||||
donsol.timeline.add_event('Wasted potion!')
|
||||
donsol.player.health.add_event('Wasted')
|
||||
return
|
||||
}
|
||||
const before_health = this.health.value
|
||||
let new_health = this.health.value + potion_value; new_health = new_health > 21 ? 21 : new_health
|
||||
|
||||
const mod = new_health - before_health
|
||||
donsol.player.health.value = new_health
|
||||
donsol.player.health.add_event(mod > 0 ? '+' + mod : 'Wasted')
|
||||
donsol.player.experience.add_event('+1')
|
||||
donsol.timeline.add_event('Drank potion.')
|
||||
this.can_drink = false
|
||||
donsol.is_complete = false
|
||||
this.health.update()
|
||||
this.shield.update()
|
||||
}
|
||||
|
||||
this.escape_room = function () {
|
||||
donsol.speaker.play_effect('click2')
|
||||
if (this.health.value < 1 || donsol.is_complete === true || this.experience.value == 0) {
|
||||
donsol.new_game()
|
||||
return
|
||||
}
|
||||
if (this.can_escape() !== true) {
|
||||
donsol.timeline.add_event('Cannot escape the room!')
|
||||
return
|
||||
}
|
||||
|
||||
this.has_escaped = true
|
||||
this.can_drink = true
|
||||
|
||||
donsol.board.return_cards()
|
||||
donsol.board.enter_room()
|
||||
donsol.timeline.add_event('Escaped the room!')
|
||||
}
|
||||
|
||||
this.update = function () {
|
||||
if (this.health.value < 1) {
|
||||
this.escape_button.innerHTML = 'Restart'
|
||||
this.element.setAttribute('class', 'death')
|
||||
} else if (this.can_escape() === true) {
|
||||
this.escape_button.innerHTML = 'Run'
|
||||
this.element.setAttribute('class', 'unlocked')
|
||||
} else {
|
||||
this.escape_button.innerHTML = 'Locked'
|
||||
this.element.setAttribute('class', 'locked')
|
||||
}
|
||||
|
||||
this.health.clear_event()
|
||||
this.shield.clear_event()
|
||||
this.experience.clear_event()
|
||||
|
||||
this.health.update()
|
||||
this.shield.update()
|
||||
this.experience.update()
|
||||
}
|
||||
|
||||
this.can_escape = function () {
|
||||
// Basic Overrides
|
||||
if (this.health.value < 1) { return true } // Death
|
||||
if (this.experience.value === 0) { return true } // New Game
|
||||
|
||||
// - All monsters have been delt with. (Easy Mode)
|
||||
// - The player has not escaped the previous room. (Normal Mode)
|
||||
// - There is only one card left in the room. (Hard Mode)
|
||||
// - Can never escape. (Expert Mode)
|
||||
|
||||
// Easy
|
||||
if (donsol.difficulty == 0) {
|
||||
if (!this.has_escaped) { return true }
|
||||
if (donsol.board.has_monsters()) { console.warn('Monsters present.'); return false }
|
||||
return true
|
||||
}
|
||||
|
||||
// Normal
|
||||
if (donsol.difficulty == 1) {
|
||||
if (!this.has_escaped) { return true }
|
||||
if (donsol.board.has_monsters()) { console.warn('Monsters present.'); return false }
|
||||
return true
|
||||
}
|
||||
|
||||
// Hard
|
||||
if (donsol.difficulty == 2) {
|
||||
if (!this.has_escaped) { return true }
|
||||
if (!donsol.board.cards_flipped().length != 3) { console.warn('Cards remain.'); return false }
|
||||
if (donsol.board.has_monsters()) { console.warn('Monsters present.'); return false }
|
||||
return true
|
||||
}
|
||||
|
||||
// Expert
|
||||
if (donsol.difficulty == 3) {
|
||||
console.warn('Cannot escape(expert).')
|
||||
return false
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
}
|
||||
28
sources/scripts/speaker.js
Normal file
28
sources/scripts/speaker.js
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
'use strict'
|
||||
|
||||
function Speaker () {
|
||||
this.effect = new Audio()
|
||||
|
||||
this.audio_catalog = {}
|
||||
|
||||
this.is_muted = false
|
||||
|
||||
this.play_effect = function (name) {
|
||||
this.effect = this.load(name, 'effect', `media/audio/effect/${name}.ogg`)
|
||||
this.effect.play()
|
||||
}
|
||||
|
||||
this.load = function (name, role, src, loop = false) {
|
||||
const audio_id = role + '_' + name
|
||||
if (!(audio_id in this.audio_catalog)) {
|
||||
const audio = new Audio()
|
||||
audio.name = name
|
||||
audio.src = src
|
||||
audio.loop = loop
|
||||
audio.mute = 'muted'
|
||||
this.audio_catalog[audio_id] = audio
|
||||
}
|
||||
this.audio_catalog[audio_id].currentTime = 0
|
||||
return this.audio_catalog[audio_id]
|
||||
}
|
||||
}
|
||||
16
sources/scripts/timeline.js
Normal file
16
sources/scripts/timeline.js
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
'use strict'
|
||||
|
||||
function Timeline () {
|
||||
this.el = document.createElement('div')
|
||||
this.el.id = 'timeline'
|
||||
|
||||
this.install = function (host) {
|
||||
host.appendChild(this.el)
|
||||
}
|
||||
|
||||
this.add_event = function (message) {
|
||||
this.el.className = ''
|
||||
this.el.style.opacity = '0'
|
||||
setTimeout(() => { this.el.style.opacity = 1; this.el.innerHTML = message }, 100)
|
||||
}
|
||||
}
|
||||
103
sources/scripts/walkthrough.js
Normal file
103
sources/scripts/walkthrough.js
Normal file
|
|
@ -0,0 +1,103 @@
|
|||
'use strict'
|
||||
|
||||
function Walkthrough () {
|
||||
this.is_running = false
|
||||
this.speed = 2500
|
||||
|
||||
this.start = function () {
|
||||
console.log('Started walkthrough')
|
||||
this.is_running = true
|
||||
}
|
||||
|
||||
this.run = function (force = false) {
|
||||
if (!this.is_running && !force) { return } // Idle
|
||||
if (donsol.player.health.value < 1) { this.is_running = false; return }
|
||||
|
||||
const results = this.rate_room(donsol.board.room)
|
||||
const target = results[0]
|
||||
|
||||
// Return if going to waste potions
|
||||
if (target && target[1] < -10 && donsol.player.can_escape()) {
|
||||
donsol.player.escape_room()
|
||||
return
|
||||
}
|
||||
|
||||
if (target) {
|
||||
donsol.board.room[target[[0]]].touch()
|
||||
}
|
||||
}
|
||||
|
||||
this.rate_room = function (room) {
|
||||
const a = []
|
||||
for (const id in room) {
|
||||
const card = room[id]
|
||||
if (card.is_flipped) { continue }
|
||||
a.push(this.rate_card(id, card))
|
||||
}
|
||||
return a.sort(function (a, b) {
|
||||
return a[1] - b[1]
|
||||
}).reverse()
|
||||
}
|
||||
|
||||
this.rate_card = function (id, card) {
|
||||
let rating = 0
|
||||
if (card.type == 'diamond') {
|
||||
if (donsol.player.shield.value > 0) {
|
||||
rating = donsol.player.shield.value - card.value
|
||||
} else {
|
||||
rating = card.value
|
||||
}
|
||||
}
|
||||
if (card.type == 'heart') {
|
||||
// Will waste
|
||||
if (!donsol.player.can_drink || donsol.player.health.value == 21) {
|
||||
rating = -card.value * 4
|
||||
} else {
|
||||
const after = clamp(donsol.player.health.value + card.value, 0, 21)
|
||||
const actual = (donsol.player.health.value - after)
|
||||
rating = actual - card.value
|
||||
}
|
||||
}
|
||||
if (card.type == 'clove' || card.type == 'spade') {
|
||||
const strongest = this.find_strongest(id)
|
||||
if (card.value < strongest.value) {
|
||||
rating = -strongest.value - card.value
|
||||
} else {
|
||||
rating = -card.value
|
||||
}
|
||||
|
||||
if (donsol.player.shield.limit > card.value) {
|
||||
rating = donsol.player.shield.limit
|
||||
}
|
||||
}
|
||||
// TODO: Run
|
||||
// TODO: Attack in descending order
|
||||
// TODO: Don't waste shields
|
||||
return [parseInt(id), rating, card]
|
||||
}
|
||||
|
||||
this.find_strongest = function () {
|
||||
let strongest = null
|
||||
|
||||
for (const id in donsol.board.room) {
|
||||
const card = donsol.board.room[id]
|
||||
if (card.type == 'diamond' || card.type == 'heart') { continue }
|
||||
if (card.is_flipped) { continue }
|
||||
if (!strongest) { strongest = card; continue }
|
||||
if (card.value > strongest.value) { strongest = card }
|
||||
}
|
||||
return strongest
|
||||
}
|
||||
|
||||
setInterval(() => { donsol.walkthrough.run() }, this.speed)
|
||||
function clamp (v, min, max) { return v < min ? min : v > max ? max : v }
|
||||
}
|
||||
|
||||
document.onkeyup = (e) => {
|
||||
if (e.ctrlKey && e.key.toLowerCase() == 'k') {
|
||||
donsol.walkthrough.start()
|
||||
}
|
||||
if (e.ctrlKey && e.key.toLowerCase() == 'l') {
|
||||
donsol.walkthrough.run(true)
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue