Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
d4b7f44
finish ClimberSubsystem
Gary123abc Jan 29, 2026
2f41282
[ClimberSubsystem] feat:新增初版程式
Gary123abc Jan 29, 2026
f8fccfa
[ClimberSubsystem]fix:修改排版問題
Gary123abc Jan 29, 2026
17fee36
[ClimberSubsystem]fix:修改import順序
Gary123abc Jan 29, 2026
6db4d79
[ClimberSubsysten]fix:再次修改import
Gary123abc Jan 29, 2026
316e8de
[ClimberSubsystem]fix:再再次修改import
Gary123abc Jan 29, 2026
e3ef040
[ClimberSubsystem]fix:3度修改import.
Gary123abc Jan 29, 2026
5d96323
[ClimberSubsystem]feat:增加constants同時修改命名方式
Gary123abc Jan 29, 2026
e1a2d04
[ClimberSubsystem]fix:修改空格數及constants
Gary123abc Jan 29, 2026
0b630f6
[ClimberSubsystem]feat:新增簡易command
Gary123abc Jan 30, 2026
a97aa47
[ClimberSubsystem]:style修正排版
Gary123abc Jan 30, 2026
6939b0e
[ClimberSubsystem]style:再次修改排版
Gary123abc Jan 30, 2026
aee521c
[ClimberSubsystem]style:修改檔名
Gary123abc Jan 30, 2026
2ec7914
[Climber]style:修改檔名
Gary123abc Jan 30, 2026
cdfe1ab
[ClimberSubsystem]style:修改檔名
Gary123abc Jan 30, 2026
29bfb95
[ClimberSubsysyem]feat:新增簡易command
Gary123abc Feb 2, 2026
47db318
[ClimberSubsystem]feat:新增簡易command
Gary123abc Feb 2, 2026
4090adf
[ClimberSubsystem]sytle:修改排版
Gary123abc Feb 2, 2026
fddda67
[ClimberSubsystem]feat:換成DutyCycleEncoder
Gary123abc Feb 3, 2026
6926fe8
[Climber]feat:修改toHome邏輯
Gary123abc Feb 4, 2026
bfff155
[ClimberSubsystem]feat: 修改clamp
Gary123abc Feb 5, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions src/main/java/frc/robot/Constants.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,4 +7,14 @@
/** Add your docs here. */
public class Constants {

public static class ClimberConstants {
public static final int motorId = 0;
public static final double kP = 0.01;
public static final double kI = 0.0;
public static final double kD = 0.0;
public static final int currentLimit = 80;
public static final double L1position = 25;
public static final double L2position = 50;

}
}
5 changes: 3 additions & 2 deletions src/main/java/frc/robot/RobotContainer.java
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,10 @@ public RobotContainer() {
configureBindings();
}

private void configureBindings() {}
private void configureBindings() {
}

public Command getAutonomousCommand() {
return Commands.print("No autonomous command configured");
}
}
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

啊,你這邊好像又不小心把一行刪掉了
你可以看 PR 的 Files changed 頁面確認一下跟原本的差在哪

86 changes: 80 additions & 6 deletions src/main/java/frc/robot/subsystems/ClimberSubsystem.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,34 +4,108 @@

package frc.robot.subsystems;

import com.revrobotics.PersistMode;
import com.revrobotics.ResetMode;
import com.revrobotics.spark.SparkLowLevel.MotorType;
import com.revrobotics.spark.SparkMax;
import com.revrobotics.spark.config.SparkMaxConfig;
import edu.wpi.first.math.MathUtil;
import edu.wpi.first.math.controller.PIDController;
import edu.wpi.first.wpilibj.DutyCycleEncoder;
import edu.wpi.first.wpilibj.smartdashboard.SmartDashboard;
import edu.wpi.first.wpilibj2.command.Command;
import edu.wpi.first.wpilibj2.command.SubsystemBase;
import frc.robot.Constants.ClimberConstants;

public class ClimberSubsystem extends SubsystemBase {
/** Creates a new ClimberSubsystem. */
public ClimberSubsystem() {}

private void toLowRung() {
private final SparkMax climberMotor = new SparkMax(ClimberConstants.motorId, MotorType.kBrushless);
private final PIDController climberPID = new PIDController(
ClimberConstants.kP, ClimberConstants.kI, ClimberConstants.kD);
private final DutyCycleEncoder climberEncoder = new DutyCycleEncoder(1, 360, 0);

public ClimberSubsystem() {
SparkMaxConfig config = new SparkMaxConfig();
config
.idleMode(com.revrobotics.spark.config.SparkBaseConfig.IdleMode.kBrake)
.smartCurrentLimit(ClimberConstants.currentLimit);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

為什麼需要特別調整 SparkMax 預設的 CurrentLimit?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Gary123abc 可以回覆一下嗎?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

因為原本有要測馬達邏輯,所以就先設小一點,然後clamp的數值也是


climberMotor.configure(
config, ResetMode.kResetSafeParameters, PersistMode.kNoPersistParameters);
}

public void toLowRung() {
climberPID.setSetpoint(ClimberConstants.L1position);
}

public void toMidRung() {
climberPID.setSetpoint(ClimberConstants.L2position);
}

public void climbUp() {
climberPID.setSetpoint(climberEncoder.get() + 10);
}

private void toMidRung() {
public void climbDown() {
climberPID.setSetpoint(climberEncoder.get() - 10);
}

public void toHome() {
climberPID.setSetpoint(0);
}

private void climbUp() {
public void resetEncoder() {
climberMotor.getEncoder().setPosition(0);
climberPID.reset();
climberPID.setSetpoint(0);
}
Comment on lines +58 to +62

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

感覺有點怪怪的 你爬升用的是 dutycycle encoder 可是這裡 reset 的是 sparkMax 的


public Command toLowRungCmd() {
Command cmd = this.runEnd(() -> toLowRung(), () -> climberMotor.set(0));
cmd.setName("toLowRungCmd");
return cmd;
}

private void climbDown() {
public Command toMidRungCmd() {
Command cmd = this.runEnd(() -> toMidRung(), () -> climberMotor.set(0));
cmd.setName("toMidRungCmd");
return cmd;
}

public Command climbUpCmd() {
Command cmd = this.runEnd(() -> climbUp(), () -> climberMotor.set(0));
cmd.setName("climbUpCmd");
return cmd;
}

private void stopClimb() {
public Command climbDownCmd() {
Command cmd = this.runEnd(() -> climbDown(), () -> climberMotor.set(0));
cmd.setName("climbDownCmd");
return cmd;
}
Comment on lines +64 to +86
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

你希望這些 command 要怎麼動阿

Copy link
Author

@Gary123abc Gary123abc Feb 5, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

按著的時候就可以往上往下,然後放開就停在那個高度,toLowRung和toMidRung是按一下就可以到L1和L2的高度


public Command stopClimbCmd() {
Command cmd = this.runOnce(() -> this.climberMotor.set(0));
cmd.setName("toHomeCmd");
return cmd;
}

public Command resetEncoderCmd() {
Command cmd = this.runOnce(() -> resetEncoder());
cmd.setName("resetEncoderCmd");
return cmd;
}

@Override
public void periodic() {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

希望可以在不同的東西之間加上空行,會比較方便其他人閱讀。(可以分成取得目前位置、控制馬達、把東西放上 Dashboard)

// This method will be called once per scheduler run

double currentPosition = climberEncoder.get();
double pidOutput = climberPID.calculate(currentPosition);
double limitedOutput = MathUtil.clamp(pidOutput, -0.5, 0.5);
climberMotor.set(limitedOutput);
SmartDashboard.putNumber("climberPosition", climberEncoder.get());
SmartDashboard.putNumber("climberTarget", climberPID.getSetpoint());
}
}
171 changes: 171 additions & 0 deletions vendordeps/Phoenix5-5.36.0.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,171 @@
{
"fileName": "Phoenix5-5.36.0.json",
"name": "CTRE-Phoenix (v5)",
"version": "5.36.0",
"frcYear": "2026",
"uuid": "ab676553-b602-441f-a38d-f1296eff6537",
"mavenUrls": [
"https://maven.ctr-electronics.com/release/"
],
"jsonUrl": "https://maven.ctr-electronics.com/release/com/ctre/phoenix/Phoenix5-frc2026-latest.json",
"requires": [
{
"uuid": "e995de00-2c64-4df5-8831-c1441420ff19",
"errorMessage": "Phoenix 5 requires low-level libraries from Phoenix 6. Please add the Phoenix 6 vendordep before adding Phoenix 5.",
"offlineFileName": "Phoenix6-frc2026-latest.json",
"onlineUrl": "https://maven.ctr-electronics.com/release/com/ctre/phoenix6/latest/Phoenix6-frc2026-latest.json"
}
],
"conflictsWith": [
{
"uuid": "e7900d8d-826f-4dca-a1ff-182f658e98af",
"errorMessage": "Users must use the Phoenix 5 replay vendordep when using the Phoenix 6 replay vendordep.",
"offlineFileName": "Phoenix6-replay-frc2026-latest.json"
},
{
"uuid": "fbc886a4-2cec-40c0-9835-71086a8cc3df",
"errorMessage": "Users cannot have both the replay and regular Phoenix 5 vendordeps in their robot program.",
"offlineFileName": "Phoenix5-replay-frc2026-latest.json"
}
],
"javaDependencies": [
{
"groupId": "com.ctre.phoenix",
"artifactId": "api-java",
"version": "5.36.0"
},
{
"groupId": "com.ctre.phoenix",
"artifactId": "wpiapi-java",
"version": "5.36.0"
}
],
"jniDependencies": [
{
"groupId": "com.ctre.phoenix",
"artifactId": "cci",
"version": "5.36.0",
"isJar": false,
"skipInvalidPlatforms": true,
"validPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"linuxathena"
],
"simMode": "hwsim"
},
{
"groupId": "com.ctre.phoenix.sim",
"artifactId": "cci-sim",
"version": "5.36.0",
"isJar": false,
"skipInvalidPlatforms": true,
"validPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"osxuniversal"
],
"simMode": "swsim"
}
],
"cppDependencies": [
{
"groupId": "com.ctre.phoenix",
"artifactId": "wpiapi-cpp",
"version": "5.36.0",
"libName": "CTRE_Phoenix_WPI",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"linuxathena"
],
"simMode": "hwsim"
},
{
"groupId": "com.ctre.phoenix",
"artifactId": "api-cpp",
"version": "5.36.0",
"libName": "CTRE_Phoenix",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"linuxathena"
],
"simMode": "hwsim"
},
{
"groupId": "com.ctre.phoenix",
"artifactId": "cci",
"version": "5.36.0",
"libName": "CTRE_PhoenixCCI",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"linuxathena"
],
"simMode": "hwsim"
},
{
"groupId": "com.ctre.phoenix.sim",
"artifactId": "wpiapi-cpp-sim",
"version": "5.36.0",
"libName": "CTRE_Phoenix_WPISim",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"osxuniversal"
],
"simMode": "swsim"
},
{
"groupId": "com.ctre.phoenix.sim",
"artifactId": "api-cpp-sim",
"version": "5.36.0",
"libName": "CTRE_PhoenixSim",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"osxuniversal"
],
"simMode": "swsim"
},
{
"groupId": "com.ctre.phoenix.sim",
"artifactId": "cci-sim",
"version": "5.36.0",
"libName": "CTRE_PhoenixCCISim",
"headerClassifier": "headers",
"sharedLibrary": true,
"skipInvalidPlatforms": true,
"binaryPlatforms": [
"windowsx86-64",
"linuxx86-64",
"linuxarm64",
"osxuniversal"
],
"simMode": "swsim"
}
]
}
Loading
Loading