{"id":2358,"url":"https://github.com/lkzhao/YetAnotherAnimationLibrary","last_synced_at":"2025-08-02T23:33:08.207Z","repository":{"id":56930144,"uuid":"87661634","full_name":"lkzhao/YetAnotherAnimationLibrary","owner":"lkzhao","description":"Designed for gesture-driven animations. Fast, simple, \u0026 extensible!","archived":false,"fork":false,"pushed_at":"2023-10-08T23:08:02.000Z","size":360,"stargazers_count":516,"open_issues_count":7,"forks_count":29,"subscribers_count":10,"default_branch":"master","last_synced_at":"2024-04-30T19:22:24.248Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"Swift","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/lkzhao.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null}},"created_at":"2017-04-08T20:18:27.000Z","updated_at":"2024-01-31T06:45:30.000Z","dependencies_parsed_at":"2024-01-02T21:24:25.146Z","dependency_job_id":null,"html_url":"https://github.com/lkzhao/YetAnotherAnimationLibrary","commit_stats":{"total_commits":32,"total_committers":2,"mean_commits":16.0,"dds":0.03125,"last_synced_commit":"9a924cb520568f96e7dc9eed683a8b7c385e0d2f"},"previous_names":[],"tags_count":11,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lkzhao%2FYetAnotherAnimationLibrary","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lkzhao%2FYetAnotherAnimationLibrary/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lkzhao%2FYetAnotherAnimationLibrary/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lkzhao%2FYetAnotherAnimationLibrary/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/lkzhao","download_url":"https://codeload.github.com/lkzhao/YetAnotherAnimationLibrary/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":228503192,"owners_count":17930532,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-01-05T20:16:11.788Z","updated_at":"2024-12-06T17:31:00.551Z","avatar_url":"https://github.com/lkzhao.png","language":"Swift","funding_links":[],"categories":["UI","HarmonyOS"],"sub_categories":["Animation","Other free courses","Windows Manager"],"readme":"# Yet Another Animation Library\n\nDesigned for gesture-driven animations. Fast, simple, \u0026 extensible!\n\nIt is written in pure swift 3.1 with protocol oriented design and extensive use of generics.\n\nConsider this as a swift optimized version of facebook's pop. It plays nicer with swift and faster too.\n\n**Fast**:\n  * Uses SIMD types and instructions for calculation\n  * Better compiler optimization through swift generics\n\n**Simple**:\n  * Supports Curve(Basic), Spring, \u0026 Decay animations out of the box\n  * Easy API for animating common animatable properties. (checkout the [Extensions](https://github.com/lkzhao/YetAnotherAnimationLibrary/tree/master/Sources/Extensions) folder for list of included properties)\n  * Type safety guaranteed when assigning animation values\n  * Observable, including value, velocity, and target value\n  * Builtin chaining operator to easily react to changes in value\n  * Provide velocity interpolation with gestures\n\n**Extensible**:\n  * Supports custom property\n  * Supports custom animatable type\n  * Supports custom animation\n\n## Installation\n\n```ruby\npod \"YetAnotherAnimationLibrary\"\n```\n\n## Usage\n\n### Animation\n\n```swift\n// Spring animation\nview.yaal.center.animateTo(CGPoint(x:50, y:100))\nview.yaal.alpha.animateTo(0.5, stiffness: 300, damping: 20)\n\n// Curve(Basic) animation\nview.yaal.frame.animateTo(CGRect(x:0, y:0, width:50, height:50), duration:0.5, curve: .linear)\n\n// Decay Animation\nview.yaal.center.decay(initialVelocity:CGPoint(x:100, y:0))\n```\n\n### Observe Changes\n\n```swift\n// observe value changes\nview.yaal.center.value.changes.addListener { oldVelocity, newVelocity in\n  print(oldVelocity, newVelocity)\n}\n// observe velocity changes\nview.yaal.center.velocity.changes.addListener { oldVelocity, newVelocity in\n  print(oldVelocity, newVelocity)\n}\n```\n\n### Chaining Reactions\n```swift\n// when scale changes, also change its alpha\n// for example if view's scale animates from 1 to 0.5. its alpha will animate to 0.5 as well\nview.yaal.scale.value =\u003e view.yaal.alpha\n// equvalent to the following\n// view.yaal.scale.value.changes.addListener { _, newScale in\n//   view.yaal.alpha.animateTo(newScale)\n// }\n\n// optionally you can provide a mapping function in between.\n// For example, the following code makes the view more transparent the faster it is moving\nview.yaal.center.velocity =\u003e { 1 - $0.magnitude / 1000 } =\u003e view.yaal.alpha\n// equvalent to the following\n// view.yaal.center.velocity.changes.addListener { _, newVelocity in\n//   view.yaal.alpha.animateTo(1 - newVelocity.magnitude / 1000)\n// }\n```\n\n### Set Value (Notify listeners)\n```swift\n// this sets the value directly (not animate to). Change listeners are called.\n// Velocity listeners will receive a series of smoothed velocity values.\nview.yaal.center.setTo(gestureRecognizer.location(in:nil))\n```\n\n## Advance Usages\n\n### React to changes\nAnimate is very efficient at observing animated value and react accordingly. Some awesome effects can be achieved through observed values.\n\nFor example, here is a simple 2d rotation animation thats made possible through observing the center value's velocity.\n```swift\n   override func viewDidLoad() {\n     // ...\n     view.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(tap(gr:))))\n     squareView.yaal.center.velocity =\u003e { $0.x / 1000 } =\u003e squareView.yaal.rotation\n   }\n   func tap(gr: UITapGestureRecognizer) {\n       squareView.yaal.center.animateTo(gr.location(in: view))\n   }\n```\n\u003cimg src=\"https://cloud.githubusercontent.com/assets/3359850/24976406/51c0e0ae-1f97-11e7-8e7d-7684a625195f.gif\" width=\"300\"/\u003e\n\n----------------------\n\nAnimate also provide smooth velocity interpolation when calling `setTo(_:)`. This is especially useful when dealing with user gesture.\n\nFor example. the following does a 3d rotate animation when dragged\n```swift\noverride func viewDidLoad() {\n    // ...\n    squareView.addGestureRecognizer(UIPanGestureRecognizer(target: self, action: #selector(pan(gr:))))\n    squareView.yaal.perspective.setTo(-1.0 / 500.0)\n    squareView.yaal.center.velocity =\u003e { $0.x / 1000 } =\u003e squareView.yaal.rotationY\n    squareView.yaal.center.velocity =\u003e { -$0.y / 1000 } =\u003e squareView.yaal.rotationX\n}\n\nfunc pan(gr: UIPanGestureRecognizer) {\n    squareView.yaal.center.setTo(gr.location(in: view))\n}\n```\n\u003cimg src=\"https://cloud.githubusercontent.com/assets/3359850/24976408/52d1afe6-1f97-11e7-84ee-356b92076333.gif\" width=\"300\"/\u003e\n\n### Custom property\n\nTo animate custom property, just create an animation object by calling `SpringAnimation(getter:setter:)`. Use the animation object to animate and set the values. There are 4 types of animations provided by Animate:\n\n* SpringAnimation\n* CurveAnimation\n* DecayAnimation\n* MixAnimation (does all three types of animation)\n\n```swift\nclass Foo {\n    var volumn: Float = 0.0\n    lazy var volumnAnimation: SpringAnimation\u003cFloat\u003e\n        = SpringAnimation(getter: { [weak self] in self?.volumn },\n                          setter: { [weak self] in self?.volumn = $0 })\n}\n\nvolumnAnimation.animateTo(0.5)\n```\n\nIf your class inherits from NSObject, then it is even easier by using the built in animation store.\n\n### via extension \u0026 `yaal.animationFor`\n```swift\nextension Foo {\n    public var volumnAnimation: MixAnimation\u003cCGRect\u003e {\n        return yaal.animationFor(key: \"volumn\",\n                                 getter: { [weak self] in self?.volumn },\n                                 setter: { [weak self] in self?.volumn = $0 })\n    }\n}\n```\n\n### via `yaal.register` \u0026 `yaal.animationFor`\n```swift\n// or register ahead of time\nyaal.register(key: \"volumn\", \n              getter: { [weak self] in self?.volumn },\n              setter: { [weak self] in self?.volumn = $0 })\n\n// and retrieve the animation object through the same key.\nyaal.animationFor(key: \"volumn\")!.animateTo(0.5)\n\n// NOTE: that this method have limited type safety. You can basically pass any animatable type into `animateTo()`\n// There is nothing to stop you from doing the following. but they will crash at run time\nyaal.animationFor(key: \"volumn\")!.animateTo(CGSize.zero)\nyaal.animationFor(key: \"volumn\")!.animateTo(CGRect.zero)\n```\n\n### Custom Animatable Type\n\nCustom animatable types are also supported. Just make the type conform to `VectorConvertable`.\n\n```swift\n// the following makes IndexPath animatable\nextension IndexPath: VectorConvertible {\n    public typealias Vector = Vector2\n    public init(vector: Vector) {\n        self.init(item: Int(vector.x), section: Int(vector.y))\n    }\n    public var vector: Vector {\n        return [Double(item), Double(section)]\n    }\n}\n// Can now be used like this\nlet indexAnimation = SpringAnimation(getter: { self.indexPath },\n                                     setter: { self.indexPath = $0 })\nindexAnimation.animateTo(IndexPath(item:0, section:0))\n\n// Note that everything is type safe. incorrect type won't be allowed to compile\n```\n\n### Custom Animation\n\nJust subclass `Animation` and override `update(dt:TimeInterval)` method.\nIf your animation need getter \u0026 setter support, subclass `ValueAnimation` instead.\nCheckout the builtin animations for example.\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flkzhao%2FYetAnotherAnimationLibrary","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flkzhao%2FYetAnotherAnimationLibrary","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flkzhao%2FYetAnotherAnimationLibrary/lists"}