diff --git a/.github/labeler.yml b/.github/labeler.yml new file mode 100644 index 0000000000..c91083a5ba --- /dev/null +++ b/.github/labeler.yml @@ -0,0 +1,59 @@ +'2027': +- base-branch: '2027' +'component: apriltag': +- changed-files: + - any-glob-to-any-file: apriltag/** +'component: command-based': +- changed-files: + - any-glob-to-any-file: wpilibNewCommands/** +'component: cscore': +- changed-files: + - any-glob-to-any-file: cscore/** +'component: datalogtool': +- changed-files: + - any-glob-to-any-file: datalogtool/** +'component: epilogue': +- changed-files: + - any-glob-to-any-file: epilogue-*/** +'component: examples': +- changed-files: + - any-glob-to-any-file: wpilib*Examples/** +'component: examples': +- changed-files: + - any-glob-to-any-file: wpilib*Examples/** +'component: glass': +- changed-files: + - any-glob-to-any-file: glass/** +'component: hal': +- changed-files: + - any-glob-to-any-file: hal/** +'component: ntcore': +- changed-files: + - any-glob-to-any-file: ntcore/** +'component: outlineviewer': +- changed-files: + - any-glob-to-any-file: outlineviewer/** +'component: sysid': +- changed-files: + - any-glob-to-any-file: sysid/** +'component: teamnumbersetter': +- changed-files: + - any-glob-to-any-file: roborioteamnumbersetter/** +'component: wpilibc': +- changed-files: + - any-glob-to-any-file: wpilibc/** +'component: wpilibj': +- changed-files: + - any-glob-to-any-file: wpilibj/** +'component: wpimath': +- changed-files: + - any-glob-to-any-file: wpimath/** +'component: wpinet': +- changed-files: + - any-glob-to-any-file: wpinet/** +'component: wpiunits': +- changed-files: + - any-glob-to-any-file: wpiunits/** +'component: wpiutil': +- changed-files: + - any-glob-to-any-file: wpiutil/** diff --git a/.github/workflows/labeler.yml b/.github/workflows/labeler.yml new file mode 100644 index 0000000000..e57cd86e2b --- /dev/null +++ b/.github/workflows/labeler.yml @@ -0,0 +1,12 @@ +name: "Pull Request Labeler" +on: +- pull_request_target + +jobs: + labeler: + permissions: + contents: read + pull-requests: write + runs-on: ubuntu-latest + steps: + - uses: actions/labeler@v5 diff --git a/wpimath/src/main/native/include/frc/geometry/Rotation2d.h b/wpimath/src/main/native/include/frc/geometry/Rotation2d.h index 2c3c94540a..7cb7801e19 100644 --- a/wpimath/src/main/native/include/frc/geometry/Rotation2d.h +++ b/wpimath/src/main/native/include/frc/geometry/Rotation2d.h @@ -98,6 +98,43 @@ class WPILIB_DLLEXPORT Rotation2d { } } + /** + * Constructs a Rotation2d from a rotation matrix. + * + * @param rotationMatrix The rotation matrix. + * @throws std::domain_error if the rotation matrix isn't special orthogonal. + */ + constexpr explicit Rotation2d(const Eigen::Matrix2d& rotationMatrix) { + auto impl = + [](const Matrix2d& R) -> std::pair { + // Require that the rotation matrix is special orthogonal. This is true if + // the matrix is orthogonal (RRᵀ = I) and normalized (determinant is 1). + if ((R * R.transpose() - Matrix2d::Identity()).norm() > 1e-9) { + throw std::domain_error("Rotation matrix isn't orthogonal"); + } + if (gcem::abs(R.determinant() - 1.0) > 1e-9) { + throw std::domain_error( + "Rotation matrix is orthogonal but not special orthogonal"); + } + + // R = [cosθ −sinθ] + // [sinθ cosθ] + return {R(0, 0), R(1, 0)}; + }; + + if (std::is_constant_evaluated()) { + auto cossin = impl(ct_matrix2d{rotationMatrix}); + m_cos = std::get<0>(cossin); + m_sin = std::get<1>(cossin); + } else { + auto cossin = impl(rotationMatrix); + m_cos = std::get<0>(cossin); + m_sin = std::get<1>(cossin); + } + + m_value = units::radian_t{gcem::atan2(m_sin, m_cos)}; + } + /** * Adds two rotations together, with the result being bounded between -π and * π. diff --git a/wpiutil/build.gradle b/wpiutil/build.gradle index 5191e17e56..9846a49cc7 100644 --- a/wpiutil/build.gradle +++ b/wpiutil/build.gradle @@ -184,6 +184,12 @@ nativeUtils.exportsConfigs { } } +nativeUtils.platformConfigs.each { + if (it.name.contains('windows')) { + it.cppCompiler.args.add("/D_DISABLE_CONSTEXPR_MUTEX_CONSTRUCTOR") + } +} + cppHeadersZip { def thirdpartyIncDirs = [ 'src/main/native/thirdparty/argparse/include',