Browse Source

update

tags/v0
zhaohe 7 months ago
parent
commit
98bb9264d7
  1. 2
      src/main/java/a8k/app/a8ktype/state/SampleInfo.java
  2. 8
      src/main/java/a8k/app/service/mainctrl/mainflowctrl/MainFlowCtrlScheduler.java
  3. 19
      src/main/java/a8k/app/service/mainctrl/mainflowctrl/processer/MainFlowStateChangeProcesser.java
  4. 8
      src/main/java/a8k/app/service/statemgr/ConsumablesMgrService.java
  5. 8
      src/main/java/a8k/extui/mgr/ExtApiPageGroupCfgMgr.java
  6. 289
      src/main/java/a8k/extui/page/extapp/OptFullFlowVerificationPage.java

2
src/main/java/a8k/app/a8ktype/state/SampleInfo.java

@ -9,7 +9,7 @@ public class SampleInfo implements Serializable {
public String sampleId = ""; //样本ID-系统生成-唯一标识一个样本 public String sampleId = ""; //样本ID-系统生成-唯一标识一个样本
public Boolean isHighTube = false; public Boolean isHighTube = false;
public Boolean isEmergency = false; public Boolean isEmergency = false;
public BloodType bloodType = BloodType.WHOLE_BLOOD; //血液类型
public BloodType bloodType = BloodType.SERUM_OR_PLASMA; //血液类型
public String sampleBarcode = ""; //用于请求用户信息的条码ID public String sampleBarcode = ""; //用于请求用户信息的条码ID
public String userid = ""; //用户输入的样本ID不做逻辑只做展示 public String userid = ""; //用户输入的样本ID不做逻辑只做展示

8
src/main/java/a8k/app/service/mainctrl/mainflowctrl/MainFlowCtrlScheduler.java

@ -280,6 +280,14 @@ public class MainFlowCtrlScheduler implements ApplicationListener<ApplicationSta
changeWorkState(A8kWorkState.WORKING); changeWorkState(A8kWorkState.WORKING);
} }
} else if (state.stopActionPending) { } else if (state.stopActionPending) {
if (state.workState != A8kWorkState.IDLE) { if (state.workState != A8kWorkState.IDLE) {
changeWorkState(A8kWorkState.IDLE); changeWorkState(A8kWorkState.IDLE);
} }

19
src/main/java/a8k/app/service/mainctrl/mainflowctrl/processer/MainFlowStateChangeProcesser.java

@ -1,7 +1,9 @@
package a8k.app.service.mainctrl.mainflowctrl.processer; package a8k.app.service.mainctrl.mainflowctrl.processer;
import a8k.app.service.mainctrl.TubeHolderSettingMgrService;
import a8k.app.service.mainctrl.mainflowctrl.base.IMainFlowStateChangeProcesser; import a8k.app.service.mainctrl.mainflowctrl.base.IMainFlowStateChangeProcesser;
import a8k.app.service.mainctrl.mainflowctrl.base.MainFlowProcesser; import a8k.app.service.mainctrl.mainflowctrl.base.MainFlowProcesser;
import a8k.app.service.statemgr.ConsumablesMgrService;
import a8k.app.service.statemgr.IncubationPlateStateMgrService; import a8k.app.service.statemgr.IncubationPlateStateMgrService;
import a8k.app.service.statemgr.ProjectContextMgrService; import a8k.app.service.statemgr.ProjectContextMgrService;
import a8k.app.service.statemgr.TubeStateMgrService; import a8k.app.service.statemgr.TubeStateMgrService;
@ -34,6 +36,8 @@ public class MainFlowStateChangeProcesser implements IMainFlowStateChangeProcess
IncubationPlateStateMgrService incubationPlateStateMgrService; IncubationPlateStateMgrService incubationPlateStateMgrService;
@Resource @Resource
TubeStateMgrService tubeStateMgrService; TubeStateMgrService tubeStateMgrService;
@Resource
ConsumablesMgrService consumablesMgrService;
@Resource @Resource
ProjectContextMgrService projectContextMgrService; ProjectContextMgrService projectContextMgrService;
@ -53,7 +57,9 @@ public class MainFlowStateChangeProcesser implements IMainFlowStateChangeProcess
virtualDevice.doVirtualThings("清空设备"); virtualDevice.doVirtualThings("清空设备");
return; return;
} }
//光学模组清空
optScanModuleCtrlService.dropPlate();
//弹出所有孵育盘
ejectAllPlates(); ejectAllPlates();
//弹出试管架 //弹出试管架
tubeFeedingCtrlService.ejectTubeHolder(); tubeFeedingCtrlService.ejectTubeHolder();
@ -61,15 +67,20 @@ public class MainFlowStateChangeProcesser implements IMainFlowStateChangeProcess
hbotMoveExCtrlService.dropTip(); hbotMoveExCtrlService.dropTip();
//hbot快速归零 //hbot快速归零
hbotMoveExCtrlService.moveQuickToZero(); hbotMoveExCtrlService.moveQuickToZero();
incubationPlateStateMgrService.resetAll();
tubeStateMgrService.resetAll();
} }
@Override @Override
public void onStop() throws AppException { public void onStop() throws AppException {
//物理清空设备
doClearDevice(); doClearDevice();
//清空孵育盘状态
incubationPlateStateMgrService.resetAll();
//清空试管状态
tubeStateMgrService.resetAll();
//清空项目上下文
projectContextMgrService.clearCxts(); projectContextMgrService.clearCxts();
//恢复耗材预定状态
consumablesMgrService.bakAllReserveConsumable();
} }
@Override @Override

8
src/main/java/a8k/app/service/statemgr/ConsumablesMgrService.java

@ -285,6 +285,14 @@ public class ConsumablesMgrService {
priSetConsumableGroupNum(consumable.getGroup(), num, reserveNum); priSetConsumableGroupNum(consumable.getGroup(), num, reserveNum);
} }
synchronized public void bakAllReserveConsumable() {
for (var group : ConsumableGroup.values()) {
cState.reactionPlateGroup[group.off].reserveNum = 0;
cState.larBottleGroup[group.off].reserveNum = 0;
cState.littBottleGroup[group.off].reserveNum = 0;
}
}
// //
// PRIVATE // PRIVATE

8
src/main/java/a8k/extui/mgr/ExtApiPageGroupCfgMgr.java

@ -2,6 +2,7 @@ package a8k.extui.mgr;
import a8k.app.utils.ZList; import a8k.app.utils.ZList;
import a8k.extui.page.debug.*; import a8k.extui.page.debug.*;
import a8k.extui.page.extapp.*;
import a8k.extui.page.extsetting.db.DeviceActionParameterSettingPage; import a8k.extui.page.extsetting.db.DeviceActionParameterSettingPage;
import a8k.extui.page.extsetting.db.ProjInfoMgrPage; import a8k.extui.page.extsetting.db.ProjInfoMgrPage;
import a8k.extui.page.extsetting.db.ReactionRecordMgrDebugPage; import a8k.extui.page.extsetting.db.ReactionRecordMgrDebugPage;
@ -13,15 +14,11 @@ import a8k.extui.page.test.driver.LowLevelBoardVersionPreviewPage;
import a8k.extui.page.test.codetest.OptFormulaTestPage; import a8k.extui.page.test.codetest.OptFormulaTestPage;
import a8k.extui.page.test.codetest.OptFormulaTestPageV2; import a8k.extui.page.test.codetest.OptFormulaTestPageV2;
import a8k.extui.page.test.driver.PipetteCtrlDriverPage; import a8k.extui.page.test.driver.PipetteCtrlDriverPage;
import a8k.extui.page.extapp.A8kOptVerification;
import a8k.extui.page.test.frond_end_test.FakeReactionRecordGeneratorPage; import a8k.extui.page.test.frond_end_test.FakeReactionRecordGeneratorPage;
import a8k.extui.page.test.frond_end_test.VirtualEventGeneratorPage; import a8k.extui.page.test.frond_end_test.VirtualEventGeneratorPage;
import a8k.extui.page.extapp.OptModuleParamCalibration;
import a8k.extui.page.extsetting.pos_calibration.*; import a8k.extui.page.extsetting.pos_calibration.*;
import a8k.extui.page.test.stress_test.PipetteGunStressTest; import a8k.extui.page.test.stress_test.PipetteGunStressTest;
import a8k.extui.page.extapp.P01PipetteGunVerification;
import a8k.extui.page.extapp.P02A8kTemperaturaVerfication;
import a8k.extui.page.test.verification.*; import a8k.extui.page.test.verification.*;
import a8k.extui.page.test.verification.P34LiquidOperationTestPage; import a8k.extui.page.test.verification.P34LiquidOperationTestPage;
import a8k.extui.page.test.verification.P10ProjejIDCardTestPage; import a8k.extui.page.test.verification.P10ProjejIDCardTestPage;
@ -129,7 +126,8 @@ public class ExtApiPageGroupCfgMgr {
new Menu("高级应用", ZList.of( new Menu("高级应用", ZList.of(
new Menu("光学标定与验证", ZList.of( new Menu("光学标定与验证", ZList.of(
new Menu(A8kOptVerification.class, "光学模组验证"), new Menu(A8kOptVerification.class, "光学模组验证"),
new Menu(OptModuleParamCalibration.class, "光学模块参数校准")
new Menu(OptModuleParamCalibration.class, "光学模块参数校准"),
new Menu(OptFullFlowVerificationPage.class,"快速项目检测")
)), )),
new Menu("验证(过检专用)", ZList.of( new Menu("验证(过检专用)", ZList.of(
new Menu(P01PipetteGunVerification.class, "移液枪验证"), new Menu(P01PipetteGunVerification.class, "移液枪验证"),

289
src/main/java/a8k/extui/page/extapp/OptFullFlowVerificationPage.java

@ -0,0 +1,289 @@
package a8k.extui.page.extapp;
import a8k.OS;
import a8k.app.a8kproj.A8kReactionResultComputer;
import a8k.app.a8kproj.optalgo.type.OptScanResult;
import a8k.app.a8ktype.device.*;
import a8k.app.a8ktype.exception.AppException;
import a8k.app.a8ktype.param.type.A8kSamplePos;
import a8k.app.a8ktype.state.SampleInfo;
import a8k.app.a8ktype.type.ReactionResult;
import a8k.app.a8ktype.type.TubeHolderScanResult;
import a8k.app.dao.db.type.ProjExtInfoCard;
import a8k.app.dao.db.type.a8kidcard.zenum.A8kReactionFlowType;
import a8k.app.hardware.driver.PipetteCtrlDriver;
import a8k.app.service.bases.AppEventBusService;
import a8k.app.service.bases.FrontEndMessageBoxAndEventMgr;
import a8k.app.service.data.ProjIdCardInfoMgrService;
import a8k.app.service.data.ProjInfoMgrService;
import a8k.app.service.data.ReactionRecordMgrService;
import a8k.app.service.lowerctrl.*;
import a8k.app.utils.ProjBuildinInfo;
import a8k.app.utils.ProjInfo;
import a8k.app.utils.ProjInfoReader;
import a8k.app.utils.ZDateUtils;
import a8k.extui.mgr.ExtApiPageMgr;
import a8k.extui.type.ExtApiStatu;
import jakarta.annotation.PostConstruct;
import jakarta.annotation.Resource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.Assert;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;
@Component
public class OptFullFlowVerificationPage {
@Resource
TubeFeedingCtrlService tubeFeedingCtrlService;
@Resource
TubePreProcesModuleExCtrlService tubePreProcesModuleExCtrlService;
TubeHolderScanResult tubeHolderScanResult;
@Resource
PlateBoxCtrlService plateBoxCtrlService;
@Resource
OptScanModuleCtrlService optScanModuleCtrlService;
@Resource
PipetteCtrlDriver pipetteCtrlDriver;
@Resource
HbotMoveExCtrlService hbotMoveExCtrlService;
@Resource
LiquidOperationCtrlService liquidOperationCtrlService;
@Resource
TurnableMoveCtrlService turnableMoveCtrlService;
@Resource
ProjIdCardInfoMgrService projIdCardInfoMgrService;
@Resource
ProjInfoMgrService projInfoMgrService;
@Resource
AppEventBusService appEventBusService;
@Resource
FrontEndMessageBoxAndEventMgr frontEndMessageBoxAndEventMgr;
@Autowired
private ReactionRecordMgrService reactionRecordMgrService;
//
//Config
//
static public class Context {
public SampleInfo sampleInfo = new SampleInfo();
public ProjBuildinInfo projBuildinInfo;
public ProjExtInfoCard projExtInfoCard;
public A8kSamplePos samplePos = A8kSamplePos.EmergencyTubePos;
public ConsumableGroup consumableGroup = ConsumableGroup.CG1;
public Integer consumablePosOff = 0;
public IncubatorPos incubatorPos = IncubatorPos.SPACE01;
public List<ReactionResult> results = new ArrayList<>();
public Boolean isInit = false;
}
static public class State {
public Integer incubateRemainTime;
}
Context cxt = new Context();
State state = new State();
@ExtApiStatu(name = "", group = "样本信息", order = 1, minWidth = "33.3%")
public SampleInfo showSampleInfo() {
return cxt.sampleInfo;
}
@ExtApiStatu(name = "", group = "项目信息", order = 2, minWidth = "33.3%")
public ProjBuildinInfo showProjInfo() {
return cxt.projBuildinInfo;
}
@ExtApiStatu(name = "", group = "项目卡信息", order = 3, minWidth = "33.3%")
public ProjExtInfoCard showProjExtInfoCard() {
return cxt.projExtInfoCard;
}
@ExtApiStatu(name = "", group = "上下文", order = 4, minWidth = "33.3%")
public Object showConsumableInfo() {
return Map.<String, Object>of(
"耗材位置", String.format("%s-%d", cxt.consumableGroup, cxt.consumablePosOff),
"孵育盘位置", cxt.incubatorPos,
"取样位置", cxt.samplePos,
"样本信息是否初始化", cxt.isInit
);
}
@ExtApiStatu(name = "", group = "状态", order = 5, minWidth = "33.3%")
public State showState() {
return state;
}
@ExtApiStatu(name = "", group = "结果", order = 6, minWidth = "33.3%")
public List<ReactionResult> showResults() {
return cxt.results;
}
Integer tippos = 0;
void takeTip() throws AppException {
Boolean takeTip = false;
for (int i = 0; i < 10; i++) {
tippos = tippos % 120;
takeTip = hbotMoveExCtrlService.takeTipNoCheck(TipGroup.TipG1, tippos);
if (takeTip) {
break;
}
tippos++;
}
if (!takeTip) {
throw AppException.ofAECodeError("取Tip失败");
}
}
public void clearDevice() throws AppException {
optScanModuleCtrlService.dropPlate();
optScanModuleCtrlService.pullPlate(IncubatorPos.SPACE01);
optScanModuleCtrlService.dropPlate();
}
void prepareReactionPlate() throws AppException {
plateBoxCtrlService.pushPlateQuick(cxt.consumableGroup, cxt.incubatorPos);
}
void procesSample() throws AppException {
liquidOperationCtrlService.setProjContext(cxt.projBuildinInfo, cxt.projExtInfoCard);
if (!hbotMoveExCtrlService.isHasTip())
takeTip();
if (cxt.projBuildinInfo.reactionFlowType.equals(A8kReactionFlowType.SampleAndBS)) {
//param 小瓶缓冲液位置
var preReactionPos = new PreReactionPos(ConsumableType.SmallBottleBuffer, cxt.consumableGroup, cxt.consumablePosOff);
//param 取样量
Integer sampleVol = ProjInfoReader.getSampleVol(cxt.projBuildinInfo, cxt.projExtInfoCard, cxt.sampleInfo.bloodType);
//action ->刺破
liquidOperationCtrlService.pirceLittleBuffer(preReactionPos);
//action ->取样
liquidOperationCtrlService.takeSample(cxt.samplePos, preReactionPos, sampleVol);
//action ->孵育盘移动到吐液位置
turnableMoveCtrlService.trunableMoveToDropLiquidPos(cxt.incubatorPos); //
//action ->取反应液到反应板上
liquidOperationCtrlService.takePreReactionLiquidToLiquid(preReactionPos); //
} else if (cxt.projBuildinInfo.reactionFlowType.equals(A8kReactionFlowType.SampleAndBSAndProbeSubstance)) {
//param 探测物位置
var preReactionPos = new PreReactionPos(ConsumableType.ProbeSubstance, cxt.consumableGroup, cxt.consumablePosOff);
//param 取样量
Integer sampleVol = ProjInfoReader.getSampleVol(cxt.projBuildinInfo, cxt.projExtInfoCard, cxt.sampleInfo.bloodType);
//action ->取大瓶缓冲液到探测物质
liquidOperationCtrlService.takeLargeBottleBufferLiquidToProbeSubstance(
LargeBufferPos.of(cxt.consumableGroup), preReactionPos, cxt.projBuildinInfo.bigBufferSampleUl);
//action ->取样品
liquidOperationCtrlService.takeSample(cxt.samplePos, preReactionPos, sampleVol);
//action ->孵育盘移动到吐液位置
turnableMoveCtrlService.trunableMoveToDropLiquidPos(cxt.incubatorPos); //
//action ->取反应液到反应板上
liquidOperationCtrlService.takePreReactionLiquidToLiquid(preReactionPos); //
}
}
void incubate() throws AppException {
//等待孵育完成
state.incubateRemainTime = cxt.projBuildinInfo.reactionPlateIncubationTimeMin * 60;
while (state.incubateRemainTime > 0) {
state.incubateRemainTime -= 1;
OS.forceSleep(1000);
}
frontEndMessageBoxAndEventMgr.showInfo("孵育完成");
}
void pullAndScan() throws AppException {
optScanModuleCtrlService.pullPlate(cxt.incubatorPos);
ProjInfo projInfo = new ProjInfo();
projInfo.buildIn = cxt.projBuildinInfo;
projInfo.ext = cxt.projExtInfoCard;
List<OptScanResult> optScanResults = new ArrayList<>();
for (int i = 0; i < cxt.projBuildinInfo.subProjNum; i++) {
var optScanResult = optScanModuleCtrlService.optScan(cxt.projBuildinInfo, i);
ReactionResult result = A8kReactionResultComputer.optComputeResult(cxt.sampleInfo, projInfo, i, optScanResult.analysResult);
cxt.results.add(result);
optScanResults.add(optScanResult);
}
reactionRecordMgrService.addRecord(cxt.sampleInfo, projInfo, optScanResults, cxt.results);
}
public void initSampleInfo() throws AppException {
cxt.sampleInfo.sampleId = ZDateUtils.toID(new Date());
cxt.sampleInfo.userid = cxt.sampleInfo.sampleId;
cxt.sampleInfo.sampleBarcode = cxt.sampleInfo.sampleId;
cxt.sampleInfo.bloodType = BloodType.SERUM_OR_PLASMA;
cxt.sampleInfo.isHighTube = false;
cxt.sampleInfo.isEmergency = true;
cxt.projExtInfoCard = projIdCardInfoMgrService.getMountedProjInfoCard();
Assert.notNull(cxt.projExtInfoCard, "请插入项目卡");
cxt.projBuildinInfo = projInfoMgrService.getProjBuildInInfo(cxt.projExtInfoCard.projId);
cxt.isInit = true;
cxt.incubatorPos = IncubatorPos.SPACE01;
cxt.consumableGroup = ConsumableGroup.CG1;
cxt.consumablePosOff = 0;
}
public void startProcessSample(Boolean scanOnly) throws AppException {
initSampleInfo();
clearDevice();
frontEndMessageBoxAndEventMgr.showInfo("反应板准备");
prepareReactionPlate();
if (!scanOnly) {
frontEndMessageBoxAndEventMgr.showInfo("样本处理");
procesSample();
frontEndMessageBoxAndEventMgr.showInfo("孵育");
incubate();
}
frontEndMessageBoxAndEventMgr.showInfo("扫描");
pullAndScan();
frontEndMessageBoxAndEventMgr.showInfo("丢板");
optScanModuleCtrlService.dropPlate();
frontEndMessageBoxAndEventMgr.showInfo("结束");
}
public void sampleAndIncubateAndScan() throws AppException {
startProcessSample(false);
}
public void scanOnly(Integer scanTimes) throws AppException {
for (int i = 0; i < scanTimes; i++) {
startProcessSample(true);
}
}
@Resource
ExtApiPageMgr extApiPageMgr;
@PostConstruct
public void init() {
var page = extApiPageMgr.newPage(this);
page.addFunction("取样.孵育.扫描", this::sampleAndIncubateAndScan);
page.addFunction("只扫描", this::scanOnly);
extApiPageMgr.addPage(page);
}
}
Loading…
Cancel
Save