1.两片玻璃贴合后一起搬运的逻辑问题再优化,同时修改Slot信息,贴合后的玻璃应该放置在同一Slot.
已修改13个文件
269 ■■■■ 文件已修改
SourceCode/Bond/Servo/CArm.cpp 18 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CArmTray.cpp 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CBonder.cpp 24 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CBonder.h 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CEFEM.cpp 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CEquipment.cpp 43 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CGlass.cpp 15 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CGlass.h 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CMaster.cpp 86 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CMaster.h 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CMeasurement.cpp 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CRobotTask.cpp 67 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CRobotTask.h 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CArm.cpp
@@ -41,10 +41,6 @@
        m_slot[0].setPosition(m_nID);
        m_slot[0].setNo(1);
        m_slot[0].setName("Slot 1(Temp)");
        m_slot[1].enable();
        m_slot[1].setPosition(m_nID);
        m_slot[1].setNo(2);
        m_slot[1].setName("Slot 2(Temp)");
    }
    void CArm::onTimer(UINT nTimerid)
@@ -70,22 +66,14 @@
    int CArm::tempStore(CGlass* pGlass)
    {
        // 原:保证列表中只存储一个物料
        // 修改为:先清空之前的,再添加当前pGlass, 如果pGlass有buddy,也要加入列表中
        // 修改为:先清空之前的,再添加当前pGlass
        Lock();
        CGlass* pPreviousGlass;
        pPreviousGlass = (CGlass*)m_slot[0].getContext();
        if (pPreviousGlass != nullptr) {
            pPreviousGlass->release();
        }
        pPreviousGlass = (CGlass*)m_slot[1].getContext();
        if (pPreviousGlass != nullptr) {
            pPreviousGlass->release();
        }
        m_slot[0].setContext(pGlass);
        if (pGlass->getBuddy() != nullptr) {
            m_slot[1].setContext(pGlass->getBuddy());
        }
        Unlock();
        if (m_listener.onDataChanged != nullptr) {
@@ -106,10 +94,6 @@
        pGlass = pPreviousGlass;
        pGlass->addRef();
        m_slot[0].setContext(nullptr);
        CGlass* pBuddy = pGlass->getBuddy();
        if (pBuddy != nullptr) {
            m_slot[1].setContext(nullptr);
        }
        Unlock();
        if (m_listener.onDataChanged != nullptr) {
SourceCode/Bond/Servo/CArmTray.cpp
@@ -41,10 +41,6 @@
        m_slot[0].setPosition(m_nID);
        m_slot[0].setNo(1);
        m_slot[0].setName("Slot 1");
        m_slot[1].enable();
        m_slot[1].setPosition(m_nID);
        m_slot[1].setNo(2);
        m_slot[1].setName("Slot 2");
    }
    void CArmTray::onTimer(UINT nTimerid)
SourceCode/Bond/Servo/CBonder.cpp
@@ -416,6 +416,14 @@
        return m_nIndex;
    }
    BOOL CBonder::hasBondClass()
    {
        CGlass* pGlass = (CGlass*)m_slot[1].getContext();
        if (pGlass == nullptr) return FALSE;
        CGlass* pBuddy = pGlass->getBuddy();
        return pBuddy != nullptr;
    }
    int CBonder::onProcessData(CProcessData* pProcessData)
    {
        CEquipment::onProcessData(pProcessData);
@@ -423,33 +431,27 @@
        // 检查数据,当前两片玻璃,一片为G1, 一片为G2, 且pProcessData中的id能匹配G1或G2
        Lock();
        CGlass* pGlass1 = getGlassFromSlot(1);
        CGlass* pGlass2 = getGlassFromSlot(2);
        CGlass* pGlass2 = getGlassFromSlot(1);
        CGlass* pGlass1 = getGlassFromSlot(2);
        if (pGlass1 == nullptr || pGlass2 == nullptr) {
            LOGE("<CBonder-%s>onProcessData,错误!不满足两片玻璃且分别为G1与G2的条件,请检查数据是否正确!", m_strName.c_str());
            Unlock();
            return -1;
        }
        if (pGlass1->getBuddy() != nullptr || pGlass2->getBuddy() != nullptr) {
        if (pGlass1->getBuddy() != nullptr) {
            LOGE("<CBonder-%s>onProcessData,错误!玻璃较早前已被绑定,请检查数据是否正确!", m_strName.c_str());
            Unlock();
            return -1;
        }
        if (pGlass1->getBuddy() != nullptr || pGlass2->getBuddy() != nullptr) {
            LOGE("<CBonder-%s>onProcessData,错误!玻璃较早前已被贴合,请检查数据是否正确!", m_strName.c_str());
            Unlock();
            return -1;
        }
        if (pGlass1->getType() == pGlass2->getType()) {
        if (pGlass1->getType() != MaterialsType::G1 || pGlass2->getType() != MaterialsType::G2) {
            LOGE("<CBonder-%s>onProcessData,错误!两片玻璃未匹配,必须分别为G1和G2类型,请检查数据是否正确!", m_strName.c_str());
            Unlock();
            return -1;
        }
        pGlass1->setBuddy(pGlass2);
        pGlass2->setBuddy(pGlass1);
        getSlot(0)->setContext(nullptr);
        LOGE("<CBonder-%s>onProcessData,%s和%s已贴合!", m_strName.c_str(),
            pGlass1->getID().c_str(), pGlass2->getID().c_str());
        Unlock();
SourceCode/Bond/Servo/CBonder.h
@@ -27,6 +27,7 @@
    public:
        void setIndex(unsigned int index);
        unsigned int getIndex();
        BOOL hasBondClass();
    private:
        unsigned int m_nIndex;
SourceCode/Bond/Servo/CEFEM.cpp
@@ -22,6 +22,10 @@
        m_pPort[3] = nullptr;
        m_pAligner = nullptr;
        m_pFliper = nullptr;
        m_robotData.status = ROBOT_STATUS::Idle;
        m_robotData.position = ROBOT_POSITION::Port1;
        m_robotData.armState[0] = FALSE;
        m_robotData.armState[1] = FALSE;
    }
    CEFEM::~CEFEM()
SourceCode/Bond/Servo/CEquipment.cpp
@@ -255,13 +255,21 @@
            if (!m_slot[i].isEnable()) continue;
            CGlass* pGlass = (CGlass*)m_slot[i].getContext();
            CGlass* pBuddy = nullptr;
            if (pGlass == nullptr) {
                attrubutes.addAttribute(new CAttribute(m_slot[i].getName().c_str(),
                    "", "", weight++));
            }
            else {
                attrubutes.addAttribute(new CAttribute(m_slot[i].getName().c_str(),
                    pGlass->getID().c_str(), "", weight++));
                pBuddy = pGlass->getBuddy();
                if (pBuddy == nullptr) {
                    attrubutes.addAttribute(new CAttribute(m_slot[i].getName().c_str(),
                        pGlass->getID().c_str(), "", weight++));
                }
                else {
                    attrubutes.addAttribute(new CAttribute(m_slot[i].getName().c_str(),
                        (pGlass->getID() + " -> " + pBuddy->getID()).c_str(), "", weight++));
                }
            }
        }
@@ -317,8 +325,13 @@
            Lock();
            for (int i = 0; i < SLOT_MAX; i++) {
                m_slot[i].serialize(ar);
                if (m_slot[i].getContext() != nullptr) {
                    ((CGlass*)m_slot[i].getContext())->serialize(ar);
                CGlass* pGlass = (CGlass *)m_slot[i].getContext();
                if (pGlass != nullptr) {
                    pGlass->serialize(ar);
                    CGlass* pBuddy = pGlass->getBuddy();
                    if (pBuddy != nullptr) {
                        pBuddy->serialize(ar);
                    }
                }
            }
            Unlock();
@@ -330,10 +343,16 @@
                    CGlass* pGlass = theApp.m_model.m_glassPool.allocaGlass();
                    pGlass->serialize(ar);
                    m_slot[i].setContext(pGlass);
                    if (pGlass->getBuddy() != nullptr) {
                        CGlass* pBuddy = theApp.m_model.m_glassPool.allocaGlass();
                        pBuddy->serialize(ar);
                        pGlass->forceSetBuddy(pBuddy);
                    }
                }
            }
            
            // 梳理各玻璃之间的绑定关系
            /*
            Lock();
            for (int i = 0; i < SLOT_MAX; i++) {
                CGlass* pGlass = (CGlass*)m_slot[i].getContext();
@@ -351,6 +370,7 @@
                }
            }
            Unlock();
            */
        }
    }
@@ -766,18 +786,6 @@
            return -3;
        }
        // 如果此玻璃已经贴合,贴合的玻璃也要从列表中移除
        CGlass* pBuddy = pContext->getBuddy();
        if (pBuddy != nullptr) {
            for (int i = 0; i < SLOT_MAX; i++) {
                CGlass* pGlass = (CGlass*)m_slot[i].getContext();
                if (pGlass != nullptr && compareJobDataB(pBuddy->getJobDataB(), pGlass->getJobDataB())) {
                    m_slot[i].setContext(nullptr);
                    break;
                }
            }
        }
        ((CArm*)m_pArm)->tempStore(pContext);
        pContext->release();
@@ -811,6 +819,7 @@
        // 如果此玻璃已经贴合,贴合的玻璃也要从加入到列表中
        /*
        CGlass* pBuddy = pGlass->getBuddy();
        if (pBuddy != nullptr) {
            Lock();
@@ -823,7 +832,7 @@
            }
            Unlock();
        }
        */
        if (m_listener.onDataChanged != nullptr) {
            m_listener.onDataChanged(this, EDCC_STORED_JOB);
SourceCode/Bond/Servo/CGlass.cpp
@@ -135,7 +135,7 @@
            m_jobDataB.unserialize(temp, JOBDATAB_SIZE);
            ar.Read(temp, JOBDATAS_SIZE);
            m_jobDataS.unserialize(temp, JOBDATAS_SIZE);
            ar >> ullPath;                    // 这是m_pBuddy, 用不上
            ar >> ullPath;    m_pBuddy = (CGlass*)ullPath;
            ReadString(ar, m_strBuddyId);
            Unlock();
        }
@@ -166,9 +166,16 @@
        if (m_pBuddy != nullptr) return FALSE;
        if (pGlass->getType() == this->getType()) return FALSE;
        m_pBuddy = pGlass;
        if (m_type == MaterialsType::G1) {
            m_pBuddy->addRef();
        }
        m_pBuddy->addRef();
        m_strBuddyId = m_pBuddy->getID();
        return TRUE;
    }
    BOOL CGlass::forceSetBuddy(CGlass* pGlass)
    {
        m_pBuddy = pGlass;
        m_pBuddy->addRef();
        m_strBuddyId = m_pBuddy->getID();
        return TRUE;
SourceCode/Bond/Servo/CGlass.h
@@ -33,6 +33,7 @@
        void setJobDataS(CJobDataS* pJobDataS);
        CJobDataS* getJobDataS();
        BOOL setBuddy(CGlass* pGlass);
        BOOL forceSetBuddy(CGlass* pGlass);
        CGlass* getBuddy();
        std::string& getBuddyId();
        void processEnd(unsigned int nEqId, unsigned int nUnit);
SourceCode/Bond/Servo/CMaster.cpp
@@ -477,7 +477,7 @@
                // Fliper(G2) -> Bonder
                // VacuumBake(G1) -> Bonder
                if (!rmd.armState[1]) {
                if (!rmd.armState[1] && !pBonder1->hasBondClass()) {
                    m_pActiveRobotTask = createTransferTask(pFliper, pBonder1, primaryType, secondaryType, 2);
                    if (m_pActiveRobotTask != nullptr) {
                        m_pActiveRobotTask->pick();
@@ -491,7 +491,7 @@
                    }
                }
                if (!rmd.armState[1]) {
                if (!rmd.armState[1] && !pBonder2->hasBondClass()) {
                    m_pActiveRobotTask = createTransferTask(pFliper, pBonder2, primaryType, secondaryType, 2);
                    if (m_pActiveRobotTask != nullptr) {
                        m_pActiveRobotTask->pick();
@@ -505,7 +505,7 @@
                    }
                }
                if (!rmd.armState[0]) {
                if (!rmd.armState[0] && !pBonder1->hasBondClass()) {
                    m_pActiveRobotTask = createTransferTask(pVacuumBake, pBonder1, primaryType, secondaryType);
                    if (m_pActiveRobotTask != nullptr) {
                        m_pActiveRobotTask->pick();
@@ -519,7 +519,7 @@
                    }
                }
                if (!rmd.armState[0]) {
                if (!rmd.armState[0] && !pBonder2->hasBondClass()) {
                    m_pActiveRobotTask = createTransferTask(pVacuumBake, pBonder2, primaryType, secondaryType);
                    if (m_pActiveRobotTask != nullptr) {
                        m_pActiveRobotTask->pick();
@@ -1204,14 +1204,11 @@
        if (pSrcSlot != nullptr && nullptr != pTarSlot) {
            int srcPos, srcSlot, tarPos, tarSlot;
            transformPosAndSlot(pSrcSlot->getPosition(), pSrcSlot->getNo(), srcPos, srcSlot);
            transformPosAndSlot(pTarSlot->getPosition(), pTarSlot->getNo(), tarPos, tarSlot);
            pTask = new CRobotTask();
            pTask->setContext(pSrcSlot->getContext());
            pTask->setEFEM((CEFEM*)getEquipment(EQ_ID_EFEM));
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, armNo, srcPos,
                tarPos, srcSlot, tarSlot);
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, armNo, pSrcSlot->getPosition(),
                pTarSlot->getPosition(), pSrcSlot->getNo(), pTarSlot->getNo());
        }
@@ -1228,14 +1225,11 @@
        pSrcSlot = pSrcEq->getProcessedSlot(MaterialsType::G1);
        if (pSrcSlot != nullptr && nullptr != pTarSlot) {
            int srcPos, srcSlot, tarPos, tarSlot;
            transformPosAndSlot(pSrcSlot->getPosition(), pSrcSlot->getNo(), srcPos, srcSlot);
            transformPosAndSlot(pTarSlot->getPosition(), pTarSlot->getNo(), tarPos, tarSlot);
            pTask = new CRobotTask();
            pTask->setContext(pSrcSlot->getContext());
            pTask->setEFEM((CEFEM*)getEquipment(EQ_ID_EFEM));
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, srcPos,
                tarPos, srcSlot, tarSlot);
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, pSrcSlot->getPosition(),
                pTarSlot->getPosition(), pSrcSlot->getNo(), pTarSlot->getNo());
        }
@@ -1253,14 +1247,11 @@
        pSrcSlot = pSrcEq->getProcessedSlot2(MaterialsType::G1, slotsSrc);
        if (pSrcSlot != nullptr && nullptr != pTarSlot) {
            int srcPos, srcSlot, tarPos, tarSlot;
            transformPosAndSlot(pSrcSlot->getPosition(), pSrcSlot->getNo(), srcPos, srcSlot);
            transformPosAndSlot(pTarSlot->getPosition(), pTarSlot->getNo(), tarPos, tarSlot);
            pTask = new CRobotTask();
            pTask->setContext(pSrcSlot->getContext());
            pTask->setEFEM((CEFEM*)getEquipment(EQ_ID_EFEM));
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, srcPos,
                tarPos, srcSlot, tarSlot);
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, pSrcSlot->getPosition(),
                pTarSlot->getPosition(), pSrcSlot->getNo(), pTarSlot->getNo());
        }
@@ -1277,68 +1268,15 @@
        pSrcSlot = pSrcEq->getProcessedSlot2(MaterialsType::G1, slots);
        if (pSrcSlot != nullptr && nullptr != pTarSlot) {
            int srcPos, srcSlot, tarPos, tarSlot;
            transformPosAndSlot(pSrcSlot->getPosition(), pSrcSlot->getNo(), srcPos, srcSlot);
            transformPosAndSlot(pTarSlot->getPosition(), pTarSlot->getNo(), tarPos, tarSlot);
            pTask = new CRobotTask();
            pTask->setContext(pSrcSlot->getContext());
            pTask->setEFEM((CEFEM*)getEquipment(EQ_ID_EFEM));
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, srcPos,
                tarPos, srcSlot, tarSlot);
            taskSeqNo = pTask->setRobotTransferParam(taskSeqNo, 1, pSrcSlot->getPosition(),
                pTarSlot->getPosition(), pSrcSlot->getNo(), pTarSlot->getNo());
        }
        return pTask;
    }
    void CMaster::transformPosAndSlot(int srcPos, int srcSlot, int& tarPos, int& tarSlot)
    {
        switch (srcPos)
        {
        case EQ_ID_LOADPORT1:
        case EQ_ID_LOADPORT2:
        case EQ_ID_LOADPORT3:
        case EQ_ID_LOADPORT4:
        case EQ_ID_ARM_TRAY1:
        case EQ_ID_ARM_TRAY2:
        case EQ_ID_ALIGNER:
        case EQ_ID_FLIPER:
            tarPos = srcPos;
            tarSlot = 1;
            break;
        case EQ_ID_Bonder1:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 9 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_Bonder2:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 11 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_VACUUMBAKE:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 13 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_BAKE_COOLING:
            if (1 <= srcSlot && srcSlot <= 4) {
                tarPos = 15 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_MEASUREMENT:
            tarPos = 19;
            tarSlot = 1;
            break;
        default:
            tarPos = srcPos;
            tarSlot = srcSlot;
            break;
        }
    }
    int CMaster::abortCurrentTask()
SourceCode/Bond/Servo/CMaster.h
@@ -93,7 +93,6 @@
        CRobotTask* createTransferTask_bonder_to_bakecooling(CEquipment* pSrcEq, CEquipment* pTarEq);
        CRobotTask* createTransferTask_bake_to_cooling(CEquipment* pSrcEq);
        CRobotTask* createTransferTask_bakecooling_to_measurement(CEquipment* pSrcEq, CEquipment* pTarEq);
        void transformPosAndSlot(int srcPos, int srcSlot, int& tarPos, int& tarSlot);
    private:
        CRITICAL_SECTION m_criticalSection;
SourceCode/Bond/Servo/CMeasurement.cpp
@@ -45,10 +45,6 @@
        m_slot[0].setPosition(m_nID);
        m_slot[0].setNo(1);
        m_slot[0].setName("Slot 1");
        m_slot[1].enable();
        m_slot[1].setPosition(m_nID);
        m_slot[1].setNo(2);
        m_slot[1].setName("Slot 2");
    }
    void CMeasurement::onTimer(UINT nTimerid)
SourceCode/Bond/Servo/CRobotTask.cpp
@@ -117,26 +117,31 @@
        m_robotCmdParam[ACTION_TRANSFER].putPosition = static_cast<short>(toPos);
        m_robotCmdParam[ACTION_TRANSFER].putSlotNo = static_cast<short>(toSlot);
        // 转换一下源和目标站号
        int srcPos, srcSlot, tarPos, tarSlot;
        transformPosAndSlot(fromPos, fromSlot, srcPos, srcSlot);
        transformPosAndSlot(toPos, toSlot, tarPos, tarSlot);
        m_robotCmdParam[ACTION_PICK] = {};
        m_robotCmdParam[ACTION_PICK].sequenceNo = static_cast<short>(seq+2);
        m_robotCmdParam[ACTION_PICK].rcmd = static_cast<short>(SERVO::RCMD::Get);
        m_robotCmdParam[ACTION_PICK].armNo = static_cast<short>(armNo);
        m_robotCmdParam[ACTION_PICK].getPosition = static_cast<short>(fromPos);
        m_robotCmdParam[ACTION_PICK].getSlotNo = static_cast<short>(fromSlot);
        m_robotCmdParam[ACTION_PICK].getPosition = static_cast<short>(srcPos);
        m_robotCmdParam[ACTION_PICK].getSlotNo = static_cast<short>(srcSlot);
        m_robotCmdParam[ACTION_PLACE] = {};
        m_robotCmdParam[ACTION_PLACE].sequenceNo = static_cast<short>(seq + 2);
        m_robotCmdParam[ACTION_PLACE].rcmd = static_cast<short>(SERVO::RCMD::Put);
        m_robotCmdParam[ACTION_PLACE].armNo = static_cast<short>(armNo);
        m_robotCmdParam[ACTION_PLACE].putPosition = static_cast<short>(toPos);
        m_robotCmdParam[ACTION_PLACE].putSlotNo = static_cast<short>(toSlot);
        m_robotCmdParam[ACTION_PLACE].putPosition = static_cast<short>(tarPos);
        m_robotCmdParam[ACTION_PLACE].putSlotNo = static_cast<short>(tarSlot);
        m_robotCmdParam[ACTION_RESTORE] = {};
        m_robotCmdParam[ACTION_RESTORE].sequenceNo = static_cast<short>(seq + 1);
        m_robotCmdParam[ACTION_RESTORE].rcmd = static_cast<short>(SERVO::RCMD::Put);
        m_robotCmdParam[ACTION_RESTORE].armNo = static_cast<short>(armNo);
        m_robotCmdParam[ACTION_RESTORE].putPosition = static_cast<short>(fromPos);
        m_robotCmdParam[ACTION_RESTORE].putSlotNo = static_cast<short>(fromSlot);
        m_robotCmdParam[ACTION_RESTORE].putPosition = static_cast<short>(srcPos);
        m_robotCmdParam[ACTION_RESTORE].putSlotNo = static_cast<short>(srcSlot);
        return seq + 1;
    }
@@ -339,4 +344,54 @@
    {
        m_timeStored = CToolUnits::getUnixTimestamp();;
    }
    void CRobotTask::transformPosAndSlot(int srcPos, int srcSlot, int& tarPos, int& tarSlot)
    {
        switch (srcPos)
        {
        case EQ_ID_LOADPORT1:
        case EQ_ID_LOADPORT2:
        case EQ_ID_LOADPORT3:
        case EQ_ID_LOADPORT4:
        case EQ_ID_ARM_TRAY1:
        case EQ_ID_ARM_TRAY2:
        case EQ_ID_ALIGNER:
        case EQ_ID_FLIPER:
            tarPos = srcPos;
            tarSlot = 1;
            break;
        case EQ_ID_Bonder1:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 9 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_Bonder2:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 11 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_VACUUMBAKE:
            if (1 <= srcSlot && srcSlot <= 2) {
                tarPos = 13 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_BAKE_COOLING:
            if (1 <= srcSlot && srcSlot <= 4) {
                tarPos = 15 + srcSlot;
                tarSlot = 1;
            }
            break;
        case EQ_ID_MEASUREMENT:
            tarPos = 19;
            tarSlot = 1;
            break;
        default:
            tarPos = srcPos;
            tarSlot = srcSlot;
            break;
        }
    }
}
SourceCode/Bond/Servo/CRobotTask.h
@@ -55,6 +55,7 @@
    private:
        static std::string& generateId(std::string& out);
        void transformPosAndSlot(int srcPos, int srcSlot, int& tarPos, int& tarSlot);
    private:
        ROBOT_TASK_STATE m_state;                    /* 任务状态 */