isteammatchmaking.cs 51 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892
  1. // This file is provided under The MIT License as part of Steamworks.NET.
  2. // Copyright (c) 2013-2019 Riley Labrecque
  3. // Please see the included LICENSE.txt for additional information.
  4. // This file is automatically generated.
  5. // Changes to this file will be reverted when you update Steamworks.NET
  6. #if UNITY_ANDROID || UNITY_IOS || UNITY_TIZEN || UNITY_TVOS || UNITY_WEBGL || UNITY_WSA || UNITY_PS4 || UNITY_WII || UNITY_XBOXONE || UNITY_SWITCH
  7. #define DISABLESTEAMWORKS
  8. #endif
  9. #if !DISABLESTEAMWORKS
  10. using System.Runtime.InteropServices;
  11. using IntPtr = System.IntPtr;
  12. namespace Steamworks {
  13. public static class SteamMatchmaking {
  14. /// <summary>
  15. /// <para> game server favorites storage</para>
  16. /// <para> saves basic details about a multiplayer game server locally</para>
  17. /// <para> returns the number of favorites servers the user has stored</para>
  18. /// </summary>
  19. public static int GetFavoriteGameCount() {
  20. InteropHelp.TestIfAvailableClient();
  21. return NativeMethods.ISteamMatchmaking_GetFavoriteGameCount(CSteamAPIContext.GetSteamMatchmaking());
  22. }
  23. /// <summary>
  24. /// <para> returns the details of the game server</para>
  25. /// <para> iGame is of range [0,GetFavoriteGameCount())</para>
  26. /// <para> *pnIP, *pnConnPort are filled in the with IP:port of the game server</para>
  27. /// <para> *punFlags specify whether the game server was stored as an explicit favorite or in the history of connections</para>
  28. /// <para> *pRTime32LastPlayedOnServer is filled in the with the Unix time the favorite was added</para>
  29. /// </summary>
  30. public static bool GetFavoriteGame(int iGame, out AppId_t pnAppID, out uint pnIP, out ushort pnConnPort, out ushort pnQueryPort, out uint punFlags, out uint pRTime32LastPlayedOnServer) {
  31. InteropHelp.TestIfAvailableClient();
  32. return NativeMethods.ISteamMatchmaking_GetFavoriteGame(CSteamAPIContext.GetSteamMatchmaking(), iGame, out pnAppID, out pnIP, out pnConnPort, out pnQueryPort, out punFlags, out pRTime32LastPlayedOnServer);
  33. }
  34. /// <summary>
  35. /// <para> adds the game server to the local list; updates the time played of the server if it already exists in the list</para>
  36. /// </summary>
  37. public static int AddFavoriteGame(AppId_t nAppID, uint nIP, ushort nConnPort, ushort nQueryPort, uint unFlags, uint rTime32LastPlayedOnServer) {
  38. InteropHelp.TestIfAvailableClient();
  39. return NativeMethods.ISteamMatchmaking_AddFavoriteGame(CSteamAPIContext.GetSteamMatchmaking(), nAppID, nIP, nConnPort, nQueryPort, unFlags, rTime32LastPlayedOnServer);
  40. }
  41. /// <summary>
  42. /// <para> removes the game server from the local storage; returns true if one was removed</para>
  43. /// </summary>
  44. public static bool RemoveFavoriteGame(AppId_t nAppID, uint nIP, ushort nConnPort, ushort nQueryPort, uint unFlags) {
  45. InteropHelp.TestIfAvailableClient();
  46. return NativeMethods.ISteamMatchmaking_RemoveFavoriteGame(CSteamAPIContext.GetSteamMatchmaking(), nAppID, nIP, nConnPort, nQueryPort, unFlags);
  47. }
  48. /// <summary>
  49. /// <para>/////</para>
  50. /// <para> Game lobby functions</para>
  51. /// <para> Get a list of relevant lobbies</para>
  52. /// <para> this is an asynchronous request</para>
  53. /// <para> results will be returned by LobbyMatchList_t callback &amp; call result, with the number of lobbies found</para>
  54. /// <para> this will never return lobbies that are full</para>
  55. /// <para> to add more filter, the filter calls below need to be call before each and every RequestLobbyList() call</para>
  56. /// <para> use the CCallResult&lt;&gt; object in steam_api.h to match the SteamAPICall_t call result to a function in an object, e.g.</para>
  57. /// <para> class CMyLobbyListManager</para>
  58. /// <para> {</para>
  59. /// <para> CCallResult&lt;CMyLobbyListManager, LobbyMatchList_t&gt; m_CallResultLobbyMatchList;</para>
  60. /// <para> void FindLobbies()</para>
  61. /// <para> {</para>
  62. /// <para> // SteamMatchmaking()-&gt;AddRequestLobbyListFilter*() functions would be called here, before RequestLobbyList()</para>
  63. /// <para> SteamAPICall_t hSteamAPICall = SteamMatchmaking()-&gt;RequestLobbyList();</para>
  64. /// <para> m_CallResultLobbyMatchList.Set( hSteamAPICall, this, &amp;CMyLobbyListManager::OnLobbyMatchList );</para>
  65. /// <para> }</para>
  66. /// <para> void OnLobbyMatchList( LobbyMatchList_t *pLobbyMatchList, bool bIOFailure )</para>
  67. /// <para> {</para>
  68. /// <para> // lobby list has be retrieved from Steam back-end, use results</para>
  69. /// <para> }</para>
  70. /// <para> }</para>
  71. /// </summary>
  72. public static SteamAPICall_t RequestLobbyList() {
  73. InteropHelp.TestIfAvailableClient();
  74. return (SteamAPICall_t)NativeMethods.ISteamMatchmaking_RequestLobbyList(CSteamAPIContext.GetSteamMatchmaking());
  75. }
  76. /// <summary>
  77. /// <para> filters for lobbies</para>
  78. /// <para> this needs to be called before RequestLobbyList() to take effect</para>
  79. /// <para> these are cleared on each call to RequestLobbyList()</para>
  80. /// </summary>
  81. public static void AddRequestLobbyListStringFilter(string pchKeyToMatch, string pchValueToMatch, ELobbyComparison eComparisonType) {
  82. InteropHelp.TestIfAvailableClient();
  83. using (var pchKeyToMatch2 = new InteropHelp.UTF8StringHandle(pchKeyToMatch))
  84. using (var pchValueToMatch2 = new InteropHelp.UTF8StringHandle(pchValueToMatch)) {
  85. NativeMethods.ISteamMatchmaking_AddRequestLobbyListStringFilter(CSteamAPIContext.GetSteamMatchmaking(), pchKeyToMatch2, pchValueToMatch2, eComparisonType);
  86. }
  87. }
  88. /// <summary>
  89. /// <para> numerical comparison</para>
  90. /// </summary>
  91. public static void AddRequestLobbyListNumericalFilter(string pchKeyToMatch, int nValueToMatch, ELobbyComparison eComparisonType) {
  92. InteropHelp.TestIfAvailableClient();
  93. using (var pchKeyToMatch2 = new InteropHelp.UTF8StringHandle(pchKeyToMatch)) {
  94. NativeMethods.ISteamMatchmaking_AddRequestLobbyListNumericalFilter(CSteamAPIContext.GetSteamMatchmaking(), pchKeyToMatch2, nValueToMatch, eComparisonType);
  95. }
  96. }
  97. /// <summary>
  98. /// <para> returns results closest to the specified value. Multiple near filters can be added, with early filters taking precedence</para>
  99. /// </summary>
  100. public static void AddRequestLobbyListNearValueFilter(string pchKeyToMatch, int nValueToBeCloseTo) {
  101. InteropHelp.TestIfAvailableClient();
  102. using (var pchKeyToMatch2 = new InteropHelp.UTF8StringHandle(pchKeyToMatch)) {
  103. NativeMethods.ISteamMatchmaking_AddRequestLobbyListNearValueFilter(CSteamAPIContext.GetSteamMatchmaking(), pchKeyToMatch2, nValueToBeCloseTo);
  104. }
  105. }
  106. /// <summary>
  107. /// <para> returns only lobbies with the specified number of slots available</para>
  108. /// </summary>
  109. public static void AddRequestLobbyListFilterSlotsAvailable(int nSlotsAvailable) {
  110. InteropHelp.TestIfAvailableClient();
  111. NativeMethods.ISteamMatchmaking_AddRequestLobbyListFilterSlotsAvailable(CSteamAPIContext.GetSteamMatchmaking(), nSlotsAvailable);
  112. }
  113. /// <summary>
  114. /// <para> sets the distance for which we should search for lobbies (based on users IP address to location map on the Steam backed)</para>
  115. /// </summary>
  116. public static void AddRequestLobbyListDistanceFilter(ELobbyDistanceFilter eLobbyDistanceFilter) {
  117. InteropHelp.TestIfAvailableClient();
  118. NativeMethods.ISteamMatchmaking_AddRequestLobbyListDistanceFilter(CSteamAPIContext.GetSteamMatchmaking(), eLobbyDistanceFilter);
  119. }
  120. /// <summary>
  121. /// <para> sets how many results to return, the lower the count the faster it is to download the lobby results &amp; details to the client</para>
  122. /// </summary>
  123. public static void AddRequestLobbyListResultCountFilter(int cMaxResults) {
  124. InteropHelp.TestIfAvailableClient();
  125. NativeMethods.ISteamMatchmaking_AddRequestLobbyListResultCountFilter(CSteamAPIContext.GetSteamMatchmaking(), cMaxResults);
  126. }
  127. public static void AddRequestLobbyListCompatibleMembersFilter(CSteamID steamIDLobby) {
  128. InteropHelp.TestIfAvailableClient();
  129. NativeMethods.ISteamMatchmaking_AddRequestLobbyListCompatibleMembersFilter(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  130. }
  131. /// <summary>
  132. /// <para> returns the CSteamID of a lobby, as retrieved by a RequestLobbyList call</para>
  133. /// <para> should only be called after a LobbyMatchList_t callback is received</para>
  134. /// <para> iLobby is of the range [0, LobbyMatchList_t::m_nLobbiesMatching)</para>
  135. /// <para> the returned CSteamID::IsValid() will be false if iLobby is out of range</para>
  136. /// </summary>
  137. public static CSteamID GetLobbyByIndex(int iLobby) {
  138. InteropHelp.TestIfAvailableClient();
  139. return (CSteamID)NativeMethods.ISteamMatchmaking_GetLobbyByIndex(CSteamAPIContext.GetSteamMatchmaking(), iLobby);
  140. }
  141. /// <summary>
  142. /// <para> Create a lobby on the Steam servers.</para>
  143. /// <para> If private, then the lobby will not be returned by any RequestLobbyList() call; the CSteamID</para>
  144. /// <para> of the lobby will need to be communicated via game channels or via InviteUserToLobby()</para>
  145. /// <para> this is an asynchronous request</para>
  146. /// <para> results will be returned by LobbyCreated_t callback and call result; lobby is joined &amp; ready to use at this point</para>
  147. /// <para> a LobbyEnter_t callback will also be received (since the local user is joining their own lobby)</para>
  148. /// </summary>
  149. public static SteamAPICall_t CreateLobby(ELobbyType eLobbyType, int cMaxMembers) {
  150. InteropHelp.TestIfAvailableClient();
  151. return (SteamAPICall_t)NativeMethods.ISteamMatchmaking_CreateLobby(CSteamAPIContext.GetSteamMatchmaking(), eLobbyType, cMaxMembers);
  152. }
  153. /// <summary>
  154. /// <para> Joins an existing lobby</para>
  155. /// <para> this is an asynchronous request</para>
  156. /// <para> results will be returned by LobbyEnter_t callback &amp; call result, check m_EChatRoomEnterResponse to see if was successful</para>
  157. /// <para> lobby metadata is available to use immediately on this call completing</para>
  158. /// </summary>
  159. public static SteamAPICall_t JoinLobby(CSteamID steamIDLobby) {
  160. InteropHelp.TestIfAvailableClient();
  161. return (SteamAPICall_t)NativeMethods.ISteamMatchmaking_JoinLobby(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  162. }
  163. /// <summary>
  164. /// <para> Leave a lobby; this will take effect immediately on the client side</para>
  165. /// <para> other users in the lobby will be notified by a LobbyChatUpdate_t callback</para>
  166. /// </summary>
  167. public static void LeaveLobby(CSteamID steamIDLobby) {
  168. InteropHelp.TestIfAvailableClient();
  169. NativeMethods.ISteamMatchmaking_LeaveLobby(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  170. }
  171. /// <summary>
  172. /// <para> Invite another user to the lobby</para>
  173. /// <para> the target user will receive a LobbyInvite_t callback</para>
  174. /// <para> will return true if the invite is successfully sent, whether or not the target responds</para>
  175. /// <para> returns false if the local user is not connected to the Steam servers</para>
  176. /// <para> if the other user clicks the join link, a GameLobbyJoinRequested_t will be posted if the user is in-game,</para>
  177. /// <para> or if the game isn't running yet the game will be launched with the parameter +connect_lobby &lt;64-bit lobby id&gt;</para>
  178. /// </summary>
  179. public static bool InviteUserToLobby(CSteamID steamIDLobby, CSteamID steamIDInvitee) {
  180. InteropHelp.TestIfAvailableClient();
  181. return NativeMethods.ISteamMatchmaking_InviteUserToLobby(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, steamIDInvitee);
  182. }
  183. /// <summary>
  184. /// <para> Lobby iteration, for viewing details of users in a lobby</para>
  185. /// <para> only accessible if the lobby user is a member of the specified lobby</para>
  186. /// <para> persona information for other lobby members (name, avatar, etc.) will be asynchronously received</para>
  187. /// <para> and accessible via ISteamFriends interface</para>
  188. /// <para> returns the number of users in the specified lobby</para>
  189. /// </summary>
  190. public static int GetNumLobbyMembers(CSteamID steamIDLobby) {
  191. InteropHelp.TestIfAvailableClient();
  192. return NativeMethods.ISteamMatchmaking_GetNumLobbyMembers(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  193. }
  194. /// <summary>
  195. /// <para> returns the CSteamID of a user in the lobby</para>
  196. /// <para> iMember is of range [0,GetNumLobbyMembers())</para>
  197. /// <para> note that the current user must be in a lobby to retrieve CSteamIDs of other users in that lobby</para>
  198. /// </summary>
  199. public static CSteamID GetLobbyMemberByIndex(CSteamID steamIDLobby, int iMember) {
  200. InteropHelp.TestIfAvailableClient();
  201. return (CSteamID)NativeMethods.ISteamMatchmaking_GetLobbyMemberByIndex(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, iMember);
  202. }
  203. /// <summary>
  204. /// <para> Get data associated with this lobby</para>
  205. /// <para> takes a simple key, and returns the string associated with it</para>
  206. /// <para> "" will be returned if no value is set, or if steamIDLobby is invalid</para>
  207. /// </summary>
  208. public static string GetLobbyData(CSteamID steamIDLobby, string pchKey) {
  209. InteropHelp.TestIfAvailableClient();
  210. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey)) {
  211. return InteropHelp.PtrToStringUTF8(NativeMethods.ISteamMatchmaking_GetLobbyData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, pchKey2));
  212. }
  213. }
  214. /// <summary>
  215. /// <para> Sets a key/value pair in the lobby metadata</para>
  216. /// <para> each user in the lobby will be broadcast this new value, and any new users joining will receive any existing data</para>
  217. /// <para> this can be used to set lobby names, map, etc.</para>
  218. /// <para> to reset a key, just set it to ""</para>
  219. /// <para> other users in the lobby will receive notification of the lobby data change via a LobbyDataUpdate_t callback</para>
  220. /// </summary>
  221. public static bool SetLobbyData(CSteamID steamIDLobby, string pchKey, string pchValue) {
  222. InteropHelp.TestIfAvailableClient();
  223. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey))
  224. using (var pchValue2 = new InteropHelp.UTF8StringHandle(pchValue)) {
  225. return NativeMethods.ISteamMatchmaking_SetLobbyData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, pchKey2, pchValue2);
  226. }
  227. }
  228. /// <summary>
  229. /// <para> returns the number of metadata keys set on the specified lobby</para>
  230. /// </summary>
  231. public static int GetLobbyDataCount(CSteamID steamIDLobby) {
  232. InteropHelp.TestIfAvailableClient();
  233. return NativeMethods.ISteamMatchmaking_GetLobbyDataCount(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  234. }
  235. /// <summary>
  236. /// <para> returns a lobby metadata key/values pair by index, of range [0, GetLobbyDataCount())</para>
  237. /// </summary>
  238. public static bool GetLobbyDataByIndex(CSteamID steamIDLobby, int iLobbyData, out string pchKey, int cchKeyBufferSize, out string pchValue, int cchValueBufferSize) {
  239. InteropHelp.TestIfAvailableClient();
  240. IntPtr pchKey2 = Marshal.AllocHGlobal(cchKeyBufferSize);
  241. IntPtr pchValue2 = Marshal.AllocHGlobal(cchValueBufferSize);
  242. bool ret = NativeMethods.ISteamMatchmaking_GetLobbyDataByIndex(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, iLobbyData, pchKey2, cchKeyBufferSize, pchValue2, cchValueBufferSize);
  243. pchKey = ret ? InteropHelp.PtrToStringUTF8(pchKey2) : null;
  244. Marshal.FreeHGlobal(pchKey2);
  245. pchValue = ret ? InteropHelp.PtrToStringUTF8(pchValue2) : null;
  246. Marshal.FreeHGlobal(pchValue2);
  247. return ret;
  248. }
  249. /// <summary>
  250. /// <para> removes a metadata key from the lobby</para>
  251. /// </summary>
  252. public static bool DeleteLobbyData(CSteamID steamIDLobby, string pchKey) {
  253. InteropHelp.TestIfAvailableClient();
  254. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey)) {
  255. return NativeMethods.ISteamMatchmaking_DeleteLobbyData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, pchKey2);
  256. }
  257. }
  258. /// <summary>
  259. /// <para> Gets per-user metadata for someone in this lobby</para>
  260. /// </summary>
  261. public static string GetLobbyMemberData(CSteamID steamIDLobby, CSteamID steamIDUser, string pchKey) {
  262. InteropHelp.TestIfAvailableClient();
  263. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey)) {
  264. return InteropHelp.PtrToStringUTF8(NativeMethods.ISteamMatchmaking_GetLobbyMemberData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, steamIDUser, pchKey2));
  265. }
  266. }
  267. /// <summary>
  268. /// <para> Sets per-user metadata (for the local user implicitly)</para>
  269. /// </summary>
  270. public static void SetLobbyMemberData(CSteamID steamIDLobby, string pchKey, string pchValue) {
  271. InteropHelp.TestIfAvailableClient();
  272. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey))
  273. using (var pchValue2 = new InteropHelp.UTF8StringHandle(pchValue)) {
  274. NativeMethods.ISteamMatchmaking_SetLobbyMemberData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, pchKey2, pchValue2);
  275. }
  276. }
  277. /// <summary>
  278. /// <para> Broadcasts a chat message to the all the users in the lobby</para>
  279. /// <para> users in the lobby (including the local user) will receive a LobbyChatMsg_t callback</para>
  280. /// <para> returns true if the message is successfully sent</para>
  281. /// <para> pvMsgBody can be binary or text data, up to 4k</para>
  282. /// <para> if pvMsgBody is text, cubMsgBody should be strlen( text ) + 1, to include the null terminator</para>
  283. /// </summary>
  284. public static bool SendLobbyChatMsg(CSteamID steamIDLobby, byte[] pvMsgBody, int cubMsgBody) {
  285. InteropHelp.TestIfAvailableClient();
  286. return NativeMethods.ISteamMatchmaking_SendLobbyChatMsg(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, pvMsgBody, cubMsgBody);
  287. }
  288. /// <summary>
  289. /// <para> Get a chat message as specified in a LobbyChatMsg_t callback</para>
  290. /// <para> iChatID is the LobbyChatMsg_t::m_iChatID value in the callback</para>
  291. /// <para> *pSteamIDUser is filled in with the CSteamID of the member</para>
  292. /// <para> *pvData is filled in with the message itself</para>
  293. /// <para> return value is the number of bytes written into the buffer</para>
  294. /// </summary>
  295. public static int GetLobbyChatEntry(CSteamID steamIDLobby, int iChatID, out CSteamID pSteamIDUser, byte[] pvData, int cubData, out EChatEntryType peChatEntryType) {
  296. InteropHelp.TestIfAvailableClient();
  297. return NativeMethods.ISteamMatchmaking_GetLobbyChatEntry(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, iChatID, out pSteamIDUser, pvData, cubData, out peChatEntryType);
  298. }
  299. /// <summary>
  300. /// <para> Refreshes metadata for a lobby you're not necessarily in right now</para>
  301. /// <para> you never do this for lobbies you're a member of, only if your</para>
  302. /// <para> this will send down all the metadata associated with a lobby</para>
  303. /// <para> this is an asynchronous call</para>
  304. /// <para> returns false if the local user is not connected to the Steam servers</para>
  305. /// <para> results will be returned by a LobbyDataUpdate_t callback</para>
  306. /// <para> if the specified lobby doesn't exist, LobbyDataUpdate_t::m_bSuccess will be set to false</para>
  307. /// </summary>
  308. public static bool RequestLobbyData(CSteamID steamIDLobby) {
  309. InteropHelp.TestIfAvailableClient();
  310. return NativeMethods.ISteamMatchmaking_RequestLobbyData(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  311. }
  312. /// <summary>
  313. /// <para> sets the game server associated with the lobby</para>
  314. /// <para> usually at this point, the users will join the specified game server</para>
  315. /// <para> either the IP/Port or the steamID of the game server has to be valid, depending on how you want the clients to be able to connect</para>
  316. /// </summary>
  317. public static void SetLobbyGameServer(CSteamID steamIDLobby, uint unGameServerIP, ushort unGameServerPort, CSteamID steamIDGameServer) {
  318. InteropHelp.TestIfAvailableClient();
  319. NativeMethods.ISteamMatchmaking_SetLobbyGameServer(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, unGameServerIP, unGameServerPort, steamIDGameServer);
  320. }
  321. /// <summary>
  322. /// <para> returns the details of a game server set in a lobby - returns false if there is no game server set, or that lobby doesn't exist</para>
  323. /// </summary>
  324. public static bool GetLobbyGameServer(CSteamID steamIDLobby, out uint punGameServerIP, out ushort punGameServerPort, out CSteamID psteamIDGameServer) {
  325. InteropHelp.TestIfAvailableClient();
  326. return NativeMethods.ISteamMatchmaking_GetLobbyGameServer(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, out punGameServerIP, out punGameServerPort, out psteamIDGameServer);
  327. }
  328. /// <summary>
  329. /// <para> set the limit on the # of users who can join the lobby</para>
  330. /// </summary>
  331. public static bool SetLobbyMemberLimit(CSteamID steamIDLobby, int cMaxMembers) {
  332. InteropHelp.TestIfAvailableClient();
  333. return NativeMethods.ISteamMatchmaking_SetLobbyMemberLimit(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, cMaxMembers);
  334. }
  335. /// <summary>
  336. /// <para> returns the current limit on the # of users who can join the lobby; returns 0 if no limit is defined</para>
  337. /// </summary>
  338. public static int GetLobbyMemberLimit(CSteamID steamIDLobby) {
  339. InteropHelp.TestIfAvailableClient();
  340. return NativeMethods.ISteamMatchmaking_GetLobbyMemberLimit(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  341. }
  342. /// <summary>
  343. /// <para> updates which type of lobby it is</para>
  344. /// <para> only lobbies that are k_ELobbyTypePublic or k_ELobbyTypeInvisible, and are set to joinable, will be returned by RequestLobbyList() calls</para>
  345. /// </summary>
  346. public static bool SetLobbyType(CSteamID steamIDLobby, ELobbyType eLobbyType) {
  347. InteropHelp.TestIfAvailableClient();
  348. return NativeMethods.ISteamMatchmaking_SetLobbyType(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, eLobbyType);
  349. }
  350. /// <summary>
  351. /// <para> sets whether or not a lobby is joinable - defaults to true for a new lobby</para>
  352. /// <para> if set to false, no user can join, even if they are a friend or have been invited</para>
  353. /// </summary>
  354. public static bool SetLobbyJoinable(CSteamID steamIDLobby, bool bLobbyJoinable) {
  355. InteropHelp.TestIfAvailableClient();
  356. return NativeMethods.ISteamMatchmaking_SetLobbyJoinable(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, bLobbyJoinable);
  357. }
  358. /// <summary>
  359. /// <para> returns the current lobby owner</para>
  360. /// <para> you must be a member of the lobby to access this</para>
  361. /// <para> there always one lobby owner - if the current owner leaves, another user will become the owner</para>
  362. /// <para> it is possible (bur rare) to join a lobby just as the owner is leaving, thus entering a lobby with self as the owner</para>
  363. /// </summary>
  364. public static CSteamID GetLobbyOwner(CSteamID steamIDLobby) {
  365. InteropHelp.TestIfAvailableClient();
  366. return (CSteamID)NativeMethods.ISteamMatchmaking_GetLobbyOwner(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby);
  367. }
  368. /// <summary>
  369. /// <para> changes who the lobby owner is</para>
  370. /// <para> you must be the lobby owner for this to succeed, and steamIDNewOwner must be in the lobby</para>
  371. /// <para> after completion, the local user will no longer be the owner</para>
  372. /// </summary>
  373. public static bool SetLobbyOwner(CSteamID steamIDLobby, CSteamID steamIDNewOwner) {
  374. InteropHelp.TestIfAvailableClient();
  375. return NativeMethods.ISteamMatchmaking_SetLobbyOwner(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, steamIDNewOwner);
  376. }
  377. /// <summary>
  378. /// <para> link two lobbies for the purposes of checking player compatibility</para>
  379. /// <para> you must be the lobby owner of both lobbies</para>
  380. /// </summary>
  381. public static bool SetLinkedLobby(CSteamID steamIDLobby, CSteamID steamIDLobbyDependent) {
  382. InteropHelp.TestIfAvailableClient();
  383. return NativeMethods.ISteamMatchmaking_SetLinkedLobby(CSteamAPIContext.GetSteamMatchmaking(), steamIDLobby, steamIDLobbyDependent);
  384. }
  385. #if _PS3
  386. /// <summary>
  387. /// <para> changes who the lobby owner is</para>
  388. /// <para> you must be the lobby owner for this to succeed, and steamIDNewOwner must be in the lobby</para>
  389. /// <para> after completion, the local user will no longer be the owner</para>
  390. /// </summary>
  391. public static void CheckForPSNGameBootInvite(uint iGameBootAttributes) {
  392. InteropHelp.TestIfAvailableClient();
  393. NativeMethods.ISteamMatchmaking_CheckForPSNGameBootInvite(CSteamAPIContext.GetSteamMatchmaking(), iGameBootAttributes);
  394. }
  395. #endif
  396. }
  397. public static class SteamMatchmakingServers {
  398. /// <summary>
  399. /// <para> Request a new list of servers of a particular type. These calls each correspond to one of the EMatchMakingType values.</para>
  400. /// <para> Each call allocates a new asynchronous request object.</para>
  401. /// <para> Request object must be released by calling ReleaseRequest( hServerListRequest )</para>
  402. /// </summary>
  403. public static HServerListRequest RequestInternetServerList(AppId_t iApp, MatchMakingKeyValuePair_t[] ppchFilters, uint nFilters, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  404. InteropHelp.TestIfAvailableClient();
  405. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestInternetServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, new MMKVPMarshaller(ppchFilters), nFilters, (IntPtr)pRequestServersResponse);
  406. }
  407. public static HServerListRequest RequestLANServerList(AppId_t iApp, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  408. InteropHelp.TestIfAvailableClient();
  409. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestLANServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, (IntPtr)pRequestServersResponse);
  410. }
  411. public static HServerListRequest RequestFriendsServerList(AppId_t iApp, MatchMakingKeyValuePair_t[] ppchFilters, uint nFilters, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  412. InteropHelp.TestIfAvailableClient();
  413. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestFriendsServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, new MMKVPMarshaller(ppchFilters), nFilters, (IntPtr)pRequestServersResponse);
  414. }
  415. public static HServerListRequest RequestFavoritesServerList(AppId_t iApp, MatchMakingKeyValuePair_t[] ppchFilters, uint nFilters, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  416. InteropHelp.TestIfAvailableClient();
  417. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestFavoritesServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, new MMKVPMarshaller(ppchFilters), nFilters, (IntPtr)pRequestServersResponse);
  418. }
  419. public static HServerListRequest RequestHistoryServerList(AppId_t iApp, MatchMakingKeyValuePair_t[] ppchFilters, uint nFilters, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  420. InteropHelp.TestIfAvailableClient();
  421. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestHistoryServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, new MMKVPMarshaller(ppchFilters), nFilters, (IntPtr)pRequestServersResponse);
  422. }
  423. public static HServerListRequest RequestSpectatorServerList(AppId_t iApp, MatchMakingKeyValuePair_t[] ppchFilters, uint nFilters, ISteamMatchmakingServerListResponse pRequestServersResponse) {
  424. InteropHelp.TestIfAvailableClient();
  425. return (HServerListRequest)NativeMethods.ISteamMatchmakingServers_RequestSpectatorServerList(CSteamAPIContext.GetSteamMatchmakingServers(), iApp, new MMKVPMarshaller(ppchFilters), nFilters, (IntPtr)pRequestServersResponse);
  426. }
  427. /// <summary>
  428. /// <para> Releases the asynchronous request object and cancels any pending query on it if there's a pending query in progress.</para>
  429. /// <para> RefreshComplete callback is not posted when request is released.</para>
  430. /// </summary>
  431. public static void ReleaseRequest(HServerListRequest hServerListRequest) {
  432. InteropHelp.TestIfAvailableClient();
  433. NativeMethods.ISteamMatchmakingServers_ReleaseRequest(CSteamAPIContext.GetSteamMatchmakingServers(), hServerListRequest);
  434. }
  435. /// <summary>
  436. /// <para> the filter operation codes that go in the key part of MatchMakingKeyValuePair_t should be one of these:</para>
  437. /// <para> "map"</para>
  438. /// <para> - Server passes the filter if the server is playing the specified map.</para>
  439. /// <para> "gamedataand"</para>
  440. /// <para> - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) contains all of the</para>
  441. /// <para> specified strings. The value field is a comma-delimited list of strings to match.</para>
  442. /// <para> "gamedataor"</para>
  443. /// <para> - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) contains at least one of the</para>
  444. /// <para> specified strings. The value field is a comma-delimited list of strings to match.</para>
  445. /// <para> "gamedatanor"</para>
  446. /// <para> - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) does not contain any</para>
  447. /// <para> of the specified strings. The value field is a comma-delimited list of strings to check.</para>
  448. /// <para> "gametagsand"</para>
  449. /// <para> - Server passes the filter if the server's game tags (ISteamGameServer::SetGameTags) contains all</para>
  450. /// <para> of the specified strings. The value field is a comma-delimited list of strings to check.</para>
  451. /// <para> "gametagsnor"</para>
  452. /// <para> - Server passes the filter if the server's game tags (ISteamGameServer::SetGameTags) does not contain any</para>
  453. /// <para> of the specified strings. The value field is a comma-delimited list of strings to check.</para>
  454. /// <para> "and" (x1 &amp;&amp; x2 &amp;&amp; ... &amp;&amp; xn)</para>
  455. /// <para> "or" (x1 || x2 || ... || xn)</para>
  456. /// <para> "nand" !(x1 &amp;&amp; x2 &amp;&amp; ... &amp;&amp; xn)</para>
  457. /// <para> "nor" !(x1 || x2 || ... || xn)</para>
  458. /// <para> - Performs Boolean operation on the following filters. The operand to this filter specifies</para>
  459. /// <para> the "size" of the Boolean inputs to the operation, in Key/value pairs. (The keyvalue</para>
  460. /// <para> pairs must immediately follow, i.e. this is a prefix logical operator notation.)</para>
  461. /// <para> In the simplest case where Boolean expressions are not nested, this is simply</para>
  462. /// <para> the number of operands.</para>
  463. /// <para> For example, to match servers on a particular map or with a particular tag, would would</para>
  464. /// <para> use these filters.</para>
  465. /// <para> ( server.map == "cp_dustbowl" || server.gametags.contains("payload") )</para>
  466. /// <para> "or", "2"</para>
  467. /// <para> "map", "cp_dustbowl"</para>
  468. /// <para> "gametagsand", "payload"</para>
  469. /// <para> If logical inputs are nested, then the operand specifies the size of the entire</para>
  470. /// <para> "length" of its operands, not the number of immediate children.</para>
  471. /// <para> ( server.map == "cp_dustbowl" || ( server.gametags.contains("payload") &amp;&amp; !server.gametags.contains("payloadrace") ) )</para>
  472. /// <para> "or", "4"</para>
  473. /// <para> "map", "cp_dustbowl"</para>
  474. /// <para> "and", "2"</para>
  475. /// <para> "gametagsand", "payload"</para>
  476. /// <para> "gametagsnor", "payloadrace"</para>
  477. /// <para> Unary NOT can be achieved using either "nand" or "nor" with a single operand.</para>
  478. /// <para> "addr"</para>
  479. /// <para> - Server passes the filter if the server's query address matches the specified IP or IP:port.</para>
  480. /// <para> "gameaddr"</para>
  481. /// <para> - Server passes the filter if the server's game address matches the specified IP or IP:port.</para>
  482. /// <para> The following filter operations ignore the "value" part of MatchMakingKeyValuePair_t</para>
  483. /// <para> "dedicated"</para>
  484. /// <para> - Server passes the filter if it passed true to SetDedicatedServer.</para>
  485. /// <para> "secure"</para>
  486. /// <para> - Server passes the filter if the server is VAC-enabled.</para>
  487. /// <para> "notfull"</para>
  488. /// <para> - Server passes the filter if the player count is less than the reported max player count.</para>
  489. /// <para> "hasplayers"</para>
  490. /// <para> - Server passes the filter if the player count is greater than zero.</para>
  491. /// <para> "noplayers"</para>
  492. /// <para> - Server passes the filter if it doesn't have any players.</para>
  493. /// <para> "linux"</para>
  494. /// <para> - Server passes the filter if it's a linux server</para>
  495. /// <para> Get details on a given server in the list, you can get the valid range of index</para>
  496. /// <para> values by calling GetServerCount(). You will also receive index values in</para>
  497. /// <para> ISteamMatchmakingServerListResponse::ServerResponded() callbacks</para>
  498. /// </summary>
  499. public static gameserveritem_t GetServerDetails(HServerListRequest hRequest, int iServer) {
  500. InteropHelp.TestIfAvailableClient();
  501. return (gameserveritem_t)Marshal.PtrToStructure(NativeMethods.ISteamMatchmakingServers_GetServerDetails(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest, iServer), typeof(gameserveritem_t));
  502. }
  503. /// <summary>
  504. /// <para> Cancel an request which is operation on the given list type. You should call this to cancel</para>
  505. /// <para> any in-progress requests before destructing a callback object that may have been passed</para>
  506. /// <para> to one of the above list request calls. Not doing so may result in a crash when a callback</para>
  507. /// <para> occurs on the destructed object.</para>
  508. /// <para> Canceling a query does not release the allocated request handle.</para>
  509. /// <para> The request handle must be released using ReleaseRequest( hRequest )</para>
  510. /// </summary>
  511. public static void CancelQuery(HServerListRequest hRequest) {
  512. InteropHelp.TestIfAvailableClient();
  513. NativeMethods.ISteamMatchmakingServers_CancelQuery(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest);
  514. }
  515. /// <summary>
  516. /// <para> Ping every server in your list again but don't update the list of servers</para>
  517. /// <para> Query callback installed when the server list was requested will be used</para>
  518. /// <para> again to post notifications and RefreshComplete, so the callback must remain</para>
  519. /// <para> valid until another RefreshComplete is called on it or the request</para>
  520. /// <para> is released with ReleaseRequest( hRequest )</para>
  521. /// </summary>
  522. public static void RefreshQuery(HServerListRequest hRequest) {
  523. InteropHelp.TestIfAvailableClient();
  524. NativeMethods.ISteamMatchmakingServers_RefreshQuery(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest);
  525. }
  526. /// <summary>
  527. /// <para> Returns true if the list is currently refreshing its server list</para>
  528. /// </summary>
  529. public static bool IsRefreshing(HServerListRequest hRequest) {
  530. InteropHelp.TestIfAvailableClient();
  531. return NativeMethods.ISteamMatchmakingServers_IsRefreshing(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest);
  532. }
  533. /// <summary>
  534. /// <para> How many servers in the given list, GetServerDetails above takes 0... GetServerCount() - 1</para>
  535. /// </summary>
  536. public static int GetServerCount(HServerListRequest hRequest) {
  537. InteropHelp.TestIfAvailableClient();
  538. return NativeMethods.ISteamMatchmakingServers_GetServerCount(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest);
  539. }
  540. /// <summary>
  541. /// <para> Refresh a single server inside of a query (rather than all the servers )</para>
  542. /// </summary>
  543. public static void RefreshServer(HServerListRequest hRequest, int iServer) {
  544. InteropHelp.TestIfAvailableClient();
  545. NativeMethods.ISteamMatchmakingServers_RefreshServer(CSteamAPIContext.GetSteamMatchmakingServers(), hRequest, iServer);
  546. }
  547. /// <summary>
  548. /// <para>-----------------------------------------------------------------------------</para>
  549. /// <para> Queries to individual servers directly via IP/Port</para>
  550. /// <para>-----------------------------------------------------------------------------</para>
  551. /// <para> Request updated ping time and other details from a single server</para>
  552. /// </summary>
  553. public static HServerQuery PingServer(uint unIP, ushort usPort, ISteamMatchmakingPingResponse pRequestServersResponse) {
  554. InteropHelp.TestIfAvailableClient();
  555. return (HServerQuery)NativeMethods.ISteamMatchmakingServers_PingServer(CSteamAPIContext.GetSteamMatchmakingServers(), unIP, usPort, (IntPtr)pRequestServersResponse);
  556. }
  557. /// <summary>
  558. /// <para> Request the list of players currently playing on a server</para>
  559. /// </summary>
  560. public static HServerQuery PlayerDetails(uint unIP, ushort usPort, ISteamMatchmakingPlayersResponse pRequestServersResponse) {
  561. InteropHelp.TestIfAvailableClient();
  562. return (HServerQuery)NativeMethods.ISteamMatchmakingServers_PlayerDetails(CSteamAPIContext.GetSteamMatchmakingServers(), unIP, usPort, (IntPtr)pRequestServersResponse);
  563. }
  564. /// <summary>
  565. /// <para> Request the list of rules that the server is running (See ISteamGameServer::SetKeyValue() to set the rules server side)</para>
  566. /// </summary>
  567. public static HServerQuery ServerRules(uint unIP, ushort usPort, ISteamMatchmakingRulesResponse pRequestServersResponse) {
  568. InteropHelp.TestIfAvailableClient();
  569. return (HServerQuery)NativeMethods.ISteamMatchmakingServers_ServerRules(CSteamAPIContext.GetSteamMatchmakingServers(), unIP, usPort, (IntPtr)pRequestServersResponse);
  570. }
  571. /// <summary>
  572. /// <para> Cancel an outstanding Ping/Players/Rules query from above. You should call this to cancel</para>
  573. /// <para> any in-progress requests before destructing a callback object that may have been passed</para>
  574. /// <para> to one of the above calls to avoid crashing when callbacks occur.</para>
  575. /// </summary>
  576. public static void CancelServerQuery(HServerQuery hServerQuery) {
  577. InteropHelp.TestIfAvailableClient();
  578. NativeMethods.ISteamMatchmakingServers_CancelServerQuery(CSteamAPIContext.GetSteamMatchmakingServers(), hServerQuery);
  579. }
  580. }
  581. public static class SteamGameSearch {
  582. /// <summary>
  583. /// <para> =============================================================================================</para>
  584. /// <para> Game Player APIs</para>
  585. /// <para> a keyname and a list of comma separated values: one of which is must be found in order for the match to qualify</para>
  586. /// <para> fails if a search is currently in progress</para>
  587. /// </summary>
  588. public static EGameSearchErrorCode_t AddGameSearchParams(string pchKeyToFind, string pchValuesToFind) {
  589. InteropHelp.TestIfAvailableClient();
  590. using (var pchKeyToFind2 = new InteropHelp.UTF8StringHandle(pchKeyToFind))
  591. using (var pchValuesToFind2 = new InteropHelp.UTF8StringHandle(pchValuesToFind)) {
  592. return NativeMethods.ISteamGameSearch_AddGameSearchParams(CSteamAPIContext.GetSteamGameSearch(), pchKeyToFind2, pchValuesToFind2);
  593. }
  594. }
  595. /// <summary>
  596. /// <para> all players in lobby enter the queue and await a SearchForGameNotificationCallback_t callback. fails if another search is currently in progress</para>
  597. /// <para> if not the owner of the lobby or search already in progress this call fails</para>
  598. /// <para> periodic callbacks will be sent as queue time estimates change</para>
  599. /// </summary>
  600. public static EGameSearchErrorCode_t SearchForGameWithLobby(CSteamID steamIDLobby, int nPlayerMin, int nPlayerMax) {
  601. InteropHelp.TestIfAvailableClient();
  602. return NativeMethods.ISteamGameSearch_SearchForGameWithLobby(CSteamAPIContext.GetSteamGameSearch(), steamIDLobby, nPlayerMin, nPlayerMax);
  603. }
  604. /// <summary>
  605. /// <para> user enter the queue and await a SearchForGameNotificationCallback_t callback. fails if another search is currently in progress</para>
  606. /// <para> periodic callbacks will be sent as queue time estimates change</para>
  607. /// </summary>
  608. public static EGameSearchErrorCode_t SearchForGameSolo(int nPlayerMin, int nPlayerMax) {
  609. InteropHelp.TestIfAvailableClient();
  610. return NativeMethods.ISteamGameSearch_SearchForGameSolo(CSteamAPIContext.GetSteamGameSearch(), nPlayerMin, nPlayerMax);
  611. }
  612. /// <summary>
  613. /// <para> after receiving SearchForGameResultCallback_t, accept or decline the game</para>
  614. /// <para> multiple SearchForGameResultCallback_t will follow as players accept game until the host starts or cancels the game</para>
  615. /// </summary>
  616. public static EGameSearchErrorCode_t AcceptGame() {
  617. InteropHelp.TestIfAvailableClient();
  618. return NativeMethods.ISteamGameSearch_AcceptGame(CSteamAPIContext.GetSteamGameSearch());
  619. }
  620. public static EGameSearchErrorCode_t DeclineGame() {
  621. InteropHelp.TestIfAvailableClient();
  622. return NativeMethods.ISteamGameSearch_DeclineGame(CSteamAPIContext.GetSteamGameSearch());
  623. }
  624. /// <summary>
  625. /// <para> after receiving GameStartedByHostCallback_t get connection details to server</para>
  626. /// </summary>
  627. public static EGameSearchErrorCode_t RetrieveConnectionDetails(CSteamID steamIDHost, out string pchConnectionDetails, int cubConnectionDetails) {
  628. InteropHelp.TestIfAvailableClient();
  629. IntPtr pchConnectionDetails2 = Marshal.AllocHGlobal(cubConnectionDetails);
  630. EGameSearchErrorCode_t ret = NativeMethods.ISteamGameSearch_RetrieveConnectionDetails(CSteamAPIContext.GetSteamGameSearch(), steamIDHost, pchConnectionDetails2, cubConnectionDetails);
  631. pchConnectionDetails = ret != 0 ? InteropHelp.PtrToStringUTF8(pchConnectionDetails2) : null;
  632. Marshal.FreeHGlobal(pchConnectionDetails2);
  633. return ret;
  634. }
  635. /// <summary>
  636. /// <para> leaves queue if still waiting</para>
  637. /// </summary>
  638. public static EGameSearchErrorCode_t EndGameSearch() {
  639. InteropHelp.TestIfAvailableClient();
  640. return NativeMethods.ISteamGameSearch_EndGameSearch(CSteamAPIContext.GetSteamGameSearch());
  641. }
  642. /// <summary>
  643. /// <para> =============================================================================================</para>
  644. /// <para> Game Host APIs</para>
  645. /// <para> a keyname and a list of comma separated values: all the values you allow</para>
  646. /// </summary>
  647. public static EGameSearchErrorCode_t SetGameHostParams(string pchKey, string pchValue) {
  648. InteropHelp.TestIfAvailableClient();
  649. using (var pchKey2 = new InteropHelp.UTF8StringHandle(pchKey))
  650. using (var pchValue2 = new InteropHelp.UTF8StringHandle(pchValue)) {
  651. return NativeMethods.ISteamGameSearch_SetGameHostParams(CSteamAPIContext.GetSteamGameSearch(), pchKey2, pchValue2);
  652. }
  653. }
  654. /// <summary>
  655. /// <para> set connection details for players once game is found so they can connect to this server</para>
  656. /// </summary>
  657. public static EGameSearchErrorCode_t SetConnectionDetails(string pchConnectionDetails, int cubConnectionDetails) {
  658. InteropHelp.TestIfAvailableClient();
  659. using (var pchConnectionDetails2 = new InteropHelp.UTF8StringHandle(pchConnectionDetails)) {
  660. return NativeMethods.ISteamGameSearch_SetConnectionDetails(CSteamAPIContext.GetSteamGameSearch(), pchConnectionDetails2, cubConnectionDetails);
  661. }
  662. }
  663. /// <summary>
  664. /// <para> mark server as available for more players with nPlayerMin,nPlayerMax desired</para>
  665. /// <para> accept no lobbies with playercount greater than nMaxTeamSize</para>
  666. /// <para> the set of lobbies returned must be partitionable into teams of no more than nMaxTeamSize</para>
  667. /// <para> RequestPlayersForGameNotificationCallback_t callback will be sent when the search has started</para>
  668. /// <para> multple RequestPlayersForGameResultCallback_t callbacks will follow when players are found</para>
  669. /// </summary>
  670. public static EGameSearchErrorCode_t RequestPlayersForGame(int nPlayerMin, int nPlayerMax, int nMaxTeamSize) {
  671. InteropHelp.TestIfAvailableClient();
  672. return NativeMethods.ISteamGameSearch_RequestPlayersForGame(CSteamAPIContext.GetSteamGameSearch(), nPlayerMin, nPlayerMax, nMaxTeamSize);
  673. }
  674. /// <summary>
  675. /// <para> accept the player list and release connection details to players</para>
  676. /// <para> players will only be given connection details and host steamid when this is called</para>
  677. /// <para> ( allows host to accept after all players confirm, some confirm, or none confirm. decision is entirely up to the host )</para>
  678. /// </summary>
  679. public static EGameSearchErrorCode_t HostConfirmGameStart(ulong ullUniqueGameID) {
  680. InteropHelp.TestIfAvailableClient();
  681. return NativeMethods.ISteamGameSearch_HostConfirmGameStart(CSteamAPIContext.GetSteamGameSearch(), ullUniqueGameID);
  682. }
  683. /// <summary>
  684. /// <para> cancel request and leave the pool of game hosts looking for players</para>
  685. /// <para> if a set of players has already been sent to host, all players will receive SearchForGameHostFailedToConfirm_t</para>
  686. /// </summary>
  687. public static EGameSearchErrorCode_t CancelRequestPlayersForGame() {
  688. InteropHelp.TestIfAvailableClient();
  689. return NativeMethods.ISteamGameSearch_CancelRequestPlayersForGame(CSteamAPIContext.GetSteamGameSearch());
  690. }
  691. /// <summary>
  692. /// <para> submit a result for one player. does not end the game. ullUniqueGameID continues to describe this game</para>
  693. /// </summary>
  694. public static EGameSearchErrorCode_t SubmitPlayerResult(ulong ullUniqueGameID, CSteamID steamIDPlayer, EPlayerResult_t EPlayerResult) {
  695. InteropHelp.TestIfAvailableClient();
  696. return NativeMethods.ISteamGameSearch_SubmitPlayerResult(CSteamAPIContext.GetSteamGameSearch(), ullUniqueGameID, steamIDPlayer, EPlayerResult);
  697. }
  698. /// <summary>
  699. /// <para> ends the game. no further SubmitPlayerResults for ullUniqueGameID will be accepted</para>
  700. /// <para> any future requests will provide a new ullUniqueGameID</para>
  701. /// </summary>
  702. public static EGameSearchErrorCode_t EndGame(ulong ullUniqueGameID) {
  703. InteropHelp.TestIfAvailableClient();
  704. return NativeMethods.ISteamGameSearch_EndGame(CSteamAPIContext.GetSteamGameSearch(), ullUniqueGameID);
  705. }
  706. }
  707. public static class SteamParties {
  708. /// <summary>
  709. /// <para> =============================================================================================</para>
  710. /// <para> Party Client APIs</para>
  711. /// <para> Enumerate any active beacons for parties you may wish to join</para>
  712. /// </summary>
  713. public static uint GetNumActiveBeacons() {
  714. InteropHelp.TestIfAvailableClient();
  715. return NativeMethods.ISteamParties_GetNumActiveBeacons(CSteamAPIContext.GetSteamParties());
  716. }
  717. public static PartyBeaconID_t GetBeaconByIndex(uint unIndex) {
  718. InteropHelp.TestIfAvailableClient();
  719. return (PartyBeaconID_t)NativeMethods.ISteamParties_GetBeaconByIndex(CSteamAPIContext.GetSteamParties(), unIndex);
  720. }
  721. public static bool GetBeaconDetails(PartyBeaconID_t ulBeaconID, out CSteamID pSteamIDBeaconOwner, out SteamPartyBeaconLocation_t pLocation, out string pchMetadata, int cchMetadata) {
  722. InteropHelp.TestIfAvailableClient();
  723. IntPtr pchMetadata2 = Marshal.AllocHGlobal(cchMetadata);
  724. bool ret = NativeMethods.ISteamParties_GetBeaconDetails(CSteamAPIContext.GetSteamParties(), ulBeaconID, out pSteamIDBeaconOwner, out pLocation, pchMetadata2, cchMetadata);
  725. pchMetadata = ret ? InteropHelp.PtrToStringUTF8(pchMetadata2) : null;
  726. Marshal.FreeHGlobal(pchMetadata2);
  727. return ret;
  728. }
  729. /// <summary>
  730. /// <para> Join an open party. Steam will reserve one beacon slot for your SteamID,</para>
  731. /// <para> and return the necessary JoinGame string for you to use to connect</para>
  732. /// </summary>
  733. public static SteamAPICall_t JoinParty(PartyBeaconID_t ulBeaconID) {
  734. InteropHelp.TestIfAvailableClient();
  735. return (SteamAPICall_t)NativeMethods.ISteamParties_JoinParty(CSteamAPIContext.GetSteamParties(), ulBeaconID);
  736. }
  737. /// <summary>
  738. /// <para> =============================================================================================</para>
  739. /// <para> Party Host APIs</para>
  740. /// <para> Get a list of possible beacon locations</para>
  741. /// </summary>
  742. public static bool GetNumAvailableBeaconLocations(out uint puNumLocations) {
  743. InteropHelp.TestIfAvailableClient();
  744. return NativeMethods.ISteamParties_GetNumAvailableBeaconLocations(CSteamAPIContext.GetSteamParties(), out puNumLocations);
  745. }
  746. public static bool GetAvailableBeaconLocations(SteamPartyBeaconLocation_t[] pLocationList, uint uMaxNumLocations) {
  747. InteropHelp.TestIfAvailableClient();
  748. return NativeMethods.ISteamParties_GetAvailableBeaconLocations(CSteamAPIContext.GetSteamParties(), pLocationList, uMaxNumLocations);
  749. }
  750. /// <summary>
  751. /// <para> Create a new party beacon and activate it in the selected location.</para>
  752. /// <para> unOpenSlots is the maximum number of users that Steam will send to you.</para>
  753. /// <para> When people begin responding to your beacon, Steam will send you</para>
  754. /// <para> PartyReservationCallback_t callbacks to let you know who is on the way.</para>
  755. /// </summary>
  756. public static SteamAPICall_t CreateBeacon(uint unOpenSlots, ref SteamPartyBeaconLocation_t pBeaconLocation, string pchConnectString, string pchMetadata) {
  757. InteropHelp.TestIfAvailableClient();
  758. using (var pchConnectString2 = new InteropHelp.UTF8StringHandle(pchConnectString))
  759. using (var pchMetadata2 = new InteropHelp.UTF8StringHandle(pchMetadata)) {
  760. return (SteamAPICall_t)NativeMethods.ISteamParties_CreateBeacon(CSteamAPIContext.GetSteamParties(), unOpenSlots, ref pBeaconLocation, pchConnectString2, pchMetadata2);
  761. }
  762. }
  763. /// <summary>
  764. /// <para> Call this function when a user that had a reservation (see callback below)</para>
  765. /// <para> has successfully joined your party.</para>
  766. /// <para> Steam will manage the remaining open slots automatically.</para>
  767. /// </summary>
  768. public static void OnReservationCompleted(PartyBeaconID_t ulBeacon, CSteamID steamIDUser) {
  769. InteropHelp.TestIfAvailableClient();
  770. NativeMethods.ISteamParties_OnReservationCompleted(CSteamAPIContext.GetSteamParties(), ulBeacon, steamIDUser);
  771. }
  772. /// <summary>
  773. /// <para> To cancel a reservation (due to timeout or user input), call this.</para>
  774. /// <para> Steam will open a new reservation slot.</para>
  775. /// <para> Note: The user may already be in-flight to your game, so it's possible they will still connect and try to join your party.</para>
  776. /// </summary>
  777. public static void CancelReservation(PartyBeaconID_t ulBeacon, CSteamID steamIDUser) {
  778. InteropHelp.TestIfAvailableClient();
  779. NativeMethods.ISteamParties_CancelReservation(CSteamAPIContext.GetSteamParties(), ulBeacon, steamIDUser);
  780. }
  781. /// <summary>
  782. /// <para> Change the number of open beacon reservation slots.</para>
  783. /// <para> Call this if, for example, someone without a reservation joins your party (eg a friend, or via your own matchmaking system).</para>
  784. /// </summary>
  785. public static SteamAPICall_t ChangeNumOpenSlots(PartyBeaconID_t ulBeacon, uint unOpenSlots) {
  786. InteropHelp.TestIfAvailableClient();
  787. return (SteamAPICall_t)NativeMethods.ISteamParties_ChangeNumOpenSlots(CSteamAPIContext.GetSteamParties(), ulBeacon, unOpenSlots);
  788. }
  789. /// <summary>
  790. /// <para> Turn off the beacon.</para>
  791. /// </summary>
  792. public static bool DestroyBeacon(PartyBeaconID_t ulBeacon) {
  793. InteropHelp.TestIfAvailableClient();
  794. return NativeMethods.ISteamParties_DestroyBeacon(CSteamAPIContext.GetSteamParties(), ulBeacon);
  795. }
  796. /// <summary>
  797. /// <para> Utils</para>
  798. /// </summary>
  799. public static bool GetBeaconLocationData(SteamPartyBeaconLocation_t BeaconLocation, ESteamPartyBeaconLocationData eData, out string pchDataStringOut, int cchDataStringOut) {
  800. InteropHelp.TestIfAvailableClient();
  801. IntPtr pchDataStringOut2 = Marshal.AllocHGlobal(cchDataStringOut);
  802. bool ret = NativeMethods.ISteamParties_GetBeaconLocationData(CSteamAPIContext.GetSteamParties(), BeaconLocation, eData, pchDataStringOut2, cchDataStringOut);
  803. pchDataStringOut = ret ? InteropHelp.PtrToStringUTF8(pchDataStringOut2) : null;
  804. Marshal.FreeHGlobal(pchDataStringOut2);
  805. return ret;
  806. }
  807. }
  808. }
  809. #endif // !DISABLESTEAMWORKS