diff --git a/README.md b/README.md index abc5107..f1d5b84 100644 --- a/README.md +++ b/README.md @@ -16,7 +16,13 @@ 舵机位置约定: - 1.抓手夹紧位置为1800 + 抓手 + 1.夹紧位置为0 + 2.最大张开位置为300 + 3.垂直位置70 + 水平位置 + 初始位置为0 + 2.水平移动舵机初始化位置为200(处于设备最后端) diff --git a/src/main/java/a8k/a8k_can_protocol/A8kEcode.java b/src/main/java/a8k/a8k_can_protocol/A8kEcode.java index 19c4816..2caa6cf 100644 --- a/src/main/java/a8k/a8k_can_protocol/A8kEcode.java +++ b/src/main/java/a8k/a8k_can_protocol/A8kEcode.java @@ -23,6 +23,8 @@ public enum A8kEcode { ActionOvertime(17, "动作执行超时"),// CodeException(18, "代码异常"),// ShakeModGripperZMNotInZeroPos(19, "抓手升降电机没有在零位"),// + MNotInZeroPos(20, "电机没有在零点"),// + TubeXChannelIsNotEmpty(21, "试管架平移通道不为空"),// // // FOR HARDWARE diff --git a/src/main/java/a8k/a8k_can_protocol/RegIndex.java b/src/main/java/a8k/a8k_can_protocol/RegIndex.java index 39a815f..3c8dc37 100644 --- a/src/main/java/a8k/a8k_can_protocol/RegIndex.java +++ b/src/main/java/a8k/a8k_can_protocol/RegIndex.java @@ -149,7 +149,7 @@ public enum RegIndex { kreg_mini_servo_limit_velocity(10251), // 限制速度 kreg_mini_servo_limit_torque(10252), // 限制扭矩 kreg_mini_servo_protective_torque(10253), // 保护扭矩 - + kreg_mini_servo_is_move(10254), // 是否在运动 /*********************************************************************************************************************** * ID_CARD_READER * ***********************************************************************************************************************/ @@ -180,5 +180,4 @@ public enum RegIndex { } - } diff --git a/src/main/java/a8k/appbean/HardwareException.java b/src/main/java/a8k/appbean/HardwareException.java index c7d8698..45bef87 100644 --- a/src/main/java/a8k/appbean/HardwareException.java +++ b/src/main/java/a8k/appbean/HardwareException.java @@ -29,6 +29,13 @@ public class HardwareException extends Exception { this.cmdId = cmd; } + public HardwareException(A8kEcode ecode) { + super(String.format("Error code %s", ecode)); + this.errorCode = ecode; + this.moduleId = null; + this.cmdId = null; + } + public MId getModuleId() { return moduleId; } diff --git a/src/main/java/a8k/base_hardware/A8kCanBusService.java b/src/main/java/a8k/base_hardware/A8kCanBusService.java index 368d2be..1290466 100644 --- a/src/main/java/a8k/base_hardware/A8kCanBusService.java +++ b/src/main/java/a8k/base_hardware/A8kCanBusService.java @@ -203,11 +203,11 @@ public class A8kCanBusService { } public void moduleSetReg(MId id, RegIndex regindex, int reg) throws HardwareException { - callcmd(id.toInt(), CmdId.module_set_reg.toInt(), regindex.ordinal(), reg); + callcmd(id.toInt(), CmdId.module_set_reg.toInt(), regindex.index, reg); } public int moduleGetReg(MId id, RegIndex regindex) throws HardwareException { - var packet = callcmd(id.toInt(), CmdId.module_get_reg.toInt(), regindex.ordinal()); + var packet = callcmd(id.toInt(), CmdId.module_get_reg.toInt(), regindex.index); return packet.getContentI32(0); } @@ -318,8 +318,8 @@ public class A8kCanBusService { callcmd(id.toInt(), CmdId.step_motor_active_cfg.toInt()); } - public Boolean stepMotorReadIoState(MId id) throws HardwareException { - var packet = callcmd(id.toInt(), CmdId.step_motor_read_io_state.toInt()); + public Boolean stepMotorReadIoState(MId id, int ioindex) throws HardwareException { + var packet = callcmd(id.toInt(), CmdId.step_motor_read_io_state.toInt(), ioindex); return packet.getContentI32(0) != 0; } @@ -373,6 +373,21 @@ public class A8kCanBusService { callcmd(id.toInt(), CmdId.mini_servo_rotate_with_torque.toInt(), torque); } + public void miniServoWaitIsNotMove(MId id, int acitionOvertime) throws HardwareException, InterruptedException { + long startedAt = System.currentTimeMillis(); + do { + var isMove = moduleGetReg(id, RegIndex.kreg_mini_servo_is_move); + if (isMove != 0) { + break; + } + long now = System.currentTimeMillis(); + if (now - startedAt > acitionOvertime) { + throw new HardwareException(id, A8kEcode.Overtime); + } + Thread.sleep(100); + } while (true); + } + public Boolean getIOState(IOId ioid) throws HardwareException { if (ioid.mtype == ModuleType.kboard) { return callcmd(ioid.mid.toInt(), CmdId.extboard_read_inio.toInt(), ioid.ioIndex).getContentI32(0) != 0; @@ -415,6 +430,11 @@ public class A8kCanBusService { } + public void waitForMods(MId[] mids, Integer acitionOvertime) throws InterruptedException, HardwareException { + for (MId mid : mids) { + waitForMod(mid, acitionOvertime); + } + } public void waitForMod(MId mid, Integer acitionOvertime) throws InterruptedException, HardwareException { long startedAt = System.currentTimeMillis(); @@ -503,7 +523,7 @@ public class A8kCanBusService { // 调用sendCmd, // 如果捕获到超时异常,则重发,最多重发三次 // 如果是其他异常,则直接抛出异常。 - for (int i = 0; i < 3; i++) { + for (int i = 0; i < 5; i++) { try { return this.sendCmd(pack, A8kPacket.CMD_OVERTIME); } catch (HardwareException e) { @@ -511,8 +531,9 @@ public class A8kCanBusService { throw e; } } + } - return null; + throw new HardwareException(MId.valueOf(pack.getModuleId()), A8kEcode.Overtime); } public void callblockcmd(Integer moduleId, Integer cmdId, Integer[] params, int acitionOvertime) throws HardwareException, InterruptedException { diff --git a/src/main/java/a8k/service/ctrl_service/DeviceInitializationCtrlService.java b/src/main/java/a8k/service/ctrl_service/DeviceInitializationCtrlService.java index 2e96d75..8d49311 100644 --- a/src/main/java/a8k/service/ctrl_service/DeviceInitializationCtrlService.java +++ b/src/main/java/a8k/service/ctrl_service/DeviceInitializationCtrlService.java @@ -8,6 +8,7 @@ import a8k.appbean.ecode.AppRet; import a8k.base_hardware.A8kCanBusService; import a8k.service.db.dao.SamplesPreProcessModuleCtrlParamsService; import a8k.service.hardware.CommonHardwareOpeartion; +import a8k.service.hardware.SamplesPreProcessModuleCtrlService; import jakarta.annotation.Resource; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -30,7 +31,7 @@ public class DeviceInitializationCtrlService { CommonHardwareOpeartion commonHardOpera; @Resource - SamplesPreProcessModuleCtrlParamsService samplesPreProcessModuleCtrlParams; + SamplesPreProcessModuleCtrlService samplesPreProcessModuleCtrlService; @PostMapping("/api/DeviceInitializationCtrlService/initializeDevice") @@ -116,7 +117,7 @@ public class DeviceInitializationCtrlService { if (canBus.getIOState(IOId.THChInterPPS) || canBus.getIOState(IOId.THChOuterPPS)) { logger.warn("THChInterPPS or THChOuterPPS is trigger"); // throw new HardwareException(MId.A8kIdCardReaderBoard, A8kEcode.PlateStuckDetectorSensorTrigger); - return AppRet.fail(A8kEcode.PlateStuckDetectorSensorTrigger); + return AppRet.fail(A8kEcode.TubeXChannelIsNotEmpty); } //板夹仓盖子是否盖上 @@ -163,11 +164,13 @@ public class DeviceInitializationCtrlService { //摇匀模组初始化 - canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, 1800); + + + canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, 10); canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, actionOvertime); - canBus.miniServoMoveTo(MId.ShakeModGripperSV, 1800); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, 10); canBus.waitForMod(MId.ShakeModGripperSV, actionOvertime); - canBus.miniServoMoveTo(MId.ShakeModGripperYSV, 200); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, 10); canBus.waitForMod(MId.ShakeModGripperYSV, actionOvertime); canBus.stepMotorEasyMoveToZero(MId.ShakeModClampingM); @@ -177,6 +180,8 @@ public class DeviceInitializationCtrlService { canBus.stepMotorEasyMoveToZero(MId.ShakeModShakeM); canBus.waitForMod(MId.ShakeModShakeM, actionOvertime); + canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM,90); + //canBus.miniServoMoveTo(MId.ShakeModTubeScanerRotateSV, 1800); //板夹仓初始化 diff --git a/src/main/java/a8k/service/hardware/HardwareCtrlModule.java b/src/main/java/a8k/service/hardware/HardwareCtrlModule.java new file mode 100644 index 0000000..0a7d17d --- /dev/null +++ b/src/main/java/a8k/service/hardware/HardwareCtrlModule.java @@ -0,0 +1,34 @@ +package a8k.service.hardware; + +import a8k.appbean.HardwareException; +import a8k.appbean.ecode.AppRet; + +public interface HardwareCtrlModule { + /** + * 模块使能 + * @param enable 1:使能 0:禁用 + * @throws HardwareException 硬件异常 + */ + public void modGroupEnable(Boolean enable) throws HardwareException, InterruptedException; + + /** + * 模块停止 + * @throws HardwareException 硬件异常 + */ + public void modGroupStop() throws HardwareException; + + /** + * 电机归零 + * @throws HardwareException 硬件异常 + * @throws InterruptedException 打断异常 + */ + public void modGroupMoveToZero() throws HardwareException, InterruptedException; + + /** + * 电机快速归零 + * @throws HardwareException 硬件异常 + * @throws InterruptedException 打断异常 + */ + public void modGroupMoveToZeroQuick() throws HardwareException, InterruptedException; + +} diff --git a/src/main/java/a8k/service/hardware/MotorTubeRackMoveCtrlService.java b/src/main/java/a8k/service/hardware/MotorTubeRackMoveCtrlService.java index 8a5cf03..863da5a 100644 --- a/src/main/java/a8k/service/hardware/MotorTubeRackMoveCtrlService.java +++ b/src/main/java/a8k/service/hardware/MotorTubeRackMoveCtrlService.java @@ -12,7 +12,7 @@ import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; @Component -public class MotorTubeRackMoveCtrlService { +public class MotorTubeRackMoveCtrlService implements HardwareCtrlModule { /** * * 主要用来控制试管架的平移动作控制 @@ -40,45 +40,7 @@ public class MotorTubeRackMoveCtrlService { private CommonHardwareOpeartion comHardwareOpear; /*========================================================================================= - * 基础方法 - *========================================================================================*/ - - /** - * 移动试管架到指定位置 - * @param pos 指定位置 - * @throws HardwareException 硬件异常 - * @throws InterruptedException 打断异常 - */ - public AppRet moveTubeRackTo(int pos) throws HardwareException, InterruptedException { - if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM)) { - return AppRet.fail(A8kEcode.ShakeModGripperZMNotInZeroPos); - } - scanClampModRelease(); - - canBus.stepMotorEasyMoveTo(MId.FeedingModXM, pos); - canBus.waitForMod(MId.FeedingModXM, paramDao.getActionOvertime()); - return AppRet.success(); - } - - /** - * 扫描夹紧机构夹紧 - */ - public void scanClampModClamp() throws HardwareException, InterruptedException { - canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, paramDao.getScanCodeClampPos()); - canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, paramDao.getActionOvertime()); - } - - /** - * 扫描夹紧机构复位 - */ - public void scanClampModRelease() throws HardwareException, InterruptedException { - canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, paramDao.getScanCodeReleasePos()); - canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, paramDao.getActionOvertime()); - } - - - /*========================================================================================= - * 公共方法 + * Overrid *========================================================================================*/ /** @@ -86,68 +48,95 @@ public class MotorTubeRackMoveCtrlService { * @param enable 1:使能 0:禁用 * @throws HardwareException 硬件异常 */ - public AppRet modGroupEnable(Boolean enable) throws HardwareException { + @Override + public void modGroupEnable(Boolean enable) throws HardwareException { comHardwareOpear.enableAllMotor(enable); - return AppRet.success(); } /** * 模块停止 * @throws HardwareException 硬件异常 */ + @Override public void modGroupStop() throws HardwareException { comHardwareOpear.forceStopAllMOtor(); } - - public AppRet modGroupMoveToZero() throws HardwareException, InterruptedException { - if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM)) { - return AppRet.fail(A8kEcode.ShakeModGripperZMNotInZeroPos); + @Override + public void modGroupMoveToZero() throws HardwareException, InterruptedException { + if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM, 0)) { + throw new HardwareException(A8kEcode.ShakeModGripperZMNotInZeroPos); } canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, paramDao.getScanCodeReleasePos()); canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, paramDao.getActionOvertime()); canBus.stepMotorEasyMoveToZero(MId.FeedingModXM); canBus.waitForMod(MId.FeedingModXM, paramDao.getActionOvertime()); - return AppRet.success(); } + @Override + public void modGroupMoveToZeroQuick() throws HardwareException, InterruptedException { + moveTubeRackTo(0); + canBus.stepMotorEasyMoveToZero(MId.FeedingModXM); + canBus.waitForMod(MId.FeedingModXM, paramDao.getActionOvertime()); + + } + + /*========================================================================================= + * 基础方法 + *========================================================================================*/ + /** - * 电机归零,电机运行时归零,特点是通过归零判断设备是否丢步 + * 移动试管架到指定位置 + * @param pos 指定位置 * @throws HardwareException 硬件异常 * @throws InterruptedException 打断异常 */ - public AppRet modGroupMoveToZeroQuick() throws HardwareException, InterruptedException { - var ret = moveTubeRackTo(0); - if (!ret.isSuccess()) { - return AppRet.fail(ret); + public void moveTubeRackTo(int pos) throws HardwareException, InterruptedException { + if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM, 0)) { + throw new HardwareException(A8kEcode.ShakeModGripperZMNotInZeroPos); } + scanClampModRelease(); - moveTubeRackTo(0); - canBus.stepMotorEasyMoveToZero(MId.FeedingModXM); + canBus.stepMotorEasyMoveTo(MId.FeedingModXM, pos); canBus.waitForMod(MId.FeedingModXM, paramDao.getActionOvertime()); + } - return AppRet.success(); + /** + * 扫描夹紧机构夹紧 + */ + public void scanClampModClamp() throws HardwareException, InterruptedException { + canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, paramDao.getScanCodeClampPos()); + canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, paramDao.getActionOvertime()); + } + + /** + * 扫描夹紧机构复位 + */ + public void scanClampModRelease() throws HardwareException, InterruptedException { + canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, paramDao.getScanCodeReleasePos()); + canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, paramDao.getActionOvertime()); } + /** * 移动试管架到入口位置 */ - public AppRet tubeRackMoveToEnterPos() throws HardwareException, InterruptedException { - return moveTubeRackTo(paramDao.getTubeRackEnterPos()); + public void tubeRackMoveToEnterPos() throws HardwareException, InterruptedException { + moveTubeRackTo(paramDao.getTubeRackEnterPos()); } /** * 移动试管架到出口位置 */ - public AppRet moveTubeRackToExitPos() throws HardwareException, InterruptedException { - return moveTubeRackTo(paramDao.getTubeRackExitPos()); + public void moveTubeRackToExitPos() throws HardwareException, InterruptedException { + moveTubeRackTo(paramDao.getTubeRackExitPos()); } /** * 移动试管架到试管架扫码位置 */ - public AppRet moveTubeRackToScanPos() throws HardwareException, InterruptedException { - return moveTubeRackTo(paramDao.getTubeRackScanCodePos()); + public void moveTubeRackToScanPos() throws HardwareException, InterruptedException { + moveTubeRackTo(paramDao.getTubeRackScanCodePos()); } /** @@ -155,10 +144,8 @@ public class MotorTubeRackMoveCtrlService { */ public AppRet moveTubeRackToScanPosAndScan() throws HardwareException, InterruptedException { String result; - var ret = moveTubeRackToScanPos(); - if (!ret.isSuccess()) { - return AppRet.fail(ret); - } + moveTubeRackToScanPos(); + scanClampModClamp(); canBus.codeScanerStartScan(MId.FeedingModScannerMod); result = canBus.codeScanerWaittingForResult(MId.FeedingModScannerMod, 1000); diff --git a/src/main/java/a8k/service/hardware/ReactionPlatesTransmitCtrlService.java b/src/main/java/a8k/service/hardware/ReactionPlatesTransmitCtrlService.java index 99ca7fa..a0aff07 100644 --- a/src/main/java/a8k/service/hardware/ReactionPlatesTransmitCtrlService.java +++ b/src/main/java/a8k/service/hardware/ReactionPlatesTransmitCtrlService.java @@ -40,8 +40,7 @@ public class ReactionPlatesTransmitCtrlService { //试管平移通道是否有障碍 if (canBus.getIOState(IOId.THChInterPPS) || canBus.getIOState(IOId.THChOuterPPS)) { logger.warn("THChInterPPS or THChOuterPPS is trigger"); - // throw new HardwareException(MId.A8kIdCardReaderBoard, A8kEcode.PlateStuckDetectorSensorTrigger); - return AppRet.fail(A8kEcode.PlateStuckDetectorSensorTrigger); + return AppRet.fail(A8kEcode.TubeXChannelIsNotEmpty); } //板夹仓卡板检测 if (canBus.getIOState(IOId.PlateBoxPlateStuckPPS)) { diff --git a/src/main/java/a8k/service/hardware/SamplesPreProcessModuleCtrlService.java b/src/main/java/a8k/service/hardware/SamplesPreProcessModuleCtrlService.java index d50f5c7..fa00e74 100644 --- a/src/main/java/a8k/service/hardware/SamplesPreProcessModuleCtrlService.java +++ b/src/main/java/a8k/service/hardware/SamplesPreProcessModuleCtrlService.java @@ -1,486 +1,602 @@ package a8k.service.hardware; -import a8k.a8k_can_protocol.CmdId; import a8k.a8k_can_protocol.A8kEcode; import a8k.a8k_can_protocol.MId; import a8k.appbean.A8kTubeType; import a8k.appbean.HardwareException; +import a8k.appbean.ecode.AppRet; import a8k.base_hardware.A8kCanBusService; -import a8k.service.db.dao.A8kTubeInfoDao; -import a8k.service.db.dao.SamplesPreProcessModuleCtrlParamsService; import com.iflytop.uf.util.UfCommon; import jakarta.annotation.Resource; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; +import org.springframework.stereotype.Controller; +import org.springframework.web.bind.annotation.*; + +@Controller +public class SamplesPreProcessModuleCtrlService implements HardwareCtrlModule { + static Logger logger = LoggerFactory.getLogger(SamplesPreProcessModuleCtrlService.class); -@Component -public class SamplesPreProcessModuleCtrlService { - @Resource - A8kTubeInfoDao tubeInfoDao; @Resource - private A8kCanBusService a8kCanBusService; + private A8kCanBusService canBus; + @Resource - private SamplesPreProcessModuleCtrlParamsService samplesPreProcessModuleCtrlParamsService; - /* - 样品预处理模块 - 主要负责样品预处理的相关操作 + private CommonHardwareOpeartion comHardwareOpear; + @Autowired + private CommonHardwareOpeartion commonHardwareOpeartion; - */ + final private int actionDelayTime = 0; + final private Boolean debug = true; - /* ======================================================================================= - 基础方法 - =======================================================================================*/ + // + // 参数 + // - /** - * 按照一定顺序归零设备 - */ - public void moveToZero() throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); + public Integer getActionOvertime() { + return 5000; + } - /* - 1. 假设没有试管在当前设备上的前提下归零设备 - 2. 舵机虽然没有零位,但需要将其移动到待机位置 - */ + public Integer getGripperOpenPos() { + return 150; } - /** - * 使能模组 - * @param enable 是否使能模组 - */ - public void enableModule(Boolean enable) throws HardwareException { - this.a8kCanBusService.callcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_enable.toInt(), - enable ? 1 : 0 - ); - this.a8kCanBusService.callcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_enable.toInt(), - enable ? 1 : 0 - ); - this.a8kCanBusService.callcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_enable.toInt(), - enable ? 1 : 0 - ); - this.a8kCanBusService.callcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_enable.toInt(), - enable ? 1 : 0 - ); - this.a8kCanBusService.callcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_enable.toInt(), - enable ? 1 : 0 - ); - this.a8kCanBusService.stepMotorEnable(MId.ShakeModGripperZM, enable ? 1 : 0); + public Integer getGripperClosePos() { + return 10; } + public Integer getGripperTakeCapPos() { + return 50;//垂直张开 + } + public Integer getGripperTakeTubePos() { + return 300;// + } + public Integer getGripperTakeTubeYPos() { + return 2717; + } + public Integer getGripperShakeYPos() { + return 1778; + } - /* ======================================================================================= - 主要服务 - =======================================================================================*/ + public Integer getGripperZeroYPos() { + return 10; + } + // TakeTubeZ + public Integer getGripperTakeHTubeZPos() { + return 739 - 20; + } - /** - * 取试管帽,如果试管帽存在, - * @param tubeType TubeType_HighBlood,TubeType_ShortBlood,TubeType_Mini,TubeType_MiniBlood,TubeType_BulletTube1P5,TubeType_BulletTube0P5 - * @param judgeCapExist 是否判断试管帽子存在与否 - */ - public A8kEcode takeTube(String tubeType, Boolean judgeCapExist) throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_takeCapPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getTubeClampMotor_standbyPos(), - params.getActionOvertime() - ); - - var motorUdTubeTaskPos = params.getZMotor_ShortBloodTakeTubeHeight(); - var tubeTypeValue = A8kTubeType.valueOf(tubeType); - if ( tubeTypeValue.equals(A8kTubeType.HighBlood) ) { - motorUdTubeTaskPos = params.getZMotor_HighBloodTakeTubeHeight(); - } - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - motorUdTubeTaskPos, - params.getActionOvertime() - ); - - if ( judgeCapExist ) { - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.mini_servo_rotate_with_torque.toInt(), - params.getGripperServo_takeCapTorque(), - params.getActionOvertime() - ); - this.a8kCanBusService.callcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_stop.toInt() - ); - var pos = this.a8kCanBusService.callcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_read_pos.toInt() - ); - if ( pos.getContentI32(0) > params.getGripperServo_hatDeterminesPosThres() ) { - return A8kEcode.TubeNotHasHat; - } - } + public Integer getGripperTakeSTubeZPos() { + return 980 - 20; + } - this.a8kCanBusService.callcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_rotate_with_torque.toInt(), - params.getGripperServo_takeCapTorque() - ); - UfCommon.delay(2000); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_takePushCapPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getZMotor_placeShakeHeight(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getTubeClampMotor_ClampPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); + //JudgeTubeCapZ + public Integer getGripperJudgeHTubeCapZPos() { + return 591; + } + public Integer getGripperJudgeSTubeCapZPos() { + return 867; + } - /* - 注意事项: - 1. 取试管并将试管放在试管夹紧位置,同时升降电机和平移电机移动到待机位 - 2. 试管放置的水平高度和其在试管架中的高度保持一直 - 3. 取试管前,先通过试管夹紧功能判断一下试管帽是否存在(在试管没帽的边沿位置,抓手扭矩抓紧,如果等待一定时间后,抓手位置接近极限位置,则认为没有帽子,返回TubeNotHasHat错误) - 4. 无论是否抓取成功,只要不向外抛出异常,方法结束时,该模块涉及到组件均需要返回待机位置。 - */ + //ShakeTubeZ + public Integer getGripperShakeTubeZPos() { + return 835 - 20; + } - return A8kEcode.Success; + //TakeCapZ + public Integer getGripperTakeCapZPos() { + return 835; } - /** - * 取试管帽 - */ - public A8kEcode takeTubeCap( String tubeType ) throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_takePushCapPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - - var motorUdTakeCapPos = params.getZMotor_ShortBloodTakeCapHeight(); - var tubeTypeValue = A8kTubeType.valueOf(tubeType); - if ( tubeTypeValue.equals(A8kTubeType.HighBlood) ) { - motorUdTakeCapPos = params.getZMotor_HighBloodTakeCapHeight(); - } - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - motorUdTakeCapPos, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_takeTubePos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); - return A8kEcode.Success; + public Integer getShakeClampingPos() { + return 10; } - /** - * 盖试管帽,并将试管移动回试管架中 - */ - public void pushBackTubeCapAndTakeBakTube(String tubeType) throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getHorizontalMotor_takePushCapPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - - var motorUdTakeCapPos = params.getZMotor_ShortBloodTakeCapHeight(); - var tubeTypeValue = A8kTubeType.valueOf(tubeType); - if ( tubeTypeValue.equals(A8kTubeType.HighBlood) ) { - motorUdTakeCapPos = params.getZMotor_HighBloodTakeCapHeight(); + // + public Integer getShakeModShakeMStandbyPos() { + return 90; + } + + + /*========================================================================================= + * Overrid + *========================================================================================*/ + + @PostMapping(value = "/api/SamplesPreProcessModuleCtrlService/modGroupEnable") + @ResponseBody + @Override + public void modGroupEnable(Boolean enable) throws HardwareException, InterruptedException { + if (enable) { + this.comHardwareOpear.enableAllMotor(); + + } else { + canBus.stepMotorEnable(MId.ShakeModClampingM, 1); + canBus.stepMotorEasyMoveBy(MId.ShakeModClampingM, 10); + canBus.waitForMod(MId.ShakeModClampingM, getActionOvertime()); + comHardwareOpear.disableAllMotor(); } - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - motorUdTakeCapPos, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getActionOvertime() - ); - - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); } + @Override + public void modGroupStop() throws HardwareException { + comHardwareOpear.forceStopAllMOtor(); + } - /* ======================================================================================= - 辅助操作 - =======================================================================================*/ + @PostMapping(value = "/api/SamplesPreProcessModuleCtrlService/modGroupMoveToZero") + @ResponseBody + @Override + public void modGroupMoveToZero() throws HardwareException, InterruptedException { + // if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM, 0)) { + // throw new HardwareException(A8kEcode.ShakeModGripperZMNotInZeroPos); + // } + + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperClosePos());//此步骤,除了归零的同时还能够检测是否有试管在夹爪中 + canBus.waitForMod(MId.ShakeModGripperSV, getActionOvertime()); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperZeroYPos()); + canBus.waitForMod(MId.ShakeModGripperYSV, getActionOvertime()); + + canBus.stepMotorEasyMoveToZero(MId.ShakeModClampingM); + canBus.waitForMod(MId.ShakeModClampingM, getActionOvertime()); + canBus.stepMotorEasyMoveToZero(MId.ShakeModGripperZM); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + canBus.stepMotorEasyMoveToZero(MId.ShakeModShakeM); + canBus.waitForMod(MId.ShakeModShakeM, getActionOvertime()); + + canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM, 90); + canBus.waitForMod(MId.ShakeModShakeM, getActionOvertime()); + + canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, -2); + } - /** - * 摇匀试管 - * @param tubeType TubeType_HighBlood,TubeType_ShortBlood,TubeType_Mini,TubeType_MiniBlood,TubeType_BulletTube1P5,TubeType_BulletTube0P5 - * @param times 摇匀次数 - * @param shakeDegree 摇匀角度 - */ - public void ShakeTube(String tubeType, Integer times, Integer shakeDegree) throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - var standByPos = params.getShakeMotor_standbyPos(); - var startPos = standByPos - shakeDegree/2; - var endPos = standByPos + shakeDegree/2; - this.a8kCanBusService.callblockcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_easy_reciprocating_motion.toInt(), - startPos, - endPos, - times, - params.getActionOvertime() - ); + + @Override + public void modGroupMoveToZeroQuick() throws HardwareException, InterruptedException { + /* + * 1.Z轴回到零位 + * 2.试管夹紧回到零位 + * 3.摇匀回到零位 + */ + + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, 0); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + + canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, 0); + canBus.waitForMod(MId.ShakeModClampingM, getActionOvertime()); + + canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM, 0); + canBus.waitForMod(MId.ShakeModShakeM, getActionOvertime()); + + modGroupMoveToZero(); } - /** - * 打开气溶胶风扇 - */ - public void openAerosolFan() throws HardwareException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callcmd(MId.WbTubeFanMod.toInt(), CmdId.fan_controler_set_speed.toInt(), params.getAerosolFanLevel()); + Boolean IntEq(Integer pos1, Integer pos2, Integer diff) { + return Math.abs(pos1 - pos2) < diff; } - /** - * 关闭气溶胶风扇 - */ - public void closeAerosolFan() throws HardwareException { - this.a8kCanBusService.callcmd(MId.WbTubeFanMod.toInt(), CmdId.fan_controler_set_speed.toInt(), 0); + + void actionDelay() throws InterruptedException { + if (actionDelayTime != 0) + Thread.sleep(actionDelayTime); } + /** - * 设备初始化时复位 + * 取试管帽,如果试管帽存在, + * @param tubeType HighBlood,ShortBlood,Mini,MiniBlood,BulletTube1P5,BulletTube0P5 + * @param actionDealyTime 为true时,为不带试管测试,且步骤之间有1s的动作延迟 */ - public void moduleResetWhenPowerOn() throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.stepMotorEasyMoveTo(MId.ShakeModClampingM, params.getTubeClampMotor_standbyPos()); - this.a8kCanBusService.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); - this.a8kCanBusService.stepMotorEasyMoveTo(MId.ShakeModShakeM, params.getShakeMotor_standbyPos()); - this.a8kCanBusService.waitForMod(MId.ShakeModShakeM, params.getActionOvertime()); + @PostMapping(value = "/api/SamplesPreProcessModuleCtrlService/takeTubeAndJudgeTubeExist") + @ResponseBody + public AppRet takeTubeAndJudgeTubeExist(@RequestParam String tubeType) throws HardwareException, InterruptedException { + logger.info("takeTube tubeType:{}", tubeType); + + /* + * 校验: + * 1.当前摇匀模组设计到的电机是否都处于待机位 + */ + + //Z轴在原点 + if (!canBus.stepMotorReadIoState(MId.ShakeModGripperZM, 0)) { + throw new HardwareException(MId.ShakeModGripperZM, A8kEcode.MNotInZeroPos); + } + + //Y轴在零点附近 + if (!IntEq(canBus.miniServoReadPos(MId.ShakeModGripperYSV), getGripperZeroYPos(), 30)) { + throw new HardwareException(MId.ShakeModGripperYSV, A8kEcode.MNotInZeroPos); + } + + //夹爪没有零位置 + if (!IntEq(canBus.miniServoReadPos(MId.ShakeModGripperSV), getGripperClosePos(), 30)) { + throw new HardwareException(MId.ShakeModGripperSV, A8kEcode.MNotInZeroPos); + } + + //检查摇匀夹紧是否在零位 + if (!canBus.stepMotorReadIoState(MId.ShakeModClampingM, 0)) { + throw new HardwareException(MId.ShakeModClampingM, A8kEcode.MNotInZeroPos); + } + + boolean isHighBlood = A8kTubeType.HighBlood.equals(A8kTubeType.valueOf(tubeType)); + boolean tubeCapExist = true; + Integer gripperJudgeCapZPos = isHighBlood ? getGripperJudgeHTubeCapZPos() : getGripperJudgeSTubeCapZPos(); + Integer gripperTakeTubeZPos = isHighBlood ? getGripperTakeHTubeZPos() : getGripperTakeSTubeZPos(); + Integer gripperShakeZPos = getGripperShakeTubeZPos(); + + //固定试管架 + logger.info("固定试管架"); + canBus.miniServoMoveTo(MId.ShakeModTubeScanerClampingSV, 900); + canBus.waitForMod(MId.ShakeModTubeScanerClampingSV, getActionOvertime()); + actionDelay(); + + //试管夹紧移动到终点位置 + logger.info("试管夹紧移动到终点位置"); + canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, 60); + canBus.waitForMod(MId.ShakeModClampingM, getActionOvertime()); + actionDelay(); + + + //试管摇匀移动到90度 + logger.info("试管摇匀移动到90度"); + canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM, getShakeModShakeMStandbyPos()); + canBus.waitForMod(MId.ShakeModShakeM, getActionOvertime()); + actionDelay(); + + + //Y轴向前移动 + logger.info("夹爪Y轴移动到取试管位置"); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperTakeTubeYPos()); + canBus.waitForMod(MId.ShakeModGripperYSV, getActionOvertime()); + actionDelay(); + + //打开夹爪 + logger.info("打开抓手"); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperOpenPos()); + canBus.waitForMod(MId.ShakeModGripperSV, getActionOvertime()); + actionDelay(); + + //Z轴下移动到试管帽有无检测位 + logger.info("Z轴下移动到试管帽有无检测位"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, gripperJudgeCapZPos); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //闭合夹爪检测试管帽是否存在 + logger.info("闭合夹爪检测试管帽是否存在"); + canBus.miniServoRotateWithTorque(MId.ShakeModGripperSV, -400); + Thread.sleep(1000); + if (IntEq(canBus.miniServoReadPos(MId.ShakeModGripperSV), getGripperClosePos(), 30)) { + logger.info("试管帽不存在"); + tubeCapExist = false; + } + actionDelay(); + + if (debug || tubeCapExist) { + //打开夹爪 + logger.info("打开夹爪"); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperOpenPos()); + canBus.waitForMod(MId.ShakeModGripperSV, getActionOvertime()); + actionDelay(); + + + //Z轴下移动到取试管位置 + logger.info("Z轴下移动到取试管位置"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, gripperTakeTubeZPos); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + + //夹爪夹紧 + logger.info("夹爪夹紧"); + canBus.miniServoRotateWithTorque(MId.ShakeModGripperSV, -getGripperTakeTubeTorque()); + canBus.miniServoWaitIsNotMove(MId.ShakeModGripperSV, getActionOvertime()); + actionDelay(); + + + //Z轴上移动到零位 + logger.info("Z轴上移动到零位"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, 0); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //Y轴移动到摇匀位 + logger.info("Y轴移动到摇匀位"); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperShakeYPos()); + canBus.waitForMod(MId.ShakeModGripperYSV, getActionOvertime()); + actionDelay(); + + //Z轴下移动到摇匀位放试管的位置 + logger.info("Z轴下移动到摇匀位放试管的位置"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, gripperShakeZPos); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //夹紧试管 + logger.info("夹紧试管"); + canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, getShakeClampingPos()); + canBus.waitForMod(MId.ShakeModClampingM, getActionOvertime()); + actionDelay(); + + //松开夹爪,放置试管 + logger.info("松开夹爪,放置试管"); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperOpenPos()); + canBus.waitForMod(MId.ShakeModGripperSV, getActionOvertime()); + actionDelay(); + + //Z轴上移动到零位 + logger.info("Z轴上移动到零位"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, 0); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //Z轴归零,校准一次位置 + logger.info("Z轴归零"); + canBus.stepMotorEasyMoveToZero(MId.ShakeModGripperZM); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //Y轴移动到零位 + logger.info("Y轴移动到零位"); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperZeroYPos()); + canBus.waitForMod(MId.ShakeModGripperYSV, getActionOvertime()); + actionDelay(); + + } else { + modGroupMoveToZeroQuick(); + } + return AppRet.success(tubeCapExist); //Z轴下移动试管判断的位置 } - /** - * 设备运行时复位 - */ - public void moduleRuntimeReset() throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getGripperServo_standbyPos(), - params.getActionOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperZM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModGripperYSV.toInt(), - CmdId.mini_servo_move_to.toInt(), - params.getHorizontalMotor_standbyPos(), - params.getActionOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModClampingM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_easy_move_to.toInt(), - 0, - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.callblockcmd( - MId.ShakeModShakeM.toInt(), - CmdId.step_motor_easy_move_to_zero.toInt(), - params.getMoveToZeroOvertime() - ); - this.a8kCanBusService.stepMotorEasyMoveTo(MId.ShakeModClampingM, params.getTubeClampMotor_standbyPos()); - this.a8kCanBusService.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); - this.a8kCanBusService.stepMotorEasyMoveTo(MId.ShakeModShakeM, params.getShakeMotor_standbyPos()); - this.a8kCanBusService.waitForMod(MId.ShakeModShakeM, params.getActionOvertime()); + + @PostMapping(value = "/api/SamplesPreProcessModuleCtrlService/shakeTube") + @ResponseBody + public void shakeTube(@RequestParam Integer shakeDegree, @RequestParam Integer times) throws HardwareException, InterruptedException { + var standByPos = getShakeModShakeMStandbyPos(); + var startPos = standByPos - shakeDegree; + var endPos = standByPos + shakeDegree; + canBus.stepMotorEasyReciprocatingMotion(MId.ShakeModShakeM, startPos, endPos, times); + canBus.waitForMod(MId.ShakeModShakeM, getActionOvertime()); } - public void openTubeClip() throws HardwareException, InterruptedException { - var params = this.samplesPreProcessModuleCtrlParamsService; - this.a8kCanBusService.stepMotorEasyMoveBy(MId.ShakeModClampingM, 10); - this.a8kCanBusService.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); + @PostMapping(value = "/api/SamplesPreProcessModuleCtrlService/takeTubeCap") + @ResponseBody + public void takeTubeCap() throws HardwareException, InterruptedException { + //Y移动到取试管帽位置 + logger.info("Y移动到取试管帽位置 && 打开夹爪"); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperShakeYPos()); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperOpenPos()); + canBus.waitForMods(new MId[]{MId.ShakeModGripperYSV, MId.ShakeModGripperSV}, getActionOvertime()); + actionDelay(); + + //Z下移动到取试管帽位置 + logger.info("Z下移动到取试管帽位置"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, getGripperTakeHTubeZPos()); + canBus.waitForMod(MId.ShakeModGripperZM, getActionOvertime()); + actionDelay(); + + //闭合夹爪 + logger.info("闭合夹爪"); + canBus.miniServoMoveTo(MId.ShakeModGripperSV, getGripperTakeCapPos()); + canBus.waitForMod(MId.ShakeModGripperSV, getActionOvertime()); + + //Z上移动到零位 + logger.info("Z上移动到零位"); + canBus.stepMotorEasyMoveTo(MId.ShakeModGripperZM, 0); + canBus.waitForMods(new MId[]{MId.ShakeModGripperZM}, getActionOvertime()); + + //Y移动到待机位 + logger.info("Y移动到待机位"); + canBus.miniServoMoveTo(MId.ShakeModGripperYSV, getGripperZeroYPos()); + canBus.waitForMods(new MId[]{MId.ShakeModGripperYSV}, getActionOvertime()); } + + // /* ======================================================================================= + // 主要服务 + // =======================================================================================*/ + // + // + // /* + // * 整体流程: + // * 1.试管(只有全血试管,才取试管) + // * 2.GripperYSM移动到取试管的位置 + // * 3.打开夹爪 + // * 4.ZM下移动到试管帽有无检测位,检测试管帽有无 + // * 5.ZM下移动到取试管位置,取试管 + // * 6.ZM上移到零位,同时判断是否发生丢步 + // * 7.YSM移动到摇匀位 + // * 8.ZM下移动到摇匀位放试管的位置 + // * 9.放置试管 + // * + // * 夹爪打开(夹爪打开为待机位),ZM,YSM,回零, + // */ + // + // + // /** + // * 取试管帽,如果试管帽存在, + // * @param tubeType HighBlood,ShortBlood,Mini,MiniBlood,BulletTube1P5,BulletTube0P5 + // * @param judgeCapExist 是否判断试管帽子存在与否 + // */ + // public A8kEcode takeTube(String tubeType, Boolean judgeCapExist) throws HardwareException, InterruptedException { + // logger.info("takeTube {} {}", tubeType, judgeCapExist); + // + // /* + // * check: + // * 1.当前摇匀模组设计到的电机是否都处于待机位 + // * + // * step: + // * + // * + // * + // * + // */ + // + // + // var params = this.paramDao; + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_takeCapPos(), params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getTubeClampMotor_standbyPos(), params.getActionOvertime()); + // + // var motorUdTubeTaskPos = params.getZMotor_ShortBloodTakeTubeHeight(); + // var tubeTypeValue = A8kTubeType.valueOf(tubeType); + // if (tubeTypeValue.equals(A8kTubeType.HighBlood)) { + // motorUdTubeTaskPos = params.getZMotor_HighBloodTakeTubeHeight(); + // } + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), motorUdTubeTaskPos, params.getActionOvertime()); + // + // if (judgeCapExist) { + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.mini_servo_rotate_with_torque.toInt(), params.getGripperServo_takeCapTorque(), params.getActionOvertime()); + // this.canBus.callcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_stop.toInt()); + // var pos = this.canBus.callcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_read_pos.toInt()); + // if (pos.getContentI32(0) > params.getGripperServo_hatDeterminesPosThres()) { + // return A8kEcode.TubeNotHasHat; + // } + // } + // + // this.canBus.callcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_rotate_with_torque.toInt(), params.getGripperServo_takeCapTorque()); + // UfCommon.delay(2000); + // + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_takePushCapPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getZMotor_placeShakeHeight(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getTubeClampMotor_ClampPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_standbyPos(), params.getActionOvertime()); + // /* + // 注意事项: + // 1. 取试管并将试管放在试管夹紧位置,同时升降电机和平移电机移动到待机位 + // 2. 试管放置的水平高度和其在试管架中的高度保持一直 + // 3. 取试管前,先通过试管夹紧功能判断一下试管帽是否存在(在试管没帽的边沿位置,抓手扭矩抓紧,如果等待一定时间后,抓手位置接近极限位置,则认为没有帽子,返回TubeNotHasHat错误) + // 4. 无论是否抓取成功,只要不向外抛出异常,方法结束时,该模块涉及到组件均需要返回待机位置。 + // */ + // return A8kEcode.Success; + // } + // + // /** + // * 取试管帽 + // */ + // public A8kEcode takeTubeCap(String tubeType) throws HardwareException, InterruptedException { + // var params = this.paramDao; + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_takePushCapPos(), params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // + // var motorUdTakeCapPos = params.getZMotor_ShortBloodTakeCapHeight(); + // var tubeTypeValue = A8kTubeType.valueOf(tubeType); + // if (tubeTypeValue.equals(A8kTubeType.HighBlood)) { + // motorUdTakeCapPos = params.getZMotor_HighBloodTakeCapHeight(); + // } + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), motorUdTakeCapPos, params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getGripperServo_takeTubePos(), params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_standbyPos(), params.getActionOvertime()); + // return A8kEcode.Success; + // } + // + // /** + // * 盖试管帽,并将试管移动回试管架中 + // */ + // public void pushBackTubeCapAndTakeBakTube(String tubeType) throws HardwareException, InterruptedException { + // var params = this.paramDao; + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getHorizontalMotor_takePushCapPos(), params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // + // var motorUdTakeCapPos = params.getZMotor_ShortBloodTakeCapHeight(); + // var tubeTypeValue = A8kTubeType.valueOf(tubeType); + // if (tubeTypeValue.equals(A8kTubeType.HighBlood)) { + // motorUdTakeCapPos = params.getZMotor_HighBloodTakeCapHeight(); + // } + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), motorUdTakeCapPos, params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getActionOvertime()); + // + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.step_motor_easy_move_to.toInt(), params.getHorizontalMotor_standbyPos(), params.getActionOvertime()); + // } + // + // + // /* ======================================================================================= + // 辅助操作 + // =======================================================================================*/ + // + // /** + // * 摇匀试管 + // * @param tubeType HighBlood,ShortBlood,Mini,MiniBlood,BulletTube1P5,BulletTube0P5 + // * @param times 摇匀次数 + // * @param shakeDegree 摇匀角度 + // */ + // public void ShakeTube(String tubeType, Integer times, Integer shakeDegree) throws HardwareException, InterruptedException { + // var params = this.paramDao; + // var standByPos = params.getShakeMotor_standbyPos(); + // var startPos = standByPos - shakeDegree / 2; + // var endPos = standByPos + shakeDegree / 2; + // this.canBus.callblockcmd(MId.ShakeModShakeM.toInt(), CmdId.step_motor_easy_reciprocating_motion.toInt(), startPos, endPos, times, params.getActionOvertime()); + // } + // + // /** + // * 打开气溶胶风扇 + // */ + // public void openAerosolFan() throws HardwareException { + // var params = this.paramDao; + // this.canBus.callcmd(MId.WbTubeFanMod.toInt(), CmdId.fan_controler_set_speed.toInt(), params.getAerosolFanLevel()); + // } + // + // /** + // * 关闭气溶胶风扇 + // */ + // public void closeAerosolFan() throws HardwareException { + // this.canBus.callcmd(MId.WbTubeFanMod.toInt(), CmdId.fan_controler_set_speed.toInt(), 0); + // } + // + // /** + // * 设备初始化时复位 + // */ + // public void moduleResetWhenPowerOn() throws HardwareException, InterruptedException { + // var params = this.paramDao; + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_standbyPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModShakeM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, params.getTubeClampMotor_standbyPos()); + // this.canBus.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); + // this.canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM, params.getShakeMotor_standbyPos()); + // this.canBus.waitForMod(MId.ShakeModShakeM, params.getActionOvertime()); + // } + // + // /** + // * 设备运行时复位 + // */ + // public void moduleRuntimeReset() throws HardwareException, InterruptedException { + // var params = this.paramDao; + // this.canBus.callblockcmd(MId.ShakeModGripperSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getGripperServo_standbyPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperZM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModGripperYSV.toInt(), CmdId.mini_servo_move_to.toInt(), params.getHorizontalMotor_standbyPos(), params.getActionOvertime()); + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModClampingM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModShakeM.toInt(), CmdId.step_motor_easy_move_to.toInt(), 0, params.getMoveToZeroOvertime()); + // this.canBus.callblockcmd(MId.ShakeModShakeM.toInt(), CmdId.step_motor_easy_move_to_zero.toInt(), params.getMoveToZeroOvertime()); + // this.canBus.stepMotorEasyMoveTo(MId.ShakeModClampingM, params.getTubeClampMotor_standbyPos()); + // this.canBus.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); + // this.canBus.stepMotorEasyMoveTo(MId.ShakeModShakeM, params.getShakeMotor_standbyPos()); + // this.canBus.waitForMod(MId.ShakeModShakeM, params.getActionOvertime()); + // } + // + // public void openTubeClip() throws HardwareException, InterruptedException { + // var params = this.paramDao; + // this.canBus.stepMotorEasyMoveBy(MId.ShakeModClampingM, 10); + // this.canBus.waitForMod(MId.ShakeModClampingM, params.getActionOvertime()); + // } + + } diff --git a/zhaohe_app.db b/zhaohe_app.db index 7e8293b..a582a92 100644 Binary files a/zhaohe_app.db and b/zhaohe_app.db differ