{"id":14961273,"url":"https://github.com/timdonnelly/advance","last_synced_at":"2025-04-06T00:04:04.861Z","repository":{"id":42568923,"uuid":"51620349","full_name":"timdonnelly/Advance","owner":"timdonnelly","description":"Physics-based animations for iOS, tvOS, and macOS.","archived":true,"fork":false,"pushed_at":"2022-05-16T17:49:30.000Z","size":7796,"stargazers_count":4499,"open_issues_count":3,"forks_count":207,"subscribers_count":95,"default_branch":"master","last_synced_at":"2025-04-06T00:03:48.388Z","etag":null,"topics":["animation","gestures","interaction","ios","motion","physics","springs","swift","ui"],"latest_commit_sha":null,"homepage":"http://timdonnelly.github.io/Advance/","language":"Swift","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"bsd-2-clause","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/timdonnelly.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}},"created_at":"2016-02-12T22:20:07.000Z","updated_at":"2025-04-02T02:41:30.000Z","dependencies_parsed_at":"2022-08-21T01:50:34.283Z","dependency_job_id":null,"html_url":"https://github.com/timdonnelly/Advance","commit_stats":null,"previous_names":["storehouse/advance"],"tags_count":18,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/timdonnelly%2FAdvance","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/timdonnelly%2FAdvance/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/timdonnelly%2FAdvance/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/timdonnelly%2FAdvance/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/timdonnelly","download_url":"https://codeload.github.com/timdonnelly/Advance/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247415963,"owners_count":20935388,"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":["animation","gestures","interaction","ios","motion","physics","springs","swift","ui"],"created_at":"2024-09-24T13:24:19.388Z","updated_at":"2025-04-06T00:04:04.842Z","avatar_url":"https://github.com/timdonnelly.png","language":"Swift","readme":"[![Build Status](https://travis-ci.org/timdonnelly/Advance.svg?branch=master)](https://travis-ci.org/timdonnelly/Advance)\n![Swift 5.0](https://img.shields.io/badge/Swift-5.0-orange.svg)\n![GitHub release](https://img.shields.io/github/release/timdonnelly/Advance.svg)\n[![SwiftPM compatible](https://img.shields.io/badge/SwiftPM-compatible-orange.svg)](#swift-package-manager)\n[![CocoaPods compatible](https://img.shields.io/cocoapods/v/Advance.svg)](#cocoapods) \n\n\n\n# Advance\n\nAn animation library for iOS, tvOS, and macOS that uses physics-based animations (including springs) to power interactions that move and respond realistically.\n\n\n```swift\nlet view = UIView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))\n\n// Springs animate changes to a value\nlet spring = Spring(initialValue: view.center)\n\n// The `onChange` closure will be called every time the spring updates\nspring.onChange = { [view] newCenter in\n    view.center = newCenter\n}\n\n/// The view's center will realistically animate to the new target value.\nspring.target = CGPoint(x: 300, y: 200)\n```\n\n## Installation\n\nThere are several ways to integrate Advance into your project.\n\n* **Manually:** add  `Advance.xcodeproj` to your project, then add `Advance-{iOS|macOS|tvOS}.framework` as an \"Embedded Binary\" to your application target (under General in target settings). From there, add `import Advance` to your code and you're good to go.\n\n* **Carthage:** add `github \"timdonnelly/Advance\"` to your `Cartfile`.\n\n* **CocoaPods:** add `pod 'Advance'` to your `Podfile`.\n\n* **Swift Package Manager:** add a dependency to your `Project.swift`: `.package(url: \"http://github.com/timdonnelly/Advance\", from: \"3.0.0\")`\n\n##### Requirements\n* iOS 10+, tvOS 10+, or macOS 10.12+\n* Swift 5.0 (Xcode 10.2 or higher)\n\n## Usage\n\n**API documentation is [available here](http://timdonnelly.github.io/Advance/).**\n\nAdvance animations are applied on every frame (using `CADisplayLink` on iOS/tvOS, and `CVDisplayLink` on macOS), allowing for fine-grained control at any time.\n\n\n### `Spring`\n\n`Spring` instances animate changes to a value over time, using spring physics.\n\n\n```swift\nlet spring = Spring(initialValue: 0.0)\nspring.onChange = { [view] newAlpha in \n    view.alpha = newAlpha \n}\n\n// Off it goes!\nspring.target = 0.5\n```\n\n#### Configuring a spring\n\n```swift\n\n/// Spring values can be adjusted at any time.\nspring.tension = 30.0 /// The strength of the spring\nspring.damping = 2.0 /// The resistance (drag) that the spring encounters\nspring.threshold = 0.1 /// The maximum delta between the current value and the spring's target (for each component) for which the simulation can enter a converged state.\n\n/// Update the simulation state at any time.\nspring.velocity = 6.5\nspring.value = 0.2\n\n/// Sets the spring's target and the current simulation value, and removes all velocity. This causes the spring to converge at the given value.\nspring.reset(to: 0.5)\n\n```\n\n\n### `Animator`\n\n`Animator` allows for more flexibility in the types of animation that can be performed, but gives up some convenience\nin order to do so. Specifically, animators allow for *any* type of animation or simulation to be performed for a single\nvalue.\n\n```swift\nlet view = UIView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))\n\n/// Animators coordinate animations to drive changes to a value.\nlet sizeAnimator = Animator(initialValue: view.bounds.size)\n\nsizeAnimator.onChange = { [view] newSize in\n    view.bounds.size = newSize\n}\n\n/// A simple timed animation\nsizeAnimator.animate(to: CGSize(width: 123, height: 456), duration: 0.25, timingFunction: .easeInOut)\n\n/// Some time in the future (before the previous timed animation was complete)...\n\n/// Spring physics will move the view's size to the new value, maintaining the velocity from the timed animation.\nsizeAnimator.simulate(using: SpringFunction(target: CGSize(width: 300, height: 300)))\n\n/// Some time in the future (before the previous spring animation was complete)...\n\n/// The value will keep the same velocity that it had from the preceeding spring\n/// animation, and a decay function will slowly bring movement to a stop.\nsizeAnimator.simulate(using: DecayFunction(drag: 2.0))\n\n```\n\nAnimators support two fundamentally different types of animations: timed and simulated.\n\n#### Timed animations\n\nTimed animations are, well, timed: they have a fixed duration, and they animate to a final value in a predictable manner.\n\n```swift\nanimator.animate(to: CGSize(width: 123, height: 456), duration: 0.25, timingFunction: .easeInOut)\n```\n\n`TimingFunction` described the pacing of a timed animation. \n\n`TimingFunction` comes with a standard set of functions:\n\n```swift\nTimingFunction.linear // No easing\nTimingFunction.easeIn\nTimingFunction.easeOut\nTimingFunction.easeInOut\nTimingFunction.swiftOut // Similar to Material Design's default curve\n```\n\nCustom timing functions can be expressed as unit beziers ([described here](https://www.w3.org/TR/css-easing-1/#cubic-bzier-timing-function)).\n\n```swift\nlet customTimingFunction = TimingFunction(x1: 0.1, y1: 0.2, x2: 0.6, y2: 0.0)\n```\n\n#### Simulated animations\n\nSimulated animations use a *simulation function* to power a physics-based transition. Simulation functions are types conforming to the `SimulationFunction` protocol.\n\nSimulated animations may be started using two different methods:\n\n```swift\n// Begins animating with the custom simulation function, maintaining the previous velocity of the animator.\nanimator.simulate(using: MyCustomFunction())\n\n// or...\n\n// Begins animating with the custom simulation function, imparting the specified velocity into the simulation.\nanimator.simulate(using: DecayFunction(), initialVelocity: dragGestureRecognizer.velocity(in: view))\n```\n\n### Animating Custom Types\n\nValues conforming to the `VectorConvertible` protocol can be animated by Advance. Conforming types can be converted to and from a `Vector` implementation.\n```swift\npublic protocol VectorConvertible: Equatable, Interpolatable {\n    associatedtype VectorType: SIMD where VectorType.Scalar == Double\n    init(vector: VectorType)\n    var vector: VectorType { get }\n}\n```\n\nThe library adds conformance for many common types through extensions.\n\n\n## Contributing\n\nIf you encounter any issues or surprises, please open an issue.\n\nFor suggestions or new features, please consider opening a PR with a functional implementation. Issues may be used if you aren't sure how to implement the change, but working code is typically easier to evaluate.\n\n## License\nThis project is released under the [BSD 2-clause license](https://github.com/timdonnelly/Advance/blob/master/LICENSE).\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftimdonnelly%2Fadvance","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ftimdonnelly%2Fadvance","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftimdonnelly%2Fadvance/lists"}