package audio

// Sample represents a normalized audio sample in the range [-1, +1].
type Sample float64

const (
	SampleMin Sample = -1.0
	SampleMax Sample = 1.0
)

// Frame is a stereo pair of audio samples.
type Frame struct {
	L Sample
	R Sample
}

// NewFrame creates a Frame from the provided left/right samples.
func NewFrame(l, r Sample) Frame {
	return Frame{L: l, R: r}
}

// Mono returns the (L+R)/2 signal used in MPX generation.
func (f Frame) Mono() Sample {
	return (f.L + f.R) / 2
}

// Difference returns the (L-R)/2 signal used for the stereo subcarrier.
func (f Frame) Difference() Sample {
	return (f.L - f.R) / 2
}

// Clamp ensures the sample stays within the legal range.
func (s Sample) Clamp() Sample {
	if s > SampleMax {
		return SampleMax
	}
	if s < SampleMin {
		return SampleMin
	}
	return s
}

// Scale adjusts the sample by a gain factor while keeping the result clamped.
func (s Sample) Scale(gain float64) Sample {
	return Sample(float64(s) * gain).Clamp()
}
