Skip to content

Commit 730ed92

Browse files
authored
add: support for roadrunner
* setup gradle for roadrunner extension * refactor: update unit test to use JUnit 5 assertions * add: implement FollowTrajectoryCommand and FollowTurnCommand classes * define RoadRunner version in gradle.properties and use it in roadrunn… * refactor: rename FollowTrajectoryCommand and FollowTurnCommand classe… * add: initialize Turn class with name based on angle
1 parent 350c320 commit 730ed92

13 files changed

Lines changed: 888 additions & 7 deletions

File tree

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,3 +13,5 @@
1313
.externalNativeBuild
1414
.cxx
1515
local.properties
16+
17+
/**/build

.idea/gradle.xml

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

build.gradle.kts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ plugins {
1313

1414
allprojects {
1515
version = property("version") as String
16-
group = "dev.nextftc"
16+
group = "dev.nextftc.extensions"
1717
}
1818

1919
subprojects {

gradle.properties

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,8 @@ kotlin.code.style=official
22
org.jetbrains.dokka.experimental.gradle.pluginMode=V2Enabled
33
org.jetbrains.dokka.experimental.gradle.pluginMode.noWarn=true
44

5-
version=1.0.0
6-
automaticMavenCentralSync=true
5+
automaticMavenCentralSync=true
6+
7+
android.useAndroidX=true
8+
9+
versions.roadrunner=0.1.25-1-local.3

gradle/libs.versions.toml

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
[versions]
22
kotlin = "2.0.0"
33
android = "8.7.3"
4-
nextftc = "1.0.0-SNAPSHOT"
4+
nextftc = "1.0.0-beta.2"
55
kotest = "5.9.1"
66
ftc = "10.3.0"
77
pedro = "2.0.0"
8+
rr-core = "1.0.1"
9+
rr-ftc = "0.1.25"
810

911
[libraries]
1012
kotest-runner = { module = "io.kotest:kotest-runner-junit5", version.ref = "kotest" }
@@ -18,11 +20,14 @@ ftc-common = { group = "org.firstinspires.ftc", name = "FtcCommon", version.ref
1820
nextftc-ftc = { group = "dev.nextftc", name = "ftc", version.ref = "nextftc" }
1921
nextftc-hardware = { group = "dev.nextftc", name = "hardware", version.ref = "nextftc" }
2022
pedro = { module = "com.pedropathing:ftc", version.ref = "pedro" }
23+
rr-core = { module = "com.acmerobotics.roadrunner:core", version.ref = "rr-core" }
24+
rr-ftc = { module = "com.acmerobotics.roadrunner:ftc", version.ref = "rr-ftc" }
2125

2226
[bundles]
2327
kotest = ["kotest-runner", "kotest-assertations", "kotest-property"]
2428
ftc = ["ftc-robot-core", "ftc-hardware", "ftc-common"]
2529
nextftc = ["nextftc-ftc", "nextftc-hardware"]
30+
roadrunner = ["rr-core", "rr-ftc"]
2631

2732
[plugins]
2833
kotlin-jvm = { id = "org.jetbrains.kotlin.jvm", version.ref = "kotlin" }

pedro/src/test/java/dev/nextftc/extensions/ExampleUnitTest.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
package dev.nextftc.extensions
22

3-
import org.junit.Test
43

5-
import org.junit.Assert.*
4+
import org.junit.jupiter.api.Assertions.assertEquals
5+
import org.junit.jupiter.api.Test
66

77
/**
88
* Example local unit test, which will execute on the development machine (host).

roadrunner/build.gradle.kts

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
plugins {
2+
kotlin("android")
3+
id("com.android.library")
4+
}
5+
6+
android {
7+
namespace = "dev.nextftc.extensions.roadrunner"
8+
compileSdk = 35
9+
10+
defaultConfig {
11+
minSdk = 24
12+
}
13+
14+
compileOptions {
15+
sourceCompatibility = JavaVersion.VERSION_1_8
16+
targetCompatibility = JavaVersion.VERSION_1_8
17+
}
18+
19+
kotlinOptions {
20+
jvmTarget = "1.8"
21+
freeCompilerArgs += "-Xjvm-default=all"
22+
}
23+
24+
publishing {
25+
singleVariant("release")
26+
}
27+
}
28+
29+
dependencies {
30+
implementation(libs.bundles.nextftc)
31+
implementation(libs.bundles.roadrunner)
32+
implementation(libs.bundles.ftc)
33+
}
34+
35+
description =
36+
"Support for using RoadRunner with NextFTC."
37+
38+
nextFTCPublishing {
39+
displayName = "NextFTC Extensions - RoadRunner"
40+
logoPath = "../assets/logo-icon.svg"
41+
version = property("versions.roadrunner") as String
42+
}
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
package dev.nextftc.extensions.roadrunner
2+
3+
import com.acmerobotics.roadrunner.Pose2dDual
4+
import com.acmerobotics.roadrunner.PoseVelocity2d
5+
import com.acmerobotics.roadrunner.Time
6+
import com.acmerobotics.roadrunner.TimeTrajectory
7+
import com.acmerobotics.roadrunner.Trajectory
8+
import com.acmerobotics.roadrunner.Vector2d
9+
import com.qualcomm.robotcore.util.ElapsedTime
10+
import dev.nextftc.core.commands.Command
11+
12+
/**
13+
* Follows a trajectory parametrized by time.
14+
*
15+
* Note that the output of [TrajectoryCommandBuilder.build] only returns a [Command]
16+
* object and not a [FollowTrajectory] object,
17+
* because the builder sequences the trajectory with other actions,
18+
* such as [Turn]s, [dev.nextftc.core.commands.delays.Delay]s or user-specified callbacks.
19+
*/
20+
class FollowTrajectory(private val mecanumDrive: NextFTCMecanumDrive, private val trajectory: TimeTrajectory) : Command() {
21+
constructor(mecanumDrive: NextFTCMecanumDrive, trajectory: Trajectory) :
22+
this(mecanumDrive, TimeTrajectory(trajectory))
23+
24+
val timer = ElapsedTime()
25+
26+
override val isDone: Boolean
27+
get() = timer.seconds() >= trajectory.duration
28+
29+
override fun start() {
30+
timer.reset()
31+
}
32+
33+
override fun update() {
34+
val txWorldTarget: Pose2dDual<Time> = trajectory[timer.seconds()]
35+
36+
val robotVelRobot: PoseVelocity2d = mecanumDrive.updatePoseEstimate()
37+
38+
val command =
39+
mecanumDrive.controller.compute(txWorldTarget, mecanumDrive.getPose(), robotVelRobot)
40+
41+
mecanumDrive.setDrivePowersFF(command)
42+
}
43+
44+
override fun stop(interrupted: Boolean) {
45+
mecanumDrive.setDrivePowersFF(PoseVelocity2d(Vector2d(0.0, 0.0), 0.0))
46+
}
47+
}
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
package dev.nextftc.extensions.roadrunner
2+
3+
import com.acmerobotics.roadrunner.HolonomicController
4+
import com.acmerobotics.roadrunner.Pose2d
5+
import com.acmerobotics.roadrunner.PoseVelocity2d
6+
import com.acmerobotics.roadrunner.PoseVelocity2dDual
7+
import com.acmerobotics.roadrunner.Time
8+
9+
/**
10+
* Represents a RoadRunner Mecanum drivetrain from the QuickStart.
11+
*/
12+
abstract class NextFTCMecanumDrive {
13+
abstract val controller: HolonomicController
14+
15+
abstract fun getPose(): Pose2d
16+
17+
abstract fun setDrivePowersFF(powers: PoseVelocity2dDual<Time>)
18+
19+
open fun setDrivePowersFF(powers: PoseVelocity2d) =
20+
setDrivePowersFF(PoseVelocity2dDual.constant(powers, 1))
21+
22+
abstract fun updatePoseEstimate(): PoseVelocity2d
23+
24+
abstract fun commandBuilder(beginPose: Pose2d): TrajectoryCommandBuilder
25+
26+
open fun commandBuilder() = commandBuilder(getPose())
27+
}

0 commit comments

Comments
 (0)