void C4Network2ClientListBox::ConnectionListItem::Update() { C4Network2IOConnection *pConn = GetConnection(); if (!pConn) { // No connection: Shouldn't happen pDesc->SetText("???"); pPing->SetText("???"); return; } // update connection ping int iPing = pConn->getLag(); pPing->SetText(FormatString("%d ms", iPing).getData()); // update description // get connection usage const char *szConnType; C4Network2Client *pNetClient = ::Network.Clients.GetClientByID(iClientID); if (pNetClient->getDataConn() == pNetClient->getMsgConn()) szConnType = "Data/Msg"; else if (iConnID) szConnType = "Msg"; else szConnType = "Data"; // display info pDesc->SetText(FormatString("%s: %s (%s l%d)", szConnType, ::Network.NetIO.getNetIOName(pConn->getNetClass()), pConn->getPeerAddr().ToString().getData(), pConn->getPacketLoss()).getData()); }
C4Network2IOConnection *C4Network2ClientListBox::ConnectionListItem::GetConnection() const { // get connection by connection ID C4Network2Client *pNetClient = ::Network.Clients.GetClientByID(iClientID); if (!pNetClient) return nullptr; if (iConnID == 0) return pNetClient->getDataConn(); if (iConnID == 1) return pNetClient->getMsgConn(); return nullptr; }
void C4Network2ClientDlg::UpdateText() { // begin updating (clears previous text) BeginUpdateText(); // get core const C4Client *pClient = Game.Clients.getClientByID(iClientID); if (!pClient) { // client ID unknown AddLineFmt(LoadResStr("IDS_NET_CLIENT_INFO_UNKNOWNID"), iClientID); } else { // get client (may be nullptr for local info) C4Network2Client *pNetClient = pClient->getNetClient(); // show some info StdCopyStrBuf strInfo; if (!pClient->isActivated()) { strInfo.Append(LoadResStr("IDS_MSG_INACTIVE")); strInfo.Append(" "); } if (pClient->isLocal()) { strInfo.Append(LoadResStr("IDS_MSG_LOCAL")); strInfo.Append(" "); } strInfo.AppendFormat("%s %s (ID #%d)%s", LoadResStr(pClient->isHost() ? "IDS_MSG_HOST" : "IDS_MSG_CLIENT"), pClient->getName(), iClientID, ::Network.isHost() && pNetClient && !pNetClient->isReady() ? " (!ack)" : ""); AddLine(strInfo.getData()); // show addresses int iCnt; if ((iCnt=pNetClient->getAddrCnt())) { AddLine(LoadResStr("IDS_NET_CLIENT_INFO_ADDRESSES")); for (int i=0; i<iCnt; ++i) { C4Network2Address addr = pNetClient->getAddr(i); AddLineFmt(" %d: %s", i, // adress index addr.toString().getData()); } } else AddLine(LoadResStr("IDS_NET_CLIENT_INFO_NOADDRESSES")); // show connection if (pNetClient) { // connections if (pNetClient->isConnected()) { AddLineFmt(LoadResStr("IDS_NET_CLIENT_INFO_CONNECTIONS"), pNetClient->getMsgConn() == pNetClient->getDataConn() ? "Msg/Data" : "Msg", ::Network.NetIO.getNetIOName(pNetClient->getMsgConn()->getNetClass()), pNetClient->getMsgConn()->getPeerAddr().ToString().getData(), pNetClient->getMsgConn()->getPingTime()); if (pNetClient->getMsgConn() != pNetClient->getDataConn()) AddLineFmt(LoadResStr("IDS_NET_CLIENT_INFO_CONNDATA"), ::Network.NetIO.getNetIOName(pNetClient->getDataConn()->getNetClass()), pNetClient->getDataConn()->getPeerAddr().ToString().getData(), pNetClient->getDataConn()->getPingTime()); } else AddLine(LoadResStr("IDS_NET_CLIENT_INFO_NOCONNECTIONS")); } } // update done EndUpdateText(); }
void C4Network2ClientListBox::Update() { // sync with client list ListItem *pItem = static_cast<ListItem *>(pClientWindow->GetFirst()), *pNext; const C4Client *pClient = nullptr; while ((pClient = Game.Clients.getClient(pClient))) { // skip host in startup board if (IsStartup() && pClient->isHost()) continue; // deleted client(s) present? this will also delete unneeded client connections of previous client while (pItem && (pItem->GetClientID() < pClient->getID())) { pNext = static_cast<ListItem *>(pItem->GetNext()); delete pItem; pItem = pNext; } // same present for update? // need not check for connection ID, because a client item will always be placed before the corresponding connection items if (pItem && pItem->GetClientID() == pClient->getID()) { pItem->Update(); pItem = static_cast<ListItem *>(pItem->GetNext()); } else // not present: insert (or add if pItem=nullptr) InsertElement(new ClientListItem(this, pClient->getID()), pItem); // update connections for client // but no connections in startup board if (IsStartup()) continue; // enumerate client connections C4Network2Client *pNetClient = pClient->getNetClient(); if (!pNetClient) continue; // local client does not have connections C4Network2IOConnection *pLastConn = nullptr; for (int i = 0; i<2; ++i) { C4Network2IOConnection *pConn = i ? pNetClient->getMsgConn() : pNetClient->getDataConn(); if (!pConn) continue; if (pConn == pLastConn) continue; // combined connection: Display only one pLastConn = pConn; // del leading items while (pItem && ((pItem->GetClientID() < pClient->getID()) || ((pItem->GetClientID() == pClient->getID()) && (pItem->GetConnectionID() < i)))) { pNext = static_cast<ListItem *>(pItem->GetNext()); delete pItem; pItem = pNext; } // update connection item if (pItem && pItem->GetClientID() == pClient->getID() && pItem->GetConnectionID() == i) { pItem->Update(); pItem = static_cast<ListItem *>(pItem->GetNext()); } else { // new connection: create it InsertElement(new ConnectionListItem(this, pClient->getID(), i), pItem); } } } // del trailing items while (pItem) { pNext = static_cast<ListItem *>(pItem->GetNext()); delete pItem; pItem = pNext; } }