Material Motion Exploring solutions that will empower creators with the tools needed to describe and implement rich, interactive motion on any platform. Edit this page · History
Property · Interaction Rotatable
Status Library
Draft as of December 20, 2016 interactions

Rotatable specification

This is the engineering specification for the Rotatable interaction.

Overview

Feeds rotation starting from an initial rotation to a given property.

Example use:

runtime.connect(Rotatable(view: view, containerView: containerView))

MVP

Expose a Rotatable type

public class Rotatable: Interaction

Expose configurable values

All property values should be readonly, all stream values should be settable.

class Rotatable {

  /** The property to which the value stream is expected to write. */
  public let property: ReactiveProperty<CGPoint>

  /** A stream that emits values to be written to the property. */
  public var valueStream: MotionObservable<CGPoint>

  /** A stream that emits velocity when the gesture recognizer ends. */
  public var velocityStream: MotionObservable<CGPoint>

  /** The gesture recognizer that drives this interaction. */
  public let gestureRecognizer: RotationGestureRecognizer

Expose an initializer

Allow a gesture recognizer to be optionally provided.

class Rotatable {
  public init(property: ReactiveProperty<CGPoint>,
              containerElement: Element,
              gestureRecognizer: RotationGestureRecognizer? = nil)

Store the property

class Rotatable {
  init(...) {
    self.property = property

    ...

Create a gesture recognizer if one was not provided

class Rotatable {
  init(...) {
    ...

    self.gestureRecognizer = gestureRecognizer ?? RotationGestureRecognizer()
    if self.gestureRecognizer.element == nil {
      containerView.addGestureRecognizer(self.gestureRecognizer)
    }

    ...

Create the value and velocity streams

class Rotatable {
  init(...) {
    ...

    let source = gestureSource(self.gestureRecognizer)
    self.valueStream = source.rotated(from: property)
    self.velocityStream = source.velocity()

Expose a convenience initializer

The convenience initializer should extract the necessary property from the provided element.

class Rotatable {
  public init(element: Element,
              containerElement: Element,
              gestureRecognizer: RotationGestureRecognizer? = nil)