mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2026-08-26 22:50:26 +01:00
Instrument tweaks
The piano will stop playing once you walk away from it or get stunned. The song BPM of the piano and violin will generally speaking be wrong because of discrepancies between the sleep between notes and world.tick_lag. I've solved this by locking BPM to points where the stated BPM will actually be the case because tempo == world.tick_lag. Example Current: song @ 5 tempo - 120 BPM: c, c/2, c -> note -> sleep(5) -> 6 ticks (5.4 time passes) -> note -> sleep(2.5) -> 3 ticks (2.7 time passes) -> note. With this PR: song @ 5.4 tempo - 111 BPM: c, c/2, c -> note -> sleep(5.4) -> 6 ticks (5.4 time passes) -> note/2 -> sleep(2.7) -> 3 ticks (2.7 time passes) -> note. I was hoping this would make the damn things sound better but then I realized it wasn't actually messing anything up. Oh well.
This commit is contained in:
@@ -3,7 +3,7 @@
|
||||
/datum/song
|
||||
var/name = "Untitled"
|
||||
var/list/lines = new()
|
||||
var/tempo = 5
|
||||
var/tempo = 5 // delay between notes
|
||||
|
||||
var/playing = 0 // if we're playing
|
||||
var/help = 0 // if help is open
|
||||
@@ -16,6 +16,7 @@
|
||||
var/obj/instrumentObj = null // the associated obj playing the sound
|
||||
|
||||
/datum/song/New(dir, obj)
|
||||
tempo = sanitize_tempo(tempo)
|
||||
instrumentDir = dir
|
||||
instrumentObj = obj
|
||||
|
||||
@@ -63,8 +64,10 @@
|
||||
/datum/song/proc/updateDialog(mob/user as mob)
|
||||
instrumentObj.updateDialog() // assumes it's an object in world, override if otherwise
|
||||
|
||||
/datum/song/proc/shouldStopPlaying()
|
||||
/datum/song/proc/shouldStopPlaying(mob/user)
|
||||
if(instrumentObj)
|
||||
if(!user.canUseTopic(instrumentObj))
|
||||
return 1
|
||||
return !instrumentObj.anchored // add special cases to stop in subclasses
|
||||
else
|
||||
return 1
|
||||
@@ -84,7 +87,7 @@
|
||||
var/list/notes = text2list(beat, "/")
|
||||
for(var/note in text2list(notes[1], "-"))
|
||||
//world << "note: [note]"
|
||||
if(!playing || shouldStopPlaying())//If the instrument is playing, or special case
|
||||
if(!playing || shouldStopPlaying(user))//If the instrument is playing, or special case
|
||||
playing = 0
|
||||
return
|
||||
if(lentext(note) == 0)
|
||||
@@ -104,7 +107,7 @@
|
||||
cur_oct[cur_note] = text2num(ni)
|
||||
playnote(cur_note, cur_acc[cur_note], cur_oct[cur_note])
|
||||
if(notes.len >= 2 && text2num(notes[2]))
|
||||
sleep(tempo / text2num(notes[2]))
|
||||
sleep(sanitize_tempo(tempo / text2num(notes[2])))
|
||||
else
|
||||
sleep(tempo)
|
||||
repeat--
|
||||
@@ -136,10 +139,8 @@
|
||||
dat += "<B><A href='?src=\ref[src];edit=1'>Hide Editor</A></B>"
|
||||
dat += " <A href='?src=\ref[src];newsong=1'>Start a New Song</A>"
|
||||
dat += " <A href='?src=\ref[src];import=1'>Import a Song</A><BR><BR>"
|
||||
var/calctempo = round(600 / tempo)
|
||||
var/calcstep = tempo - 600 / (calctempo+1)
|
||||
var/calcstep_b = tempo - 600 / (calctempo+10)
|
||||
dat += "Tempo: <A href='?src=\ref[src];tempo=[calcstep_b]'>-</A><A href='?src=\ref[src];tempo=[calcstep]'>-</A> [calctempo] BPM <A href='?src=\ref[src];tempo=-[calcstep]'>+</A><A href='?src=\ref[src];tempo=-[calcstep_b]'>+</A><BR><BR>"
|
||||
var/bpm = round(600 / tempo)
|
||||
dat += "Tempo: <A href='?src=\ref[src];tempo=[world.tick_lag]'>-</A> [bpm] BPM <A href='?src=\ref[src];tempo=-[world.tick_lag]'>+</A><BR><BR>"
|
||||
var/linecount = 0
|
||||
for(var/line in lines)
|
||||
linecount += 1
|
||||
@@ -183,7 +184,7 @@
|
||||
|
||||
if(href_list["newsong"])
|
||||
lines = new()
|
||||
tempo = 5 // default 120 BPM
|
||||
tempo = sanitize_tempo(5) // default 120 BPM
|
||||
name = ""
|
||||
|
||||
else if(href_list["import"])
|
||||
@@ -203,10 +204,10 @@
|
||||
spawn()
|
||||
lines = text2list(t, "\n")
|
||||
if(copytext(lines[1],1,6) == "BPM: ")
|
||||
tempo = 600 / max(1, text2num(copytext(lines[1],6)))
|
||||
tempo = sanitize_tempo(600 / text2num(copytext(lines[1],6)))
|
||||
lines.Cut(1,2)
|
||||
else
|
||||
tempo = 5 // default 120 BPM
|
||||
tempo = sanitize_tempo(5) // default 120 BPM
|
||||
if(lines.len > 50)
|
||||
usr << "Too many lines!"
|
||||
lines.Cut(51)
|
||||
@@ -235,11 +236,7 @@
|
||||
repeat = max_repeats
|
||||
|
||||
else if(href_list["tempo"])
|
||||
tempo += text2num(href_list["tempo"])
|
||||
if(tempo < 1)
|
||||
tempo = 1
|
||||
if(tempo > 600)
|
||||
tempo = 600
|
||||
tempo = sanitize_tempo(tempo + text2num(href_list["tempo"]))
|
||||
|
||||
else if(href_list["play"])
|
||||
playing = 1
|
||||
@@ -279,6 +276,9 @@
|
||||
updateDialog(usr)
|
||||
return
|
||||
|
||||
/datum/song/proc/sanitize_tempo(new_tempo)
|
||||
new_tempo = abs(new_tempo)
|
||||
return max(round(new_tempo, world.tick_lag), world.tick_lag)
|
||||
|
||||
// subclass for handheld instruments, like violin
|
||||
/datum/song/handheld
|
||||
@@ -322,6 +322,10 @@
|
||||
song = null
|
||||
..()
|
||||
|
||||
/obj/structure/piano/initialize()
|
||||
song.tempo = song.sanitize_tempo(song.tempo) // tick_lag isn't set when the map is loaded
|
||||
..()
|
||||
|
||||
/obj/structure/piano/attack_hand(mob/user as mob)
|
||||
if(!user.IsAdvancedToolUser())
|
||||
user << "<span class='danger'>You don't have the dexterity to do this!</span>"
|
||||
|
||||
Reference in New Issue
Block a user