Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
de.sciss.mellite.impl.objview.DoubleObjView.scala Maven / Gradle / Ivy
/*
* DoubleObjView.scala
* (Mellite)
*
* Copyright (c) 2012-2023 Hanns Holger Rutz. All rights reserved.
*
* This software is published under the GNU Affero General Public License v3+
*
*
* For further information, please contact Hanns Holger Rutz at
* [email protected]
*/
package de.sciss.mellite.impl.objview
import de.sciss.desktop
import de.sciss.kollflitz.Vec
import de.sciss.lucre.expr.graph.Ex
import de.sciss.lucre.synth.Txn
import de.sciss.lucre.{DoubleObj, Expr, Source, Txn => LTxn}
import de.sciss.mellite.impl.ObjGraphemeViewImpl
import de.sciss.mellite.impl.objview.ObjViewImpl.raphaelIcon
import de.sciss.mellite.{GraphemeRendering, GraphemeView, Insets, ObjGraphemeView, ObjListView, ObjView, Shapes}
import de.sciss.proc.Grapheme.Entry
import de.sciss.proc.{Code, Confluent, Universe}
import de.sciss.swingplus.Spinner
import org.rogach.scallop
import javax.swing.{Icon, SpinnerNumberModel}
import scala.swing.{Component, Graphics2D, Label}
import scala.util.Try
object DoubleObjView extends ObjListView.Factory with ObjGraphemeView.Factory with ProgramSupport {
type E[T <: LTxn[T]] = DoubleObj[T]
val icon : Icon = raphaelIcon(Shapes.RealNumber)
val prefix : String = "Double"
def humanName : String = prefix
def category : String = ObjView.categPrimitives
type Elem = Double
def tpe : Expr.Type[Elem, E] = DoubleObj
val codeType: Code.TypeT[Unit, Ex[Elem]] = Code.Program.Double
override protected def scallopValueConverter: scallop.ValueConverter[Elem] = scallop.doubleConverter
def mkListView[T <: Txn[T]](obj: E[T])(implicit tx: T): DoubleObjView[T] with ObjListView[T] = {
val ex = obj
val value = ex.value
val isEditable = Expr.isVar(ex)
val isProgram = Expr.isProgram(ex)
val isViewable = isProgram || tx.isInstanceOf[Confluent.Txn]
new ListImpl[T](tx.newHandle(obj), value, isListCellEditable = isEditable, isProgram = isProgram,
isViewable = isViewable).init(obj)
}
override def initMakeDialog[T <: Txn[T]](window: Option[desktop.Window])
(implicit universe: Universe[T]): MakeResult[T] = {
val model = new SpinnerNumberModel(0.0, Double.NegativeInfinity, Double.PositiveInfinity, 1.0)
val ggValue = new Spinner(model)
val codeValue0 = "0.0"
showMakeDialog(ggValue = ggValue, codeValue0 = codeValue0, prefix = prefix,
window = window)(model.getNumber.doubleValue())
}
def mkGraphemeView[T <: Txn[T]](entry: Entry[T], obj: E[T], mode: GraphemeView.Mode)
(implicit tx: T): ObjGraphemeView[T] = {
val isViewable = tx.isInstanceOf[Confluent.Txn]
// assert (entry.value == value)
new GraphemeImpl[T](tx.newHandle(entry), tx.newHandle(obj), value = obj.value, isViewable = isViewable)
.init(obj, entry)
}
// ---- ListObjView ----
private final class ListImpl[T <: Txn[T]](val objH: Source[T, E[T]], var value: Double,
override val isListCellEditable: Boolean, val isProgram: Boolean,
val isViewable: Boolean)
extends DoubleObjView[T] with ListBase[T]
with ObjListViewImpl.SimpleExpr[T, Elem, E] {
override def configureListCellRenderer(label: Label): Component = {
val valueS = value.toFloat.toString // avoid excessive number of digits!
label.text = if (isProgram) s"= $valueS" else valueS
label
}
def convertEditValue(v: Any): Option[Double] = v match {
case num: Elem => Some(num)
case s : String => Try(s.toDouble).toOption
case _ => None
}
}
// ---- GraphemeObjView ----
def graphemePaintFront[T <: Txn[T]](view: ObjGraphemeView[T], value: Double, g: Graphics2D,
gv: GraphemeView[T], r: GraphemeRendering): Unit = {
import ObjGraphemeView.{HandleDiameter, HandleRadius}
val c = gv.canvas
val selected = gv.selectionModel.contains(view)
val time0 = view.timeValue
val time1 = if (selected) time0 + r.ttMoveState.deltaTime else time0
val value1 = if (selected) value + r.ttMoveState.deltaModelY else value
val x = c.frameToScreen (time1 )
val y = c.modelPosToScreen(value1 )
val p = r.ellipse1
p.setFrame(x - 2, y - 2, 4, 4)
g.setPaint(if (selected) r.pntRegionBackgroundSelected else r.pntRegionBackground)
g.fill(p)
p.setFrame(x - HandleRadius, y - HandleRadius, HandleDiameter, HandleDiameter)
g.setPaint(if (selected) r.pntRegionOutlineSelected else r.pntRegionOutline)
g.draw(p)
}
private final class GraphemeImpl[T <: Txn[T]](val entryH: Source[T, Entry[T]],
val objH: Source[T, E[T]],
var value: Elem,
val isViewable: Boolean)
extends Base[T]
with ObjGraphemeViewImpl.SimpleExpr[T, Elem, E]
with ObjGraphemeView.HasStartLevels[T] {
def insets: Insets = ObjGraphemeView.DefaultInsets
def startLevels: Vec[Double] = value +: Vector.empty
override def paintFront(g: Graphics2D, gv: GraphemeView[T], r: GraphemeRendering): Unit =
graphemePaintFront(this, value, g, gv, r)
}
}
trait DoubleObjView[T <: LTxn[T]] extends ObjView[T] {
type Repr = DoubleObj[T]
}