mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
working discord presence
This commit is contained in:
parent
60500d9235
commit
1e40bd09ba
104
voxygen/src/discord.rs
Normal file
104
voxygen/src/discord.rs
Normal file
@ -0,0 +1,104 @@
|
||||
use discord_game_sdk::{Activity, Discord};
|
||||
use std::ffi::CString;
|
||||
use std::sync::mpsc::Sender;
|
||||
use std::sync::{mpsc, Mutex, MutexGuard};
|
||||
use std::thread;
|
||||
use std::thread::JoinHandle;
|
||||
|
||||
use crate::DEFAULT_PUBLIC_SERVER;
|
||||
use chrono::Utc;
|
||||
|
||||
const DISCORD_APPLICATION_ID: i64 = 583662036194689035;
|
||||
|
||||
/// Represents an update of the game which should be reflected in Discord
|
||||
pub enum DiscordUpdate {
|
||||
Details(String),
|
||||
State(String),
|
||||
SmallImg(String),
|
||||
SmallImgDesc(String),
|
||||
LargeImg(String),
|
||||
LargeImgDesc(String),
|
||||
Shutdown,
|
||||
}
|
||||
|
||||
pub struct DiscordState {
|
||||
pub tx: Sender<DiscordUpdate>,
|
||||
pub thread: Option<JoinHandle<()>>,
|
||||
}
|
||||
|
||||
pub fn run() -> Mutex<DiscordState> {
|
||||
let (tx, rx) = mpsc::channel();
|
||||
|
||||
Mutex::new(DiscordState {
|
||||
tx,
|
||||
thread: Some(thread::spawn(move || {
|
||||
let mut discord =
|
||||
Discord::new(DISCORD_APPLICATION_ID).expect("failed to initiate discord_game_sdk");
|
||||
|
||||
//Set initial Status
|
||||
let mut current_activity = Activity::empty();
|
||||
current_activity.with_details(CString::new("Menu").expect("failed to create CString"));
|
||||
current_activity.with_state(CString::new("Idling").expect("failed to create CString"));
|
||||
current_activity.with_small_image_key(
|
||||
CString::new("veloren_logo_squareicon_2000").expect("failed to create CString"),
|
||||
);
|
||||
current_activity.with_small_image_tooltip(
|
||||
CString::new("Veloren").expect("failed to create CString"),
|
||||
);
|
||||
current_activity
|
||||
.with_large_image_key(CString::new("bg_main").expect("failed to create CString"));
|
||||
current_activity.with_large_image_tooltip(
|
||||
CString::new("veloren.net").expect("failed to create CString"),
|
||||
);
|
||||
|
||||
current_activity.with_start_time(Utc::now());
|
||||
|
||||
discord.update_activity(¤t_activity, |_, _| {});
|
||||
|
||||
'outer: loop {
|
||||
discord.empty_event_receivers();
|
||||
discord.run_callbacks();
|
||||
|
||||
let msg = rx.try_recv();
|
||||
match msg {
|
||||
Ok(update) => {
|
||||
match update {
|
||||
DiscordUpdate::Details(x) => current_activity
|
||||
.with_details(CString::new(x).expect("failed to create CString")),
|
||||
DiscordUpdate::State(x) => current_activity
|
||||
.with_state(CString::new(x).expect("failed to create CString")),
|
||||
DiscordUpdate::SmallImg(x) => current_activity.with_small_image_key(
|
||||
CString::new(x).expect("failed to create CString"),
|
||||
),
|
||||
DiscordUpdate::SmallImgDesc(x) => current_activity
|
||||
.with_small_image_tooltip(
|
||||
CString::new(x).expect("failed to create CString"),
|
||||
),
|
||||
DiscordUpdate::LargeImg(x) => current_activity.with_large_image_key(
|
||||
CString::new(x).expect("failed to create CString"),
|
||||
),
|
||||
DiscordUpdate::LargeImgDesc(x) => current_activity
|
||||
.with_large_image_tooltip(
|
||||
CString::new(x).expect("failed to create CString"),
|
||||
),
|
||||
DiscordUpdate::Shutdown => break 'outer,
|
||||
};
|
||||
discord.update_activity(¤t_activity, |_, _| {});
|
||||
}
|
||||
Err(_) => {}
|
||||
}
|
||||
}
|
||||
})),
|
||||
})
|
||||
}
|
||||
|
||||
/* Some helpers */
|
||||
pub fn send_menu(disc: &mut MutexGuard<DiscordState>) {
|
||||
disc.tx.send(DiscordUpdate::Details("Menu".into()));
|
||||
disc.tx.send(DiscordUpdate::State("Idling".into()));
|
||||
disc.tx.send(DiscordUpdate::LargeImg("bg_main".into()));
|
||||
}
|
||||
pub fn send_singleplayer(disc: &mut MutexGuard<DiscordState>) {
|
||||
disc.tx.send(DiscordUpdate::Details("Singleplayer".into()));
|
||||
disc.tx.send(DiscordUpdate::State("Playing...".into()));
|
||||
}
|
@ -1,6 +1,10 @@
|
||||
#![feature(drain_filter)]
|
||||
#![recursion_limit = "2048"]
|
||||
|
||||
#[cfg(feature = "discord")]
|
||||
#[macro_use]
|
||||
extern crate lazy_static;
|
||||
|
||||
#[macro_use]
|
||||
pub mod ui;
|
||||
pub mod anim;
|
||||
@ -17,16 +21,21 @@ pub mod settings;
|
||||
pub mod singleplayer;
|
||||
pub mod window;
|
||||
|
||||
#[cfg(feature = "discord")]
|
||||
pub mod discord;
|
||||
|
||||
// Reexports
|
||||
pub use crate::error::Error;
|
||||
|
||||
use crate::{
|
||||
audio::{base::Genre, AudioFrontend},
|
||||
menu::main::MainMenuState,
|
||||
settings::Settings,
|
||||
window::Window,
|
||||
use crate::{audio::AudioFrontend, menu::main::MainMenuState, settings::Settings, window::Window};
|
||||
use log::{self, debug, error, info, warn};
|
||||
|
||||
#[cfg(feature = "discord")]
|
||||
use std::sync::{
|
||||
mpsc::Sender,
|
||||
Mutex,
|
||||
};
|
||||
use log::{debug, error, info, warn};
|
||||
|
||||
use simplelog::{CombinedLogger, Config, TermLogger, WriteLogger};
|
||||
use std::{fs::File, mem, panic, str::FromStr};
|
||||
|
||||
@ -80,6 +89,14 @@ pub trait PlayState {
|
||||
fn name(&self) -> &'static str;
|
||||
}
|
||||
|
||||
#[cfg(feature = "discord")]
|
||||
lazy_static! {
|
||||
//Set up discord rich presence
|
||||
static ref discord_instance: Mutex<discord::DiscordState> = {
|
||||
discord::run()
|
||||
};
|
||||
}
|
||||
|
||||
fn main() {
|
||||
// Set up the global state.
|
||||
let settings = Settings::load();
|
||||
@ -109,6 +126,17 @@ fn main() {
|
||||
),
|
||||
])
|
||||
.unwrap();
|
||||
|
||||
// Initialize discord. (lazy_static intialise lazily...)
|
||||
#[cfg(feature = "discord")]
|
||||
{
|
||||
match discord_instance.lock() {
|
||||
Ok(disc) => {
|
||||
//great
|
||||
}
|
||||
Err(e) => {}
|
||||
}
|
||||
}
|
||||
|
||||
// Set up panic handler to relay swish panic messages to the user
|
||||
let settings_clone = global_state.settings.clone();
|
||||
@ -238,6 +266,26 @@ fn main() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//Properly shutdown discord thread
|
||||
#[cfg(feature = "discord")]
|
||||
{
|
||||
match discord_instance.lock() {
|
||||
Ok(mut disc) => {
|
||||
disc.tx.send(discord::DiscordUpdate::Shutdown);
|
||||
match disc.thread.take() {
|
||||
Some(th) => {
|
||||
th.join();
|
||||
}
|
||||
None => {
|
||||
error!("couldn't gracefully shutdown discord thread");
|
||||
}
|
||||
}
|
||||
}
|
||||
Err(e) => error!("couldn't gracefully shutdown discord thread: {}", e),
|
||||
}
|
||||
}
|
||||
|
||||
// Save settings to add new fields or create the file if it is not already there
|
||||
if let Err(err) = global_state.settings.save_to_file() {
|
||||
warn!("Failed to save settings: {:?}", err);
|
||||
|
Loading…
Reference in New Issue
Block a user