Use universe info for game presence

This commit is contained in:
pizzaboxer 2023-03-12 17:18:05 +00:00
parent 961d21cff9
commit 75290fd9ee
10 changed files with 278 additions and 43 deletions

View File

@ -284,7 +284,7 @@ namespace Bloxstrap
var exception = t.Exception.InnerExceptions.Count >= 1 ? t.Exception.InnerExceptions[0] : t.Exception;
dialog?.ShowError($"{exception.GetType()}: {exception.Message}");
#endif
}, TaskScheduler.FromCurrentSynchronizationContext());
});
dialog?.ShowBootstrapper();
bootstrapperTask.Wait();

View File

@ -49,7 +49,9 @@ namespace Bloxstrap.Helpers
{
try
{
App.Logger.WriteLine($"[Utilities::GetJson<{typeof(T).Name}>] Getting JSON from {url}!");
string json = await App.HttpClient.GetStringAsync(url);
App.Logger.WriteLine($"[Utilities::GetJson<{typeof(T).Name}>] Got JSON: {json}");
return JsonSerializer.Deserialize<T>(json);
}
catch (Exception ex)

View File

@ -5,9 +5,9 @@ using System.Linq;
using System.Text.RegularExpressions;
using System.Threading;
using System.Threading.Tasks;
using Bloxstrap.Helpers;
using Bloxstrap.Models;
using Bloxstrap.Helpers;
using Bloxstrap.Models.RobloxApi;
using DiscordRPC;
@ -205,17 +205,40 @@ namespace Bloxstrap.Integrations
return true;
}
string placeThumbnail = "roblox";
string icon = "roblox";
var placeInfo = await Utilities.GetJson<RobloxAsset>($"https://economy.roblox.com/v2/assets/{_activityPlaceId}/details");
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Fetching data for Place ID {_activityPlaceId}");
if (placeInfo is null || placeInfo.Creator is null)
var universeIdResponse = await Utilities.GetJson<UniverseIdResponse>($"https://apis.roblox.com/universes/v1/places/{_activityPlaceId}/universe");
if (universeIdResponse is null)
{
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Could not get Universe ID!");
return false;
}
var thumbnailInfo = await Utilities.GetJson<RobloxThumbnails>($"https://thumbnails.roblox.com/v1/places/gameicons?placeIds={_activityPlaceId}&returnPolicy=PlaceHolder&size=512x512&format=Png&isCircular=false");
long universeId = universeIdResponse.UniverseId;
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Got Universe ID as {universeId}");
if (thumbnailInfo is not null)
placeThumbnail = thumbnailInfo.Data![0].ImageUrl!;
var gameDetailResponse = await Utilities.GetJson<ApiArrayResponse<GameDetailResponse>>($"https://games.roblox.com/v1/games?universeIds={universeId}");
if (gameDetailResponse is null || !gameDetailResponse.Data.Any())
{
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Could not get Universe info!");
return false;
}
GameDetailResponse universeDetails = gameDetailResponse.Data.ToArray()[0];
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Got Universe details");
var universeThumbnailResponse = await Utilities.GetJson<ApiArrayResponse<ThumbnailResponse>>($"https://thumbnails.roblox.com/v1/games/icons?universeIds={universeId}&returnPolicy=PlaceHolder&size=512x512&format=Png&isCircular=false");
if (universeThumbnailResponse is null || !universeThumbnailResponse.Data.Any())
{
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Could not get Universe thumbnail info!");
}
else
{
icon = universeThumbnailResponse.Data.ToArray()[0].ImageUrl;
App.Logger.WriteLine($"[DiscordRichPresence::SetPresence] Got Universe thumbnail as {icon}");
}
List<Button> buttons = new()
{
@ -237,14 +260,14 @@ namespace Bloxstrap.Integrations
_rpcClient.SetPresence(new RichPresence
{
Details = placeInfo.Name,
State = $"by {placeInfo.Creator.Name}",
Details = universeDetails.Name,
State = $"by {universeDetails.Creator.Name}",
Timestamps = new Timestamps { Start = DateTime.UtcNow },
Buttons = buttons.ToArray(),
Assets = new Assets
{
LargeImageKey = placeThumbnail,
LargeImageText = placeInfo.Name,
LargeImageKey = icon,
LargeImageText = universeDetails.Name,
SmallImageKey = "roblox",
SmallImageText = "Roblox"
}

View File

@ -0,0 +1,14 @@
using System.Collections.Generic;
using System.Text.Json.Serialization;
namespace Bloxstrap.Models.RobloxApi
{
/// <summary>
/// Roblox.Web.WebAPI.Models.ApiArrayResponse
/// </summary>
public class ApiArrayResponse<T>
{
[JsonPropertyName("data")]
public IEnumerable<T> Data { get; set; } = null!;
}
}

View File

@ -0,0 +1,41 @@
using System.Text.Json.Serialization;
namespace Bloxstrap.Models.RobloxApi
{
/// <summary>
/// Roblox.Games.Api.Models.Response.GameCreator
/// Response model for getting the game creator
/// </summary>
public class GameCreator
{
/// <summary>
/// The game creator id
/// </summary>
[JsonPropertyName("id")]
public long Id { get; set; }
/// <summary>
/// The game creator name
/// </summary>
[JsonPropertyName("name")]
public string Name { get; set; } = null!;
/// <summary>
/// The game creator type
/// </summary>
[JsonPropertyName("type")]
public string Type { get; set; } = null!;
/// <summary>
/// The game creator account is Luobu Real Name Verified
/// </summary>
[JsonPropertyName("isRNVAccount")]
public bool IsRNVAccount { get; set; }
/// <summary>
/// Builder verified badge status.
/// </summary>
[JsonPropertyName("hasVerifiedBadge")]
public bool HasVerifiedBadge { get; set; }
}
}

View File

@ -0,0 +1,155 @@
using System;
using System.Collections.Generic;
using System.Text.Json.Serialization;
namespace Bloxstrap.Models.RobloxApi
{
/// <summary>
/// Roblox.Games.Api.Models.Response.GameDetailResponse
/// Response model for getting the game detail
/// </summary>
public class GameDetailResponse
{
/// <summary>
/// The game universe id
/// </summary>
[JsonPropertyName("id")]
public long Id { get; set; }
/// <summary>
/// The game root place id
/// </summary>
[JsonPropertyName("rootPlaceId")]
public long RootPlaceId { get; set; }
/// <summary>
/// The game name
/// </summary>
[JsonPropertyName("name")]
public string Name { get; set; } = null!;
/// <summary>
/// The game description
/// </summary>
[JsonPropertyName("description")]
public string Description { get; set; } = null!;
/// <summary>
/// The game name in the source language, if different from the returned name.
/// </summary>
[JsonPropertyName("sourceName")]
public string SourceName { get; set; } = null!;
/// <summary>
/// The game description in the source language, if different from the returned description.
/// </summary>
[JsonPropertyName("sourceDescription")]
public string SourceDescription { get; set; } = null!;
[JsonPropertyName("creator")]
public GameCreator Creator { get; set; } = null!;
/// <summary>
/// The game paid access price
/// </summary>
[JsonPropertyName("price")]
public long? Price { get; set; }
/// <summary>
/// The game allowed gear genres
/// </summary>
[JsonPropertyName("allowedGearGenres")]
public IEnumerable<string> AllowedGearGenres { get; set; } = null!;
/// <summary>
/// The game allowed gear categoris
/// </summary>
[JsonPropertyName("allowedGearCategories")]
public IEnumerable<string> AllowedGearCategories { get; set; } = null!;
/// <summary>
/// The game allows place to be copied
/// </summary>
[JsonPropertyName("isGenreEnforced")]
public bool IsGenreEnforced { get; set; }
/// <summary>
/// The game allows place to be copied
/// </summary>
[JsonPropertyName("copyingAllowed")]
public bool CopyingAllowed { get; set; }
/// <summary>
/// Current player count of the game
/// </summary>
[JsonPropertyName("playing")]
public long Playing { get; set; }
/// <summary>
/// The total visits to the game
/// </summary>
[JsonPropertyName("visits")]
public long Visits { get; set; }
/// <summary>
/// The game max players
/// </summary>
[JsonPropertyName("maxPlayers")]
public int MaxPlayers { get; set; }
/// <summary>
/// The game created time
/// </summary>
[JsonPropertyName("created")]
public DateTime Created { get; set; }
/// <summary>
/// The game updated time
/// </summary>
[JsonPropertyName("updated")]
public DateTime Updated { get; set; }
/// <summary>
/// The setting of IsStudioAccessToApisAllowed of the universe
/// </summary>
[JsonPropertyName("studioAccessToApisAllowed")]
public bool StudioAccessToApisAllowed { get; set; }
/// <summary>
/// Gets or sets the flag to indicate whether the create vip servers button should be allowed in game details page
/// </summary>
[JsonPropertyName("createVipServersAllowed")]
public bool CreateVipServersAllowed { get; set; }
/// <summary>
/// Avatar type. Possible values are MorphToR6, MorphToR15, and PlayerChoice ['MorphToR6' = 1, 'PlayerChoice' = 2, 'MorphToR15' = 3]
/// </summary>
[JsonPropertyName("universeAvatarType")]
public string UniverseAvatarType { get; set; } = null!;
/// <summary>
/// The game genre display name
/// </summary>
[JsonPropertyName("genre")]
public string Genre { get; set; } = null!;
/// <summary>
/// Is this game all genre.
/// </summary>
[JsonPropertyName("isAllGenre")]
public bool IsAllGenre { get; set; }
/// <summary>
/// Is this game favorited by user.
/// </summary>
[JsonPropertyName("isFavoritedByUser")]
public bool IsFavoritedByUser { get; set; }
/// <summary>
/// Game number of favorites.
/// </summary>
[JsonPropertyName("favoritedCount")]
public int FavoritedCount { get; set; }
}
}

View File

@ -0,0 +1,19 @@
using System.Text.Json.Serialization;
namespace Bloxstrap.Models.RobloxApi
{
/// <summary>
/// Roblox.Web.Responses.Thumbnails.ThumbnailResponse
/// </summary>
public class ThumbnailResponse
{
[JsonPropertyName("targetId")]
public long TargetId { get; set; }
[JsonPropertyName("state")]
public string State { get; set; } = null!;
[JsonPropertyName("imageUrl")]
public string ImageUrl { get; set; } = null!;
}
}

View File

@ -0,0 +1,11 @@
using System.Text.Json.Serialization;
namespace Bloxstrap.Models.RobloxApi
{
// lmao its just one property
internal class UniverseIdResponse
{
[JsonPropertyName("universeId")]
public long UniverseId { get; set; }
}
}

View File

@ -1,13 +0,0 @@
namespace Bloxstrap.Models
{
public class RobloxAsset
{
public string? Name { get; set; }
public RobloxAssetCreator? Creator { get; set; }
}
public class RobloxAssetCreator
{
public string? Name { get; set; }
}
}

View File

@ -1,17 +0,0 @@
using System.Collections.Generic;
using System.Text.Json.Serialization;
namespace Bloxstrap.Models
{
public class RobloxThumbnails
{
[JsonPropertyName("data")]
public List<RobloxThumbnail>? Data { get; set; }
}
public class RobloxThumbnail
{
[JsonPropertyName("imageUrl")]
public string? ImageUrl { get; set; }
}
}