帮助,我疯了:)
我正在玩TeamSpeak3并有一个dll调用,它会在线返回一组客户端(ID' s)。我的问题是它在一个我无法想象在Object Pascal中读取的结构中返回。
SDK手册指定了:
This is what the docs says
To get a list of all currently visible clients on the specified virtual server:
unsigned intts3client_getClientList(serverConnectionHandlerID, result);
uint64 serverConnectionHandlerID;
anyID** result;
Parameters
• serverConnectionHandlerID
ID of the server connection handler for which the list of clients is requested.
• result
Address of a variable that receives a NULL-termianted array of client IDs. Unless an error occurs, the array must be released
using ts3client_freeMemory.
Returns ERROR_ok on success, otherwise an error code as defined in public_errors.h. If an error has occured, the
result array is uninitialized and must not be released.
到目前为止,这是我的Delphi代码。
type
PPanyID = ^PAnyID;
PanyID = ^anyID;
anyID = word;
// declaration looks like this, some guy called CodeJunkie ported it from C++)
function ts3client_getClientList(serverConnectionHandlerID: uint64; result: PPanyID): longword; cdecl; external CLIENT_DLL {$IFDEF MACOS}name '_ts3client_getClientList'{$ENDIF};
procedure TfrmMain.RequestOnlineClients;
var
clientids : PAnyId;
i : Integer;
begin
error := ts3client_getClientList(FTSServerHandlerID, @clientids);
if (error <> ERROR_ok) then
begin
if (ts3client_getErrorMessage(error, @errormsg) = ERROR_ok) then
begin
LogMsg(Format('Error requesting online clients: %s', [errormsg]));
ts3client_freeMemory(errormsg);
end;
end else
begin
// Put in into some regular Object array here, but how the h......
// Or at least interate the received array of ID's
end;
end;
C ++中的示例代码看起来像这样,它可以工作,我没有写它:)
void showClients(uint64 serverConnectionHandlerID) {
anyID *ids;
anyID ownClientID;
int i;
unsigned int error;
printf("\nList of all visible clients on virtual server %llu:\n", (unsigned long long)serverConnectionHandlerID);
if((error = ts3client_getClientList(serverConnectionHandlerID, &ids)) != ERROR_ok) { /* Get array of client IDs */
printf("Error getting client list: %d\n", error);
return;
}
if(!ids[0]) {
printf("No clients\n\n");
ts3client_freeMemory(ids);
return;
}
/* Get own clientID as we need to call CLIENT_FLAG_TALKING with getClientSelfVariable for own client */
if((error = ts3client_getClientID(serverConnectionHandlerID, &ownClientID)) != ERROR_ok) {
printf("Error querying own client ID: %d\n", error);
return;
}
for(i=0; ids[i]; i++) {
char* name;
int talkStatus;
if((error = ts3client_getClientVariableAsString(serverConnectionHandlerID, ids[i], CLIENT_NICKNAME, &name)) != ERROR_ok) { /* Query client nickname... */
printf("Error querying client nickname: %d\n", error);
break;
}
if(ids[i] == ownClientID) { /* CLIENT_FLAG_TALKING must be queried with getClientSelfVariable for own client */
if((error = ts3client_getClientSelfVariableAsInt(serverConnectionHandlerID, CLIENT_FLAG_TALKING, &talkStatus)) != ERROR_ok) {
printf("Error querying own client talk status: %d\n", error);
break;
}
} else {
if((error = ts3client_getClientVariableAsInt(serverConnectionHandlerID, ids[i], CLIENT_FLAG_TALKING, &talkStatus)) != ERROR_ok) {
printf("Error querying client talk status: %d\n", error);
break;
}
}
printf("%u - %s (%stalking)\n", ids[i], name, (talkStatus == STATUS_TALKING ? "" : "not "));
ts3client_freeMemory(name);
}
printf("\n");
ts3client_freeMemory(ids); /* Release array */
}
拜托,有人可以帮忙吗?
答案 0 :(得分:0)
你得到的指针指向第一个结果。执行Inc(clientids)
会使您转到下一个结果。继续前进,直到达到零anyid
(&#34; NULL&#34;)。
(您还需要保存clientids
的原始值,以便您可以将其传递给自由函数,如文档所述,以避免泄漏内存。)
答案 1 :(得分:0)
G 这是真的,这是否是读取从c ++ dll返回的数组的唯一方法?这也适用于64位吗?
procedure TfrmMain.RequestOnlineClients;
var
ids : array of anyID;
pids : PanyID;
aid : anyID;
begin
error := ts3client_getClientList(FTSServerHandlerID, @ids);
if (error <> ERROR_ok) then
begin
if (ts3client_getErrorMessage(error, @errormsg) = ERROR_ok) then
begin
LogMsg(Format('Error requesting online clients: %s', [errormsg]));
ts3client_freeMemory(errormsg);
end;
end else
begin
pids := @ids[0];
while (pids^ <> 0) do
begin
aid := pids^;
LogMsg(format('id %u',[aid]));
inc(pids);
end;
ts3client_freeMemory(@pids^);
end;
end;