All Downloads are FREE. Search and download functionalities are using the official Maven repository.

miksilo.modularLanguages.deltas.statement.assignment.OperatorWithAssignmentDelta.scala Maven / Gradle / Ivy

The newest version!
package miksilo.modularLanguages.deltas.statement.assignment

import miksilo.modularLanguages.core.bigrammar.grammars.BiSequence
import miksilo.modularLanguages.core.deltas.grammars.LanguageGrammars
import miksilo.modularLanguages.core.deltas.path.{NodePath, PathRoot}
import miksilo.modularLanguages.core.deltas.{Contract, DeltaWithGrammar, DeltaWithPhase}
import miksilo.modularLanguages.core.node.{Node, NodeShape}
import miksilo.languageServer.core.language.{Compilation, Language}
import miksilo.modularLanguages.deltas.expression.{BinaryOperatorDelta, LeftAssociativeBinaryOperatorDelta}

trait OperatorWithAssignmentDelta extends DeltaWithPhase with DeltaWithGrammar {

  override def description: String = s"Defines the ${operatorDelta.keyword}= operator."

  override def dependencies: Set[Contract] = Set(operatorDelta, SimpleAssignmentDelta)

  val shape: NodeShape

  def neww(target: Node, value: Node) =
    new Node(shape, SimpleAssignmentDelta.Target -> target, SimpleAssignmentDelta.Value -> value)

  def operatorDelta: BinaryOperatorDelta

  override def transformGrammars(grammars: LanguageGrammars, state: Language): Unit = {
    import grammars._

    val assignmentGrammar = find(AssignmentPrecedence.AssignmentGrammar)
    val assignmentTarget = find(SimpleAssignmentDelta.Target)
    val operatorGrammar = assignmentTarget ~~
      (leftRight(operatorDelta.keyword, "=", BiSequence.identity) ~~> assignmentGrammar.as(SimpleAssignmentDelta.Value)) asLabelledNode shape
    assignmentGrammar.addAlternative(operatorGrammar)
  }

  def transformAssignment(incrementAssignment: NodePath, state: Language): Unit = {
    val target = SimpleAssignmentDelta.getTarget(incrementAssignment)
    val newValue = operatorDelta.shape.createWithData(
      LeftAssociativeBinaryOperatorDelta.Left -> incrementAssignment.current(SimpleAssignmentDelta.Target),
      LeftAssociativeBinaryOperatorDelta.Right -> incrementAssignment.getFieldData(SimpleAssignmentDelta.Value))
    val assignment = SimpleAssignmentDelta.neww(target, newValue)
    incrementAssignment.replaceData(assignment)
  }

  override def transformProgram(program: Node, compilation: Compilation): Unit = {
    PathRoot(program).visitShape(shape, obj => transformAssignment(obj, compilation))
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy