コード例 #1
0
ファイル: main.go プロジェクト: rakyll/GCSolutions
func NewPianoKey(idx int) Key {
	const phasefac float64 = 0.5063999999999971

	k := &PianoKey{}

	k.freq = notes[idx]
	k.mod = snd.NewOscil(sqsine, k.freq/2, nil)
	k.osc = snd.NewOscil(sawtooth, k.freq, k.mod)
	k.phs = snd.NewOscil(square, k.freq*phasefac, nil)
	k.osc.SetPhase(k.phs)

	freql := k.freq * math.Pow(2, -10.0/1200)
	k.modl = snd.NewOscil(sqsine, freql/2, nil)
	k.oscl = snd.NewOscil(sawtooth, freql, k.modl)
	k.phsl = snd.NewOscil(square, freql*phasefac, nil)
	k.oscl.SetPhase(k.phsl)

	freqr := k.freq * math.Pow(2, 10.0/1200)
	k.modr = snd.NewOscil(sqsine, freqr/2, nil)
	k.oscr = snd.NewOscil(sawtooth, freqr, k.modr)
	k.phsr = snd.NewOscil(square, freqr*phasefac, nil)
	k.oscr.SetPhase(k.phsr)

	oscmix := snd.NewMixer(k.osc, k.oscl, k.oscr)

	k.reldur = 1050 * ms
	k.dur = 280*ms + k.reldur
	k.adsr0 = snd.NewADSR(30*ms, 50*ms, 200*ms, k.reldur, 0.4, 1, oscmix)
	k.adsr1 = snd.NewADSR(1*ms, 278*ms, 1*ms, k.reldur, 0.4, 1, oscmix)
	adsrmix := snd.NewMixer(k.adsr0, k.adsr1)

	k.gain = snd.NewGain(snd.Decibel(-10).Amp(), adsrmix)

	k.Instrument = snd.NewInstrument(k.gain)
	k.Off()

	return k
}
コード例 #2
0
ファイル: main.go プロジェクト: rakyll/GCSolutions
func onTouch(ev touch.Event) {

	idx := piano.KeyAt(ev, sz)
	if idx == -1 {
		// top half
		switch ev.Type {
		case touch.TypeBegin:
			if btnreverb.HitTest(ev, sz) {
				btnreverb.SetActive(!btnreverb.IsActive())
				if btnreverb.IsActive() {
					reverb.On()
					keygain.SetAmp(snd.Decibel(-3).Amp())
				} else {
					reverb.Off()
					keygain.SetAmp(snd.Decibel(3).Amp())
				}
			} else if btnlowpass.HitTest(ev, sz) {
				btnlowpass.SetActive(!btnlowpass.IsActive())
				lowpass.SetPassthrough(!btnlowpass.IsActive())
			} else if btnmetronome.HitTest(ev, sz) {
				btnmetronome.SetActive(!btnmetronome.IsActive())
				if btnmetronome.IsActive() {
					metronome.On()
				} else {
					metronome.Off()
				}
			} else if btnloop.HitTest(ev, sz) {
				if !btnloop.IsActive() {
					btnloop.SetActiveColor(1, 1, 0, 0.5)
					btnloop.SetActive(true)
					loop.Record()
				} else {
					loop.Stop()
				}
			} else if btnsndbank.HitTest(ev, sz) {
				sndbankpos = (sndbankpos + 1) % len(sndbank)
				btnsndbank.SetActiveColor(sndbankcolor())
				go makekeys()
			}
		case touch.TypeMove:
		}
		// TODO drag finger off piano and it still plays, shouldn't return here
		// to allow TypeMove to figure out what to turn off
		return
	}

	if keys[idx] == nil {
		return
	}

	switch ev.Type {
	case touch.TypeBegin:
		keys[idx].Press()
		touchseq[ev.Sequence] = idx
	case touch.TypeMove:
		// TODO drag finger off piano and it still plays, should stop
		if lastidx, ok := touchseq[ev.Sequence]; ok {
			if idx != lastidx {
				keys[lastidx].Release()
				keys[idx].Press()
				touchseq[ev.Sequence] = idx
			}
		}
	case touch.TypeEnd:
		keys[idx].Release()
		delete(touchseq, ev.Sequence)
	default:
	}
}
コード例 #3
0
ファイル: main.go プロジェクト: rakyll/GCSolutions
func onStart(ctx gl.Context) {
	ctx.Enable(gl.BLEND)
	ctx.BlendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA)

	if err := al.OpenDevice(buffers); err != nil {
		log.Fatal(err)
	}

	var err error

	keymix = snd.NewMixer()
	go makekeys()
	lowpass = snd.NewLowPass(773, keymix)
	keygain = snd.NewGain(snd.Decibel(-3).Amp(), lowpass)

	dly := snd.NewDelay(29*time.Millisecond, keygain)
	tap0 := snd.NewTap(19*time.Millisecond, dly)
	tap1 := snd.NewTap(13*time.Millisecond, dly)
	tap2 := snd.NewTap(7*time.Millisecond, dly)
	cmb := snd.NewComb(snd.Decibel(-3).Amp(), 11*time.Millisecond, snd.NewMixer(dly, tap0, tap1, tap2))
	reverb = snd.NewLowPass(2000, cmb)
	dlymix := snd.NewMixer(reverb, keygain)

	loop = snd.NewLoopFrames(loopdur, dlymix)
	loop.SetBPM(bpm)
	loopmix := snd.NewMixer(dlymix, loop)

	master = snd.NewMixer(loopmix)
	mastergain = snd.NewGain(snd.Decibel(-6).Amp(), master)
	mixwf, err = snd.NewWaveform(ctx, 2, mastergain)
	if err != nil {
		log.Fatal(err)
	}
	pan := snd.NewPan(0, mixwf)

	mtrosc := snd.NewOscil(sine, 440, nil)
	mtrdmp := snd.NewDamp(bpm.Dur(), mtrosc)
	metronome = snd.NewMixer(mtrdmp)
	metronome.Off()
	master.Append(metronome)

	piano = NewPiano()
	pianowf, err = snd.NewWaveform(ctx, 1, piano)
	if err != nil {
		log.Fatal(err)
	}

	al.AddSource(pan)

	yoff := float32(-0) //.12)

	btnreverb = snd.NewButton(ctx, -0.98, 0.96+yoff, 0.2, -0.2)
	btnreverb.SetActiveColor(0, 1, 0, 0.5)
	btnreverb.SetActive(true)

	btnlowpass = snd.NewButton(ctx, -0.76, 0.96+yoff, 0.2, -0.2)
	btnlowpass.SetActiveColor(0, 1, 1, 0.5)
	btnlowpass.SetActive(true)

	btnmetronome = snd.NewButton(ctx, -0.54, 0.96+yoff, 0.2, -0.2)
	btnmetronome.SetActiveColor(0, 0, 1, 0.5)

	btnloop = snd.NewLoopButton(snd.NewButton(ctx, -0.32, 0.96+yoff, 0.2, -0.2), loop)
	btnloop.SetActiveColor(1, 0, 0, 0.5)

	btnsndbank = snd.NewButton(ctx, 0.78, 0.96+yoff, 0.2, -0.2)
	btnsndbank.SetActive(true)
	btnsndbank.SetActiveColor(sndbankcolor())
}