#include "WindowAppItemInterface.h" #include "WindowAppBlockStandard.h" #include "WindowAppBlockPort.h" #include "WindowAppPouScene.h" #include "WindowAppItemLink.h" #include "Pou.h" #include WindowAppItemInterface::WindowAppItemInterface( _INTERFACE* pInf, POU* pPou, const TOOL* pTool, bool bShowOnly, QGraphicsItem* parent /*= nullptr*/ ): m_infInfo(pInf) , m_pPou(pPou) , m_pParentTool(pTool) , m_bShowOnly(bShowOnly) // , m_nParallelLineLen(PARARREL_LINE_BASE_LEN) { // 接收悬停事件,显示提示 setAcceptHoverEvents(true); // 设置风格,可选择但不可拖动 setFlag(QGraphicsItem::ItemIsMovable, false); setFlag(QGraphicsItem::ItemIsSelectable, true); // 接收Item移动消息 setFlag(QGraphicsItem::ItemSendsGeometryChanges); this->setParentItem(parent); } /// /// 返回接口的矩形边界 /// /// QRectF WindowAppItemInterface::boundingRect() const { QRectF rc; // Goto输出接口的矩形区域 if ( this->m_infInfo->isGotoToolEnd() ) { rc = QRectF( m_parentRect.right() + 1, -GOTO_OUTPUT_TRIA_SIDE / 2, GOTO_OUTPUT_TRIA_SIDE * qSin(60 * 3.14 / 180), GOTO_OUTPUT_TRIA_SIDE ); } // Parallel输出接口的矩形区域(并行母线) else if ( this->m_infInfo->isParallelToolEnd() ) { //rc = QRectF( // m_parentRect.x() - PARARREL_LINE_EX_LEN, // m_parentRect.bottom() + PARARREL_LINE_SPACE, // m_nParallelLineLen, // PARARREL_LINE_HEIGHT //); rc = QRectF( line().x1(), line().y1(), line().length(), PARARREL_LINE_HEIGHT ); } // 如果是正常接口,则按正常接口区域返回 else { qreal extra = (pen().width()) * 4.0; rc = QRectF( line().p1(), QSizeF(line().p2().x() - line().p1().x(), line().p2().y() - line().p1().y() )) .normalized() .adjusted(-extra, -extra, extra, extra); } return rc; } /// /// 形状边界(为了扩大接口区域的可点击范围) /// /// QPainterPath WindowAppItemInterface::shape() const { QPainterPath path; // Goto输出接口的Shape if ( this->m_infInfo->isGotoToolEnd()) { path.moveTo(m_parentRect.right() + 1, -GOTO_OUTPUT_TRIA_SIDE / 2); path.lineTo(m_parentRect.right() + 1, GOTO_OUTPUT_TRIA_SIDE / 2); path.lineTo(m_parentRect.right() + 1 + GOTO_OUTPUT_TRIA_SIDE * qSin(60 * 3.14 / 180), 0); } // Parallel输出接口的Shape else if (this->m_infInfo->isParallelToolEnd()) { //path.addRect( // m_parentRect.x() - PARARREL_LINE_EX_LEN, // m_parentRect.bottom() + PARARREL_LINE_SPACE, // m_nParallelLineLen, // PARARREL_LINE_HEIGHT //); path.addRect( line().x1(), line().y1(), line().length(), PARARREL_LINE_HEIGHT ); } // 默认的线条Shape else { qreal extra = (pen().width()) * 4.0; extra *= 1.414; path = QGraphicsLineItem::shape(); // 通过Stroker设置精确Shape QPainterPathStroker stroker; stroker.setWidth(extra); path = stroker.createStroke(path); } return path; } /// /// 接口绘制 /// /// /// /// void WindowAppItemInterface::paint(QPainter* painter, const QStyleOptionGraphicsItem* option, QWidget* widget /*= nullptr*/) { Q_UNUSED(option); Q_UNUSED(widget); // 如果本接口压根都没启用的话,则不进行绘制 if (!m_bShowOnly && !this->m_infInfo->bEnable) { return; } // 排除掉非标准接口,因为非标准接口无法通过连线的方式进行链接 if (this->m_infInfo->Type == INF_TYPE::INF_TYPE_EVENT || this->m_infInfo->Type == INF_TYPE::INF_TYPE_CONTROL ) { return; } painter->setRenderHint(QPainter::Antialiasing, true); painter->save(); // 硬件组态禁止显示端口 // if ( m_pPou->pouName() == GROUP_NAME_HARDWARE) // { // painter->restore(); // return; // } // 线条颜色 QColor penColor; // 根据接口废弃与否,显示不同的颜色 // 废弃线条显示黑色 if (m_infInfo->Discard != INF_DISCARD::INF_DEFAULT) { penColor = COLOR_INF_DISCARDLINE; } // 正常线条显示正常颜色 else { penColor = COLOR_INF_LINE; } // 根据接口选中与否,显示不同的颜色 // 尚未选中,默认线条 if (!isSelected() && !IsParentSelected()) { painter->setPen(QPen(penColor, PEN_LINE_WIDTH, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin)); } // 被选中,加粗线条 else { painter->setPen(QPen(penColor, PEN_LINE_WIDTH_SEL, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin)); } // 绘制接口线条 this->drawInterfaceLine(painter); // 绘制接口文字 this->drawInterfaceText(painter); painter->restore(); } /// /// 绘制接口线条 /// /// void WindowAppItemInterface::drawInterfaceLine(QPainter* painter) { // 如果是Goto工具的输出接口,则画一个特殊的三角形箭头 if ( this->m_infInfo->isGotoToolEnd()) { this->drawArrowOutput(painter); } // 2022-8-28,如果是ForLoop工具的ToolEnd接口,也需要画一个特殊的三角箭头,但是高度有区别 else if (this->m_infInfo->isForLoopToolEnd()) { // 调整三角形高度之后绘制 this->drawArrowOutput(painter, -10); } // 如果是Parallel工具的输出接口,则画一个特殊的并行母线 else if (this->m_infInfo->isParallelToolEnd()) { this->drawParallelOutput(painter); } // 否则绘制默认的接口线条效果 else { painter->drawLine(line()); } } /// /// 绘制接口文字 /// /// void WindowAppItemInterface::drawInterfaceText(QPainter* painter) { if ( this->m_infInfo->bShowName ) { painter->setPen(COLOR_TEXT); painter->setFont(FONT_INF); painter->drawText(m_ptInfTitle, m_infInfo->strName); } } /// /// 绘制Goto输出接口的三角形 /// /// void WindowAppItemInterface::drawArrowOutput(QPainter* painter, int nFixHeight) { QPainterPath path; // 起点 QPointF ptStart(m_parentRect.right() + 1, -GOTO_OUTPUT_TRIA_SIDE / 2 + nFixHeight); // 终点 QPointF ptEnd(ptStart.rx() + GOTO_OUTPUT_TRIA_SIDE * qSin(60 * 3.14 / 180), nFixHeight); path.moveTo(ptStart.rx(), -GOTO_OUTPUT_TRIA_SIDE / 2 + nFixHeight); path.lineTo(ptStart.rx(), GOTO_OUTPUT_TRIA_SIDE / 2 + nFixHeight); // 按照正三角形的方式绘制 path.lineTo(ptEnd); // 如果是Goto工具,则需要根据工具的执行状态改变箭头颜色 if (this->m_pParentTool->isGotoTool()) { if (this->m_pParentTool->execParams.nRetValue != VPEnum::RETURN_VALUE::Goto) { painter->fillPath(path, QBrush(COLOR_GOTO_OUTPUT_READY)); } else { painter->fillPath(path, QBrush(COLOR_GOTO_OUTPUT_DONE)); } } else { painter->fillPath(path, QBrush(COLOR_ARROW_OUTPUT)); } } /// /// 绘制并行工具的输出接口(并行母线) /// /// void WindowAppItemInterface::drawParallelOutput(QPainter* painter) { //QPointF start(m_parentRect.x() - PARARREL_LINE_EX_LEN, m_parentRect.bottom() + PARARREL_LINE_SPACE); //painter->fillRect( // start.rx(), // start.ry(), // m_nParallelLineLen, // PARARREL_LINE_HEIGHT, // COLOR_FRAME_PARALLEL //); painter->fillRect( line().x1(), line().y1(), line().length(), PARARREL_LINE_HEIGHT, COLOR_FRAME_PARALLEL ); } /// /// 更新常规接口位置 /// void WindowAppItemInterface::updateRegularPostion(int nIndex) { // 计算线条高度 int lineHeight = 0; // 根据Tool类型调整一下起始高度 //2022-9-20(所有既带ToolInterface又带普通接口的工具都需要按标准工具的布局处理) if (m_infInfo->parent()->isStandardTool() || m_infInfo->parent()->isForloopTool() || m_infInfo->parent()->isWaitTool() ) { lineHeight = m_parentRect.top() + TBD_INF_OFFSET + nIndex * (short)TBD_INF_SPACING; } else { lineHeight = m_parentRect.top() + PBD_INF_OFFSET; } // 设置线条和文字位置(需要区分左右) QRect textRect = QFontMetrics(FONT_INF).boundingRect(m_infInfo->strName); // 输出接口文字位置 if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_OUT) { QLineF lineInf( QPointF(m_parentRect.right() + 1, lineHeight), QPointF(m_parentRect.right() + TBD_INF_LINE + 1, lineHeight) ); setLine(lineInf); if (m_pParentTool->Type != TOOL_TYPE::TOOL_TYPE_GOTO) { int textX = m_parentRect.right() - textRect.width() - 4; int textY = lineHeight + textRect.height() / 4; m_ptInfTitle = QPointF(textX, textY); } // 2022-4-4增加,如果是Goto工具,则需要调整一下输出接口的显示未知 // 因为Goto工具有序号遮挡,需要把文字的位置左移 else { int textX = m_parentRect.right() - textRect.width() - TBD_INDEX_WIDTH - 4; int textY = lineHeight + textRect.height() / 4; m_ptInfTitle = QPointF(textX, textY); } } // 输入接口文字位置 else { QLineF lineInf( QPointF(m_parentRect.left() - TBD_INF_LINE, lineHeight), QPointF(m_parentRect.left(), lineHeight) ); setLine(lineInf); int textX = m_parentRect.left() + 4; int textY = lineHeight + textRect.height() / 4; m_ptInfTitle = QPointF(textX, textY); } } /// /// 更新Goto输出接口位置 /// void WindowAppItemInterface::updateGotoPosition() { // 起点 QPointF ptStart(m_parentRect.right() + 1, -GOTO_OUTPUT_TRIA_SIDE / 2); // 终点 QPointF ptEnd(ptStart.rx() + GOTO_OUTPUT_TRIA_SIDE * qSin(60 * 3.14 / 180), 0); // 2022-4-23增加,此处应该把Line也设置一下,因为Link的时候是以Line为坐标来Link的 this->setLine(ptStart.rx(), 0, ptEnd.rx(), ptEnd.ry()); } /// /// 更新Parallel输出接口位置 /// void WindowAppItemInterface::updateParallelPosition() { // 获取本接口连接的下联接口 QVector<_INTERFACE*> linkInterfaces = this->m_infInfo->pDownLinkInterfaces; // 如果尚未下联接口,则使用默认位置 if (linkInterfaces.size() <= 0) { // 基准起点 QPointF start(m_parentRect.x() - PARARREL_LINE_EX_LEN, m_parentRect.bottom() + PARARREL_LINE_SPACE); // 设置并行母线线条,母线矩形上沿 this->setLine( start.rx(), start.ry() + PARARREL_LINE_HEIGHT, start.rx() + PARARREL_LINE_BASE_LEN + PARARREL_LINE_EX_LEN, // 基础长度 start.ry() + PARARREL_LINE_HEIGHT ); } // 如果有下联接口,则遍历所有下联接口连线的坐标位置,用于并行母线的坐标参考 else { // 取出对应的LinkItem连线,这些都是从并行母线到下面各个Block的ToolStart接口连线 QList linkItems = (qobject_cast(this->scene()))->getLinkItemsByInfItem(this); // 遍历所有的接口,取出左边界和右边界的最大值 QRectF sceneParentRect = this->mapRectToScene(m_parentRect); int nBaseLeft = sceneParentRect.x(); int nBaseRight = nBaseLeft + PARARREL_LINE_BASE_LEN; int nMaxLeft = nBaseLeft; int nMaxRight = 0; // 遍历所有下联接口的Item,找到最左Item和最右Item for (auto linkItem : linkItems) { QLineF linkLine = linkItem->startLine(); int ptX = linkLine.p1().x(); // qDebug() << "linkLine.p1().x: " << ptX << " ParallineLeft: " << nBaseLeft << " ParallineRight: " << nBaseRight; if (ptX < nMaxLeft) { nMaxLeft = ptX; } else if (ptX > nMaxRight) { nMaxRight = ptX; } } // 根据下联接口线的位置,调整母线的长度 // 调整母线左侧 if (nMaxLeft < nBaseLeft) { QPointF pt = this->mapToScene(this->line().p1()); pt.setX(nMaxLeft - PARARREL_LINE_EX_LEN); pt = this->mapFromScene(pt); // qDebug() << "Before linkLine: " << line() << " pt:" << pt; this->setLine(QLineF(pt, line().p2())); // qDebug() << "Ajusted linkLine: " << line(); } // 调整母线右侧 if (nMaxRight + PARARREL_LINE_EX_LEN > nBaseRight) { QPointF pt = this->mapToScene(this->line().p2()); pt.setX(nMaxRight + PARARREL_LINE_EX_LEN); pt = this->mapFromScene(pt); // qDebug() << "Before linkLine: " << line() << " pt:" << pt; this->setLine(QLineF(line().p1(), pt)); // qDebug() << "Ajusted linkLine: " << line(); } } } /// /// 鼠标双击时,自动添加port变量并连接 /// /// void WindowAppItemInterface::mouseDoubleClickEvent(QGraphicsSceneMouseEvent* event) { Q_UNUSED(event); // QMessageBox::information(nullptr, "Vision Plus", "mouseDoubleClickEvent"); //qDebug() << this->scenePos(); //qDebug() << this->mapToScene(this->line().p1()) << this->mapToScene(this->line().p2()); // 只有鼠标左键才响应 // if (event->button() == Qt::LeftButton && !m_bShowOnly) // { // // 由于Interface本身的图形已经和所属的Block整合到了一起,所以通过Interface的scenePos()获取的是其父block的Pos // // 此处需要帮助外部函数提供一个本Interface的真实Pos // QLineF realLine = QLineF( // this->mapToScene(this->line().p1()), // this->mapToScene(this->line().p2()) // ); // // ((WindowAppPouScene*)scene())->addPortAndAutolink(this, realLine); // } } /// /// 更新最新的父矩形区域 /// /// void WindowAppItemInterface::updateParentRect(QRectF parentRect) { // 首先转换坐标系 QPointF ptFix = mapFromScene(0, 0); parentRect.translate(ptFix); m_parentRect = parentRect; } /// /// 根据Block的位置和自身的序号更新本接口的位置(标准接口) /// /// void WindowAppItemInterface::updatePostion(int nIndex) { // 由于Goto输出接口是一个三角形,所以Goto接口需要专门处理 if (this->m_infInfo->isGotoToolEnd()) { this->updateGotoPosition(); } // 由于Parallel输出接口是并行母线的形式,所以Parallel输出接口需要专门处理 else if (this->m_infInfo->isParallelToolEnd()) { this->updateParallelPosition(); } // 如果是正常的ToolInterface接口,直接走Tool类型的接口位置更新 else if (this->m_infInfo->isToolInterface()) { this->updateToolInterfacePostion(); } // 剩下的都按常规接口更新 else { this->updateRegularPostion(nIndex); } } /// /// 根据Block的位置计算ToolStart、ToolEnd接口的位置(标准工具、并行工具、For工具都会调用到此处) /// /// void WindowAppItemInterface::updateToolInterfacePostion() { // 输入接口 if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_IN) { // 线条高度 int lineHeight = m_parentRect.top() + TBD_TOPINF_SPACING; // 设置线条位置 QRect textRect = QFontMetrics(FONT_INF).boundingRect(m_infInfo->strName); QLineF lineTop( QPointF(m_parentRect.left() - TBD_TOPINF_LINE, lineHeight), QPointF(m_parentRect.left(), lineHeight) ); setLine(lineTop); //// 设置文字位置(目前ToolStart接口暂时不显示名字,为了以后需要,先计算出来) //int textX = m_parentRect.left() + 4; //int textY = lineHeight + textRect.height() / 4; //m_ptInfTitle = QPointF(textX, textY); } // 输出接口 else { // 线条高度 int lineHeight = m_parentRect.top() + TBD_TOPINF_SPACING; // 设置线条位置 QRect textRect = QFontMetrics(FONT_INF).boundingRect(m_infInfo->strName); QLineF lineTop( QPointF(m_parentRect.right() + TBD_TOPINF_LINE, lineHeight), QPointF(m_parentRect.right(), lineHeight) ); setLine(lineTop); //// 设置文字位置(目前ToolStart接口暂时不显示名字,为了以后需要,先计算出来) //int textX = m_parentRect.left() + 4; //int textY = lineHeight + textRect.height() / 4; //m_ptInfTitle = QPointF(textX, textY); } } /// /// 判断父Block是否处于选中状态 /// /// bool WindowAppItemInterface::IsParentSelected() { bool bIsParentSel = false; WindowAppBlockBase* pParentBlock = qgraphicsitem_cast(this->parentItem()); bIsParentSel = pParentBlock->isSelected(); return bIsParentSel; } /// /// 显示动态右键菜单 /// /// void WindowAppItemInterface::contextMenuEvent(QGraphicsSceneContextMenuEvent* event) { Q_UNUSED(event); // 设置接口为选中状态 this->setSelected(true); // 如果只仅供展示用,则不显示右键菜单 if (m_bShowOnly) { return; } // 动态创建 createDynamicContextMenu(); } /// /// 新建Interface的右键菜单 /// void WindowAppItemInterface::createDynamicContextMenu() { if (m_infInfo->isGotoToolEnd() || m_infInfo->isParallelToolStart() || m_infInfo->isParallelToolEnd() //|| m_infInfo->isToolStart() //|| m_infInfo->isToolEnd() ) { return; } // 硬件组态不显示右键菜单 if (m_pPou->pouName() == GROUP_NAME_HARDWARE) { return; } QMenu* contextMenu = new QMenu(); QMenu* childMenu = new QMenu(); QAction* unLinkAction = new QAction(("Unlink"), this); QAction* smartLinkAction = new QAction(("Smart link"), this); QAction* addWatchAction = new QAction(("Add Watch..."), this); QAction* addPortAction = new QAction(("Add Port..."), this); QAction* disableAction = new QAction(("Disable"), this); QAction* linkAction; // 根据输入输出显示不同的内容 if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_OUT) { linkAction = new QAction(("Link To..."), this); } else { linkAction = new QAction(("Link From..."), this); } connect(childMenu, SIGNAL(triggered(QAction*)), this, SLOT(onMenuLink(QAction*))); connect(unLinkAction, &QAction::triggered, this, &WindowAppItemInterface::onMenuUnlink); connect(smartLinkAction, &QAction::triggered, this, &WindowAppItemInterface::onMenuSmartlink); connect(addWatchAction, &QAction::triggered, this, &WindowAppItemInterface::onMenuAddWatch); connect(addPortAction, &QAction::triggered, this, &WindowAppItemInterface::onMenuAddPort); connect(disableAction, &QAction::triggered, this, &WindowAppItemInterface::onMenuDisable); // 根据适配的接口创建对应的菜单项 const QMap allInfs = m_pPou->GetAllInterfaces(); QMapIterator i(allInfs); while (i.hasNext()) { const _INTERFACE* pInf = i.next().value(); // 方向相反、类型相同、不从属于一个工具、并且父工具不是Port类型 // 目标端口未被引用 , 端口为启用状态 if (pInf->isRevDirectionTo(this->m_infInfo) && pInf->isSameTypeTo(this->m_infInfo) && pInf->parent() !=this->m_infInfo->parent() && pInf->parent()->isStandardTool() && (pInf->nRefCount == 0 || pInf->Direction == INF_DIRECTION::INF_DIR_OUT) && pInf->bEnable ) { QAction* childAction = new QAction(i.key(), this); childMenu->addAction(childAction); } } // 设置菜单结构 if (childMenu->actions().count() > 0) { linkAction->setMenu(childMenu); } // 输入端口,且未链接过数据 if ( m_infInfo->Direction == INF_DIRECTION::INF_DIR_IN && m_infInfo->nRefCount == 0 ) { contextMenu->addAction(linkAction); } // 输出端口,都可以添加 if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_OUT) { contextMenu->addAction(linkAction); } // 如果引用计数不等于 0 ,该端口允许取消链接(因为取消无意义) if (m_infInfo->nRefCount != 0) { contextMenu->addAction(unLinkAction); } contextMenu->addSeparator(); // 只有输入端口有Smartlink选项 if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_IN && m_infInfo->nRefCount == 0 ) { contextMenu->addAction(smartLinkAction); contextMenu->addSeparator(); } contextMenu->addAction(addWatchAction); // 输出端口,和输入端口引用计数为 0 的时候,允许添加 Port if (m_infInfo->Direction == INF_DIRECTION::INF_DIR_OUT && m_infInfo->nRefCount == 0 ) { contextMenu->addAction(addPortAction); } contextMenu->addSeparator(); // 如果引用计数大于 0 ,该端口不添加删除菜单 if (m_infInfo->nRefCount == 0) { contextMenu->addAction(disableAction); } contextMenu->exec(QCursor::pos()); } /// /// 菜单 - Link /// /// void WindowAppItemInterface::onMenuLink(QAction* action) { QString strInfName = action->text(); // 从Pou中找到相应的接口 WindowAppItemInterface* linktoInfItem = m_pPou->GetInterfaceItemByName(strInfName); // 此处一定不为nullptr if (linktoInfItem != nullptr) { // 根据输入输出调整link方向 if (this->m_infInfo->Direction == INF_DIRECTION::INF_DIR_OUT) { // 建立Link ((WindowAppPouScene*)scene())->addLink(this, linktoInfItem); } else { // 建立Link ((WindowAppPouScene*)scene())->addLink(linktoInfItem, this); } } } /// /// 菜单 - Unlink /// 无需检查引用计数,而且一个接口如果有多个link连线,一次性全部删除 /// void WindowAppItemInterface::onMenuUnlink() { // 直接调用scene来清除连线相关信息 ((WindowAppPouScene*)scene())->delLink(this); } /// /// 菜单 - Smartlink (只有输入端口可以执行,找离本接口最近的同类型输出端口,序号小于自己的) /// void WindowAppItemInterface::onMenuSmartlink() { // 如果本身已经处于link状态,则不处理 if (this->m_infInfo->pUpLinkInterface != nullptr) { Utility::VPCriticalMessageBox("This interface is alreaday linked!"); return; } // 调用scene()执行自动连接 ((WindowAppPouScene*)scene())->smartLink(this); } /// /// 菜单 - Add Watch /// void WindowAppItemInterface::onMenuAddWatch() { } /// /// 菜单 - Add Port /// void WindowAppItemInterface::onMenuAddPort() { if (!m_bShowOnly) { // 由于Interface本身的图形已经和所属的Block整合到了一起,所以通过Interface的scenePos()获取的是其父block的Pos // 此处需要帮助外部函数提供一个本Interface的真实Pos QLineF realLine = QLineF( this->mapToScene(this->line().p1()), this->mapToScene(this->line().p2()) ); ((WindowAppPouScene*)scene())->addPortAndAutolink(this, realLine); } } /// /// 菜单 - Disable /// void WindowAppItemInterface::onMenuDisable() { // 首先检查引用计数 int nRefCount = this->m_infInfo->nRefCount; if (nRefCount > 0) { Utility::VPCriticalMessageBox("Can't disable this interface for reference count is " + QString::number(nRefCount)); return; } // 禁用此接口 bool bRet = m_pPou->setInterfaceEnable(this->m_infInfo, false); if (!bRet) { Utility::VPCriticalMessageBox( "Can't disable this interface for reference count is " + QString::number(this->m_infInfo->nRefCount)); return; } // 重新更新父接口 // 由于只有Standard类型的会有此操作,所以直接通知Standard类型的父功能块重绘 ((WindowAppBlockStandard*)parentItem())->updatePosition(); // 重绘 ((WindowAppPouScene*)scene())->update(); } //void WindowAppItemInterface::mousePressEvent(QGraphicsSceneMouseEvent* mouseEvent) //{ // // 切换scene的操作模式 // (qobject_cast(scene()))->modeScene = MODE::LINK_MODE; // // qDebug() << "WindowAppItemInterface::mousePressEvent"; // // QGraphicsLineItem::mousePressEvent(mouseEvent); //} // 悬停事件处理函数,外观效果 void WindowAppItemInterface::hoverEnterEvent(QGraphicsSceneHoverEvent* event) { // qDebug("WindowAppItemInterface::hoverEnterEvent"); if (m_infInfo && ( m_infInfo->Type == INF_TYPE::INF_TYPE_STANDARD || m_infInfo->Type == INF_TYPE::INF_TYPE_VALUE ) ) { // 2022-9-28,如果接口被废弃了,就不要再显示接口的值了,否则会崩溃 if (m_infInfo->Discard != INF_DISCARD::INF_DEFAULT) { return; } QString strValue = m_infInfo->getValueString(); QString strType = m_infInfo->strNameWithType; setToolTip(strType + "\r\nValue: " + strValue); } else { // 可以设置鼠标效果以及鼠标提示 if (m_infInfo != nullptr) { QString strName = m_infInfo->strFullName; QString strType = m_infInfo->strNameWithType; setToolTip(strType + "\r\n" + strName); } } // if ((qobject_cast(scene()))->modeScene == MODE::LINK_MODE) // { // this->setSelected(true); // } QGraphicsLineItem::hoverEnterEvent(event); } //void WindowAppItemInterface::hoverMoveEvent(QGraphicsSceneHoverEvent* event) //{ // qDebug("WindowAppItemInterface::hoverMoveEvent"); //} // //void WindowAppItemInterface::hoverLeaveEvent(QGraphicsSceneHoverEvent* event) //{ // qDebug("WindowAppItemInterface::hoverLeaveEvent"); // // // setCursor(Qt::ArrowCursor); // // QGraphicsLineItem::hoverLeaveEvent(event); //} //void WindowAppItemInterface::mouseReleaseEvent(QGraphicsSceneMouseEvent* mouseEvent) //{ // qDebug() << "WindowAppItemInterface::mouseReleaseEvent..."; // // qDebug("%X", this); // // QGraphicsLineItem::mouseReleaseEvent(mouseEvent); //} // //bool WindowAppItemInterface::event(QEvent* e) { // if (e->type() == QEvent::ToolTip) // { // qDebug() << "tool tip show"; // } // else if (e->type() == QEvent::Leave) // { // qDebug() << "tool tip leave"; // } // return QGraphicsItem::event(e); //}