Slowly updating mods. Managed to create mod that syncs mod data between clients and server.

This commit is contained in:
2018-05-06 18:21:31 -07:00
parent ccddf1d423
commit b5a7d9797c
35 changed files with 2306 additions and 8 deletions

View File

@ -224,6 +224,7 @@ namespace Omegasis.BuyBackCollectables.Framework
if (current2.containsPoint(x, y) && this.NewItem != null && Game1.player.money >= this.Value)
{
Game1.player.money -= this.Value;
Game1.playSound("coin");
Game1.player.addItemByMenuIfNecessary(this.NewItem);
}
}
@ -239,6 +240,7 @@ namespace Omegasis.BuyBackCollectables.Framework
{
Game1.player.money -= this.Value;
Game1.player.addItemByMenuIfNecessary(this.NewItem);
Game1.playSound("coin");
}
}

View File

@ -3,9 +3,15 @@ using StardewModdingAPI;
using StardewModdingAPI.Events;
using StardewValley;
using StardewValley.Menus;
using StardewValley.Quests;
using System;
namespace Omegasis.DailyQuestAnywhere
{
/*
*TODO: Make quest core mod???
*/
/// <summary>The mod entry point.</summary>
public class DailyQuestAnywhere : Mod
{
@ -15,6 +21,8 @@ namespace Omegasis.DailyQuestAnywhere
/// <summary>The mod configuration.</summary>
private ModConfig Config;
Quest dailyQuest;
/*********
** Public methods
@ -26,9 +34,12 @@ namespace Omegasis.DailyQuestAnywhere
this.Config = helper.ReadConfig<ModConfig>();
ControlEvents.KeyPressed += this.ControlEvents_KeyPressed;
StardewModdingAPI.Events.SaveEvents.AfterSave += SaveEvents_AfterSave;
}
/*********
** Private methods
*********/
@ -38,7 +49,53 @@ namespace Omegasis.DailyQuestAnywhere
private void ControlEvents_KeyPressed(object sender, EventArgsKeyPressed e)
{
if (Context.IsPlayerFree && e.KeyPressed.ToString() == this.Config.KeyBinding)
if (Game1.player.hasDailyQuest() == false )
{
if (this.dailyQuest == null)
{
this.dailyQuest = generateDailyQuest();
}
Game1.questOfTheDay = this.dailyQuest;
Game1.activeClickableMenu = new Billboard(true);
}
}
/// <summary>
/// Makes my daily quest referene null so we can't just keep getting a new reference.
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void SaveEvents_AfterSave(object sender, System.EventArgs e)
{
this.dailyQuest = null; //Nullify my quest reference.
}
/// <summary>
/// Generate a daily quest for sure.
/// </summary>
/// <returns></returns>
public Quest generateDailyQuest()
{
Random chanceRandom = new Random((int)Game1.uniqueIDForThisGame + (int)Game1.stats.DaysPlayed);
int chance = chanceRandom.Next(0, 101);
float actualChance = chance / 100;
//If we hit the chance for actually generating a daily quest do so, otherwise don't generate a daily quest.
if (actualChance <= Config.chanceForDailyQuest)
{
Random r = new Random((int)Game1.uniqueIDForThisGame + (int)Game1.stats.DaysPlayed);
int rand = r.Next(0, 7);
if (rand == 0) return new ItemDeliveryQuest();
if (rand == 1) return new FishingQuest();
if (rand == 2) return new StardewValley.Quests.CraftingQuest();
if (rand == 3) return new StardewValley.Quests.ItemDeliveryQuest();
if (rand == 4) return new StardewValley.Quests.ItemHarvestQuest();
if (rand == 5) return new StardewValley.Quests.ResourceCollectionQuest();
if (rand == 6) return new StardewValley.Quests.SlayMonsterQuest();
}
return null; //This should never happen.
}
}
}

View File

@ -5,5 +5,10 @@
{
/// <summary>The key which shows the menu.</summary>
public string KeyBinding { get; set; } = "H";
/// <summary>
/// The chance for a daily quest to actually happen.
/// </summary>
public float chanceForDailyQuest { get; set; } = .75f;
}
}

View File

@ -1,7 +1,7 @@
{
"Name": "Fall 28 Snow Day",
"Author": "Alpha_Omegasis",
"Version": "1.4.1",
"Version": "1.5.0",
"Description": "Makes it snow on Fall 28, which makes a good explanation for all the snow on the next day.",
"UniqueID": "Omegasis.Fall28SnowDay",
"EntryDll": "Fall28SnowDay.dll",

View File

@ -1,4 +1,5 @@
using StardewValley;
using System.Collections.Generic;
namespace Omegasis.HappyBirthday.Framework
{
@ -12,7 +13,12 @@ namespace Omegasis.HappyBirthday.Framework
/// <param name="message">The message to display.</param>
public static void ShowStarMessage(string message)
{
//IEnumerable<Farmer> players= Game1.getAllFarmers();
Game1.addHUDMessage(new HUDMessage(message, 1));
if (!message.Contains("Inventory"))
{
Game1.playSound("cancel");

View File

@ -59,12 +59,12 @@ namespace Omegasis.HappyBirthday
{
["Robin"] = "Hey @, happy birthday! I'm glad you choose this town to move here to. ",
["Demetrius"] = "Happy birthday @! Make sure you take some time off today to enjoy yourself. $h",
["Maru"] = "Happy birthday @. I tried to make you an everlasting candle but sadly that didn't work out. Maybe next year right? $h",
["Maru"] = "Happy birthday @. I tried to make you an everlasting candle for you, but sadly that didn't work out. Maybe next year right? $h",
["Sebastian"] = "Happy birthday @. Here's to another year of chilling. ",
["Linus"] = "Happy birthday @. Thanks for visiting me even on your birthday. It makes me really happy. ",
["Pierre"] = "Hey @, happy birthday! Hopefully this next year for you will be a great one! ",
["Caroline"] = "Happy birthday @. Thank you for all that you've done for our community. I'm sure your parents must be proud of you.$h",
["Abigail"] = "Happy Birthday @! Hopefully this year we can go on even more adventures together $h!",
["Abigail"] = "Happy birthday @! Hopefully this year we can go on even more adventures together $h!",
["Alex"] = "Yo @, happy birthday! Maybe this will be your best year yet.$h",
["George"] = "When you get to my age birthdays come and go. Still happy birthday @.",
["Evelyn"] = "Happy birthday @. You have grown up to be such a fine individual and I'm sure you'll continue to grow. ",

View File

@ -0,0 +1,195 @@
using Galaxy.Api;
using ModdedUtilitiesNetworking.Framework;
using ModdedUtilitiesNetworking.Framework.Clients;
using ModdedUtilitiesNetworking.Framework.Delegates;
using ModdedUtilitiesNetworking.Framework.Extentions;
using ModdedUtilitiesNetworking.Framework.Servers;
using StardewModdingAPI;
using StardewValley;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.Serialization.Formatters.Binary;
using System.Text;
using System.Threading.Tasks;
using static ModdedUtilitiesNetworking.Framework.Delegates.DelegateInfo;
namespace ModdedUtilitiesNetworking
{
public class ModCore : Mod
{
public static CustomMultiplayer multiplayer;
public static IModHelper helper;
public static IMonitor monitor;
public static IManifest manifest;
bool multiplayerSet;
public static Dictionary<string, ReadWriter> objectTypes = new Dictionary<string, ReadWriter>();
public static Dictionary<string, voidFunc> possibleVoidFunctions = new Dictionary<string, voidFunc>();
public static string displayMessageString = "Omegasis.ModdedUtilitiesNetworking.ModCore.displayMessage";
public override void Entry(IModHelper helper)
{
helper = Helper;
monitor = Monitor;
manifest = ModManifest;
StardewModdingAPI.Events.SaveEvents.AfterLoad += SaveEvents_AfterLoad;
StardewModdingAPI.Events.ControlEvents.KeyPressed += ControlEvents_KeyPressed;
multiplayerSet = false;
multiplayer = new CustomMultiplayer();
possibleVoidFunctions.Add(displayMessageString, new voidFunc(displayMessage));
initializeBasicTypes();
}
private void ControlEvents_KeyPressed(object sender, StardewModdingAPI.Events.EventArgsKeyPressed e)
{
if (e.KeyPressed==Microsoft.Xna.Framework.Input.Keys.K)
{
multiplayer.sendModInfoReturnVoid(displayMessageString, typeof(String), (object)"My love is like fire.");
}
}
/// <summary>
/// Don't change this. Sets appropriate clients and servers once the game has loaded.
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void SaveEvents_AfterLoad(object sender, EventArgs e)
{
if (Game1.server != null && multiplayerSet == false)
{
List<Server> servers = new List<Server>();
if (Game1.server != null)
{
ModCore.monitor.Log(Game1.server.GetType().ToString());
//var property = ModCore.helper.Reflection.GetProperty<List<Server>>(Game1.server, "servers", true);
Type type = Game1.server.GetType();
BindingFlags bindingFlags = BindingFlags.Instance | BindingFlags.NonPublic;
// get the field info
FieldInfo finfo = type.GetField("servers", bindingFlags);
var list = (List<Server>)finfo.GetValue(Game1.server);
foreach (var server in list)
{
servers.Add(server);
}
}
Game1.server.stopServer();
Game1.server = new CustomGameServer();
multiplayerSet = true;
(Game1.server as CustomGameServer).startServer();
ModCore.monitor.Log("Custom multiplayer binding success!");
}
if(Game1.client !=null && multiplayerSet == false)
{
if(Game1.client is LidgrenClient)
{
BindingFlags bindingFlags = BindingFlags.Instance | BindingFlags.NonPublic;
// get the field info
FieldInfo finfo = typeof(LidgrenClient).GetField("address", bindingFlags);
var address = (string)finfo.GetValue(Game1.client);
Game1.client.disconnect(true); //Disconnect old client
CustomLidgrenClient client = new CustomLidgrenClient(address);
Game1.client = client;
client.connect(); //Connect new client.
multiplayerSet = true;
}
if(Game1.client is StardewValley.SDKs.GalaxyNetClient)
{
BindingFlags bindingFlags = BindingFlags.Instance | BindingFlags.NonPublic;
// get the field info
FieldInfo finfo = typeof(StardewValley.SDKs.GalaxyNetClient).GetField("lobbyId", bindingFlags);
var galaxyID = (GalaxyID)finfo.GetValue(Game1.client);
Game1.client.disconnect(true); //Disconnect old client
CustomGalaxyClient client = new CustomGalaxyClient(galaxyID);
Game1.client = client;
client.connect(); //Connect new client.
multiplayerSet = true;
}
}
}
/// <summary>
/// Static Debug function.
/// </summary>
/// <param name="param"></param>
public static void displayMessage(object param)
{
string s =(string) param;
monitor.Log(s);
}
/// <summary>
/// Initialize basic supported types.
/// </summary>
public static void initializeBasicTypes()
{
objectTypes.Add(typeof(String).ToString(), new ReadWriter(new reader(BinaryReadWriteExtentions.ReadString), new writer(BinaryReadWriteExtentions.WriteString)));
}
/// <summary>
/// Process all possible functions that can occur.
/// </summary>
/// <param name="key"></param>
/// <param name="obj"></param>
public static void processVoidFunction(string key,object obj)
{
foreach(var v in possibleVoidFunctions)
{
if (v.Key == key) v.Value.Invoke(obj);
}
}
/// <summary>
/// Process all possible data types.
/// </summary>
/// <param name="msg"></param>
/// <param name="key"></param>
/// <returns></returns>
public static object processTypes(BinaryReader msg,string key)
{
foreach(var v in objectTypes)
{
if (v.Key == key)
{
object o= v.Value.read(msg);
return o;
}
}
monitor.Log("Error: type not found: " + key, LogLevel.Error);
return null;
}
}
}

View File

@ -0,0 +1,151 @@
using Galaxy.Api;
using StardewValley;
using StardewValley.Network;
using StardewValley.SDKs;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ModdedUtilitiesNetworking.Framework.Clients
{
class CustomGalaxyClient :GalaxyNetClient
{
private GalaxyID lobbyId;
private GalaxySocket client;
private GalaxyID serverId;
public CustomGalaxyClient(GalaxyID lobbyId) : base(lobbyId)
{
this.lobbyId = lobbyId;
}
public override string getUserID()
{
return Convert.ToString(GalaxyInstance.User().GetGalaxyID().ToUint64());
}
protected override string getHostUserName()
{
return GalaxyInstance.Friends().GetFriendPersonaName(this.serverId);
}
protected override void connectImpl()
{
this.client = new GalaxySocket(ModCore.multiplayer.protocolVersion);
GalaxyInstance.User().GetGalaxyID();
this.client.JoinLobby(this.lobbyId);
ModCore.monitor.Log("Success on generating modded galaxy client.");
}
public override void disconnect(bool neatly = true)
{
if (this.client == null)
return;
Console.WriteLine("Disconnecting from server {0}", (object)this.lobbyId);
this.client.Close();
this.client = (GalaxySocket)null;
this.connectionMessage = (string)null;
}
protected override void receiveMessagesImpl()
{
if (this.client == null || !this.client.Connected)
return;
if (this.client.Connected && this.serverId == (GalaxyID)null)
this.serverId = this.client.LobbyOwner;
this.client.Receive(new Action<GalaxyID>(this.onReceiveConnection), new Action<GalaxyID, Stream>(this.onReceiveMessage), new Action<GalaxyID>(this.onReceiveDisconnect), new Action<string>(this.onReceiveError));
this.client.Heartbeat(Enumerable.Repeat<GalaxyID>(this.serverId, 1));
if (this.client.GetTimeSinceLastMessage(this.serverId) <= 30000L)
return;
this.timedOut = true;
this.disconnect(true);
}
private void onReceiveConnection(GalaxyID peer)
{
}
private void onReceiveMessage(GalaxyID peer, Stream messageStream)
{
if (peer != this.serverId)
return;
using (IncomingMessage message = new IncomingMessage())
{
using (BinaryReader reader = new BinaryReader(messageStream))
{
message.Read(reader);
this.processIncomingMessage(message);
}
}
}
private void onReceiveDisconnect(GalaxyID peer)
{
if (peer != this.serverId)
ModCore.multiplayer.playerDisconnected((long)peer.ToUint64());
else
this.timedOut = true;
}
private void onReceiveError(string messageKey)
{
this.connectionMessage = messageKey;
}
public override void sendMessage(OutgoingMessage message)
{
if (this.client == null || !this.client.Connected || this.serverId == (GalaxyID)null)
return;
this.client.Send(this.serverId, message);
}
protected override void processIncomingMessage(IncomingMessage message)
{
byte messageType = message.MessageType;
if ((uint)messageType <= 9U)
{
switch (messageType)
{
case 1:
this.receiveServerIntroduction(message.Reader);
return;
case 2:
this.userNames[message.FarmerID] = message.Reader.ReadString();
ModCore.multiplayer.processIncomingMessage(message);
return;
case 3:
ModCore.multiplayer.processIncomingMessage(message);
return;
case 9:
this.receiveAvailableFarmhands(message.Reader);
return;
}
}
else if ((int)messageType != 11)
{
if ((int)messageType == 16)
{
if (message.FarmerID != Game1.serverHost.Value.UniqueMultiplayerID)
return;
this.receiveUserNameUpdate(message.Reader);
return;
}
}
else
{
this.connectionMessage = message.Reader.ReadString();
return;
}
if (message.MessageType == 20)
{
ModCore.monitor.Log("JUMPING JELLYBEANS!!!");
}
ModCore.multiplayer.processIncomingMessage(message); //If we don't know how to initially process the message, send it to the multiplayer function.
}
}
}

View File

@ -0,0 +1,211 @@
using Lidgren.Network;
using ModdedUtilitiesNetworking.Framework.Network;
using StardewValley;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Netcode;
using ModdedUtilitiesNetworking.Framework.Extentions;
namespace ModdedUtilitiesNetworking.Framework.Clients
{
class CustomLidgrenClient : LidgrenClient
{
private string address;
private NetClient client;
private bool serverDiscovered;
public CustomLidgrenClient(string address) : base(address)
{
this.address = address;
}
public override string getUserID()
{
return "";
}
protected override string getHostUserName()
{
return this.client.ServerConnection.RemoteEndPoint.Address.ToString();
}
protected override void connectImpl()
{
NetPeerConfiguration config = new NetPeerConfiguration("StardewValley");
config.EnableMessageType(NetIncomingMessageType.DiscoveryResponse);
config.EnableMessageType(NetIncomingMessageType.Data);
config.ConnectionTimeout = 30f;
config.PingInterval = 5f;
config.MaximumTransmissionUnit = 1200;
this.client = new NetClient(config);
this.client.Start();
int serverPort = 24642;
if (this.address.Contains(":"))
{
string[] strArray = this.address.Split(':');
this.address = strArray[0];
serverPort = Convert.ToInt32(strArray[1]);
}
this.client.DiscoverKnownPeer(this.address, serverPort);
ModCore.monitor.Log("Success on generating modded lidgren client.");
}
public override void disconnect(bool neatly = true)
{
if (this.client.ConnectionStatus != NetConnectionStatus.Disconnected && this.client.ConnectionStatus != NetConnectionStatus.Disconnecting)
{
if (neatly)
this.sendMessage(new OutgoingMessage((byte)19, Game1.player, new object[0]));
this.client.FlushSendQueue();
this.client.Disconnect("");
this.client.FlushSendQueue();
}
this.connectionMessage = (string)null;
}
protected virtual bool validateProtocol(string version)
{
return version == ModCore.multiplayer.protocolVersion;
}
protected override void receiveMessagesImpl()
{
NetIncomingMessage netIncomingMessage;
while ((netIncomingMessage = this.client.ReadMessage()) != null)
{
switch (netIncomingMessage.MessageType)
{
case NetIncomingMessageType.ErrorMessage:
case NetIncomingMessageType.DebugMessage:
case NetIncomingMessageType.WarningMessage:
string str = netIncomingMessage.ReadString();
Console.WriteLine("{0}: {1}", (object)netIncomingMessage.MessageType, (object)str);
Game1.debugOutput = str;
continue;
case NetIncomingMessageType.StatusChanged:
this.statusChanged(netIncomingMessage);
continue;
case NetIncomingMessageType.Data:
this.parseDataMessageFromServer(netIncomingMessage);
continue;
case NetIncomingMessageType.DiscoveryResponse:
ModCore.monitor.Log("Found server at " + (object)netIncomingMessage.SenderEndPoint);
if (this.validateProtocol(netIncomingMessage.ReadString()))
{
this.serverName = netIncomingMessage.ReadString();
this.receiveHandshake(netIncomingMessage);
this.serverDiscovered = true;
continue;
}
this.connectionMessage = "Strings\\UI:CoopMenu_FailedProtocolVersion";
this.client.Disconnect("");
continue;
default:
continue;
}
}
if (this.client.ServerConnection == null || DateTime.Now.Second % 2 != 0)
return;
Game1.debugOutput = "Ping: " + (object)(float)((double)this.client.ServerConnection.AverageRoundtripTime * 1000.0) + "ms";
}
private void receiveHandshake(NetIncomingMessage msg)
{
this.client.Connect(msg.SenderEndPoint.Address.ToString(), msg.SenderEndPoint.Port);
}
private void statusChanged(NetIncomingMessage message)
{
switch ((NetConnectionStatus)message.ReadByte())
{
case NetConnectionStatus.Disconnected:
case NetConnectionStatus.Disconnecting:
this.clientRemotelyDisconnected();
break;
}
}
private void clientRemotelyDisconnected()
{
this.timedOut = true;
}
public override void sendMessage(OutgoingMessage message)
{
NetOutgoingMessage message1 = this.client.CreateMessage();
using (NetBufferWriteStream bufferWriteStream = new NetBufferWriteStream((NetBuffer)message1))
{
using (BinaryWriter writer = new BinaryWriter((Stream)bufferWriteStream))
message.Write(writer);
}
int num = (int)this.client.SendMessage(message1, NetDeliveryMethod.ReliableOrdered);
}
private void parseDataMessageFromServer(NetIncomingMessage dataMsg)
{
using (IncomingMessage message = new IncomingMessage())
{
using (NetBufferReadStream bufferReadStream = new NetBufferReadStream((NetBuffer)dataMsg))
{
using (BinaryReader reader = new BinaryReader((Stream)bufferReadStream))
{
while ((long)dataMsg.LengthBits - dataMsg.Position >= 8L)
{
message.Read(reader);
this.processIncomingMessage(message);
}
}
}
}
}
protected override void processIncomingMessage(IncomingMessage message)
{
base.processIncomingMessage(message);
//Packet signiture for functions that return nothing.
if (message.MessageType == 20)
{
object[] obj = message.Reader.ReadModdedInfoPacket();
string functionName = (string)obj[0];
string classType = (string)obj[1];
object actualObject = ModCore.processTypes(message.Reader, classType);
ModCore.processVoidFunction(functionName, actualObject);
return;
}
//message.Reader.ReadChar();
//Write Binary ententions reader
//ModCore.multiplayer.processIncomingMessage(message); //If we don't know how to initially process the message, send it to the multiplayer function.
}
protected override void receiveServerIntroduction(BinaryReader msg)
{
Game1.otherFarmers.Roots[Game1.player.UniqueMultiplayerID] = (NetRoot<Farmer>)(Game1.player.NetFields.Root as NetFarmerRoot);
NetFarmerRoot netFarmerRoot = ModCore.multiplayer.readFarmer(msg);
long uniqueMultiplayerId = netFarmerRoot.Value.UniqueMultiplayerID;
Game1.serverHost = netFarmerRoot;
Game1.serverHost.Value.teamRoot = ModCore.multiplayer.readObjectFull<FarmerTeam>(msg);
Game1.otherFarmers.Roots.Remove(uniqueMultiplayerId);
Game1.otherFarmers.Roots.Add(uniqueMultiplayerId, (NetRoot<Farmer>)netFarmerRoot);
Game1.player.teamRoot = Game1.serverHost.Value.teamRoot;
Game1.netWorldState = ModCore.multiplayer.readObjectFull<IWorldState>(msg);
Game1.netWorldState.Clock.InterpolationTicks = 0;
Game1.netWorldState.Value.WriteToGame1();
this.setUpGame();
if (Game1.chatBox == null)
return;
Game1.chatBox.listPlayers();
}
}
}

View File

@ -0,0 +1,108 @@
using ModdedUtilitiesNetworking.Framework.Messages;
using ModdedUtilitiesNetworking.Framework.Servers;
using StardewValley;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization.Formatters.Binary;
using System.Text;
using System.Threading.Tasks;
using static ModdedUtilitiesNetworking.Framework.Delegates.DelegateInfo;
namespace ModdedUtilitiesNetworking.Framework
{
public class CustomMultiplayer : StardewValley.Multiplayer
{
public override bool isClientBroadcastType(byte messageType)
{
return true;
}
/// <summary>
/// Sends an outgoing message to appropriate players.
/// </summary>
/// <param name="message"></param>
public void sendMessage(OutgoingMessage message)
{
if (Game1.server != null)
{
foreach (long peerId in (IEnumerable<long>)Game1.otherFarmers.Keys)
{
Game1.server.sendMessage(peerId, message);
}
}
if (Game1.client != null)
{
Game1.client.sendMessage(message);
}
}
/// <summary>
/// Updates the server.
/// </summary>
public override void UpdateEarly()
{
if (Game1.CurrentEvent == null)
this.removeDisconnectedFarmers();
this.updatePendingConnections();
if (Game1.server != null)
(Game1.server as CustomGameServer).receiveMessages();
else if (Game1.client != null)
Game1.client.receiveMessages();
this.tickFarmerRoots();
this.tickLocationRoots();
}
/// <summary>
/// Creates a net outgoing message that is written specifically to call a void function when sent.
/// </summary>
/// <param name="functionName"></param>
/// <param name="objectParametersType"></param>
/// <param name="data"></param>
/// <param name="source"></param>
/// <returns></returns>
public OutgoingMessage sendOutGoingMessageReturnVoid(string functionName, string objectParametersType, object data, Farmer source)
{
OutgoingMessage message = new OutgoingMessage((byte)20, source, makeDataArray(functionName, objectParametersType, data));
return message;
}
public OutgoingMessage sendOutGoingMessageReturnVoid(string functionName, Type objectParametersType, object data, Farmer source)
{
OutgoingMessage message = new OutgoingMessage((byte)20, source, makeDataArray(functionName, objectParametersType.ToString(), data));
return message;
}
public object[] makeDataArray(string functionName, string objectParametersType, object data)
{
object[] obj = new object[3]
{
functionName,
objectParametersType,
data
};
return obj;
}
/// <summary>
/// Creates all of the necessary parameters for the outgoing message to be sent to the server/client on what to do and how to handle the data sent.
/// This message written will attempt to access a function that doesn't return anything. Essentially null.
/// </summary>
/// <param name="uniqueID"></param>
/// <param name="classType"></param>
/// <param name="data"></param>
public void sendModInfoReturnVoid(string uniqueID,Type classType,object data)
{
Farmer f = Game1.player;
OutgoingMessage message =ModCore.multiplayer.sendOutGoingMessageReturnVoid(uniqueID, classType, data, f);
ModCore.multiplayer.sendMessage(message);
}
}
}

View File

@ -0,0 +1,44 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using static ModdedUtilitiesNetworking.Framework.Delegates.DelegateInfo;
namespace ModdedUtilitiesNetworking.Framework.Delegates
{
public class DelegateInfo
{
public delegate void voidFunc(object obj);
public delegate object reader(BinaryReader reader);
public delegate void writer(BinaryWriter writer, object obj);
}
public class ReadWriter
{
reader reader;
writer writer;
public ReadWriter(reader reader, writer writer)
{
this.reader = reader;
this.writer = writer;
}
public void write(BinaryWriter bWriter, object obj)
{
writer.Invoke(bWriter, obj);
}
public object read(BinaryReader bReader)
{
return reader.Invoke(bReader);
}
}
}

View File

@ -0,0 +1,65 @@
using Microsoft.Xna.Framework;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Netcode;
namespace ModdedUtilitiesNetworking.Framework.Extentions
{
public static class BinaryReadWriteExtentions
{
public static Vector3 ReadVector3(this BinaryReader reader)
{
float x=reader.ReadSingle();
float y=reader.ReadSingle();
float z=reader.ReadSingle();
return new Vector3(x, y, z);
}
public static string ReadString(this BinaryReader reader)
{
String s= reader.ReadString();
return new string(s.ToCharArray());
}
public static void WriteString(this BinaryWriter writer, object str)
{
writer.WriteString((string)str);
}
/// <summary>
/// Read the custom info packet sent from a modded client or server.
/// </summary>
/// <param name="reader"></param>
/// <returns></returns>
public static object[] ReadModdedInfoPacket(this BinaryReader reader)
{
object[] o = new object[2]
{
reader.ReadString(),
reader.ReadString()
};
return o;
}
/// <summary>
/// Read the remaining byte data in an array.
/// </summary>
/// <param name="reader"></param>
/// <returns></returns>
public static byte[] ReadAllBytes(this BinaryReader reader)
{
using (var memoryStream = new MemoryStream())
{
reader.BaseStream.CopyTo(memoryStream);
return memoryStream.ToArray();
}
}
//Can do custom classes here for reading and writing.
//That way it will be better to save/load data
}
}

View File

@ -0,0 +1,142 @@
using Microsoft.Xna.Framework;
using Netcode;
using StardewValley;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ModdedUtilitiesNetworking.Framework.Messages
{
public class OutgoingMessageBase
{
public byte messageType;
public long farmerID;
public object[] data;
public string uniqueID;
public byte MessageType
{
get
{
return this.messageType;
}
}
public long FarmerID
{
get
{
return this.farmerID;
}
}
public Farmer SourceFarmer
{
get
{
return Game1.getFarmer(this.farmerID);
}
}
public string UniqueID{
get
{
return this.uniqueID;
}
}
public ReadOnlyCollection<object> Data
{
get
{
return Array.AsReadOnly<object>(this.data);
}
}
public OutgoingMessageBase(byte messageType, long farmerID, string uniqueID, params object[] data)
{
this.messageType = messageType;
this.farmerID = farmerID;
this.uniqueID = uniqueID;
this.data = data;
}
public virtual OutgoingMessageBase generateOutgoingMessage(byte messageType, Farmer sourceFarmer, string uniqueID ,params object[] data)
{
return new OutgoingMessageBase(messageType, sourceFarmer.UniqueMultiplayerID, uniqueID ,data);
}
/*
public virtual OutgoingMessageBase generateOutgoingMessage(IncomingMessage message)
{
OutgoingMessageBase msg = new OutgoingMessageBase(message.MessageType, message.FarmerID, message.uniqueID,new object[1]
{
(object) message.Data
});
return msg;
}
*/
public virtual void Write(BinaryWriter writer)
{
writer.Write(this.messageType);
writer.Write(this.farmerID);
writer.Write(this.uniqueID);
object[] data = this.data;
BinaryReaderWriterExtensions.WriteSkippable(writer, (Action)(() =>
{
foreach (object enumValue in data)
{
if (enumValue is Vector2)
{
writer.Write(((Vector2)enumValue).X);
writer.Write(((Vector2)enumValue).Y);
}
else if (enumValue is Guid)
writer.Write(((Guid)enumValue).ToByteArray());
else if (enumValue is byte[])
writer.Write((byte[])enumValue);
else if (enumValue is bool)
writer.Write((bool)enumValue ? (byte)1 : (byte)0);
else if (enumValue is byte)
writer.Write((byte)enumValue);
else if (enumValue is int)
writer.Write((int)enumValue);
else if (enumValue is short)
writer.Write((short)enumValue);
else if (enumValue is float)
writer.Write((float)enumValue);
else if (enumValue is long)
writer.Write((long)enumValue);
else if (enumValue is string)
writer.Write((string)enumValue);
else if (enumValue is string[])
{
string[] strArray = (string[])enumValue;
writer.Write((byte)strArray.Length);
for (int index = 0; index < strArray.Length; ++index)
writer.Write(strArray[index]);
}
else
{
if (!(enumValue is IConvertible) || !enumValue.GetType().IsValueType)
throw new InvalidDataException();
BinaryReaderWriterExtensions.WriteEnum(writer, enumValue);
}
}
}));
}
public virtual OutgoingMessage convertToOutgoingMessage()
{
return new OutgoingMessage(this.messageType, this.farmerID, this.data);
}
}
}

View File

@ -0,0 +1,97 @@
using Lidgren.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ModdedUtilitiesNetworking.Framework.Network
{
public class NetBufferReadStream : Stream
{
private long offset;
public NetBuffer Buffer;
public override bool CanRead
{
get
{
return true;
}
}
public override bool CanSeek
{
get
{
return true;
}
}
public override bool CanWrite
{
get
{
return false;
}
}
public override long Length
{
get
{
return ((long)this.Buffer.LengthBits - this.offset) / 8L;
}
}
public override long Position
{
get
{
return (this.Buffer.Position - this.offset) / 8L;
}
set
{
this.Buffer.Position = this.offset + value * 8L;
}
}
public NetBufferReadStream(NetBuffer buffer)
{
this.Buffer = buffer;
this.offset = buffer.Position;
}
public override void Flush()
{
}
public override int Read(byte[] buffer, int offset, int count)
{
this.Buffer.ReadBytes(buffer, offset, count);
return count;
}
public override long Seek(long offset, SeekOrigin origin)
{
if (origin == SeekOrigin.Begin)
this.Position = offset;
else if (origin == SeekOrigin.Current)
this.Position = this.Position + offset;
else if (origin == SeekOrigin.End)
this.Position = this.Length + offset;
return this.Position;
}
public override void SetLength(long value)
{
throw new NotSupportedException();
}
public override void Write(byte[] buffer, int offset, int count)
{
throw new NotSupportedException();
}
}
}

View File

@ -0,0 +1,98 @@
using Lidgren.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ModdedUtilitiesNetworking.Framework.Network
{
public class NetBufferWriteStream : Stream
{
private int offset;
public NetBuffer Buffer;
public override bool CanRead
{
get
{
return false;
}
}
public override bool CanSeek
{
get
{
return true;
}
}
public override bool CanWrite
{
get
{
return true;
}
}
public override long Length
{
get
{
throw new NotSupportedException();
}
}
public override long Position
{
get
{
return (long)((this.Buffer.LengthBits - this.offset) / 8);
}
set
{
this.Buffer.LengthBits = (int)((long)this.offset + value * 8L);
}
}
public NetBufferWriteStream(NetBuffer buffer)
{
this.Buffer = buffer;
this.offset = buffer.LengthBits;
}
public override void Flush()
{
}
public override int Read(byte[] buffer, int offset, int count)
{
throw new NotSupportedException();
}
public override long Seek(long offset, SeekOrigin origin)
{
if (origin == SeekOrigin.Begin)
this.Position = offset;
else if (origin == SeekOrigin.Current)
this.Position = this.Position + offset;
else if (origin == SeekOrigin.End)
throw new NotSupportedException();
return this.Position;
}
public override void SetLength(long value)
{
throw new NotSupportedException();
}
public override void Write(byte[] buffer, int offset, int count)
{
this.Buffer.Write(buffer, offset, count);
}
}
}

View File

@ -0,0 +1,433 @@
using Microsoft.Xna.Framework;
using ModdedUtilitiesNetworking.Framework.Extentions;
using Netcode;
using StardewValley;
using StardewValley.Buildings;
using StardewValley.Locations;
using StardewValley.Minigames;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Serialization;
namespace ModdedUtilitiesNetworking.Framework.Servers
{
public class CustomGameServer : IGameServer
{
public List<Server> servers = new List<Server>();
public List<Action> pendingGameAvailableActions = new List<Action>();
public CustomGameServer()
{
this.servers = new List<Server>();
this.servers.Add(ModCore.multiplayer.InitServer((Server)new LidgrenServer((IGameServer)this)));
ModCore.monitor.Log("Custom Lidgren Server Created");
ModCore.monitor.Log("Custom Game Server Created");
if (Program.sdk.Networking == null)
return;
this.servers.Add(Program.sdk.Networking.CreateServer((IGameServer)this));
}
public CustomGameServer(List<Server> servers)
{
this.servers = new List<Server>();
foreach(var server in servers)
{
this.servers.Add(server);
}
}
public int connectionsCount
{
get
{
return Enumerable.Sum<Server>((IEnumerable<Server>)this.servers, (Func<Server, int>)(s => s.connectionsCount));
}
}
public string getInviteCode()
{
foreach (Server server in this.servers)
{
string inviteCode = server.getInviteCode();
if (inviteCode != null)
return inviteCode;
}
return (string)null;
}
public string getUserName(long farmerId)
{
foreach (Server server in this.servers)
{
if (server.getUserName(farmerId) != null)
return server.getUserName(farmerId);
}
return (string)null;
}
protected void initialize()
{
foreach (Server server in this.servers)
{
if (server.connected() == true) continue;
server.initialize();
}
this.updateLobbyData();
}
public void setPrivacy(ServerPrivacy privacy)
{
foreach (Server server in this.servers)
server.setPrivacy(privacy);
}
public void stopServer()
{
foreach (Server server in this.servers)
server.stopServer();
}
public void receiveMessages()
{
foreach (Server server in this.servers)
{
server.receiveMessages();
}
if (!this.isGameAvailable())
return;
foreach (Action action in this.pendingGameAvailableActions)
action();
this.pendingGameAvailableActions.Clear();
}
public void sendMessage(long peerId, OutgoingMessage message)
{
foreach (Server server in this.servers)
server.sendMessage(peerId, message);
}
public bool canAcceptIPConnections()
{
return Enumerable.Aggregate<bool, bool>(Enumerable.Select<Server, bool>((IEnumerable<Server>)this.servers, (Func<Server, bool>)(s => s.canAcceptIPConnections())), false, (Func<bool, bool, bool>)((a, b) => a | b));
}
public bool canOfferInvite()
{
return Enumerable.Aggregate<bool, bool>(Enumerable.Select<Server, bool>((IEnumerable<Server>)this.servers, (Func<Server, bool>)(s => s.canOfferInvite())), false, (Func<bool, bool, bool>)((a, b) => a | b));
}
public void offerInvite()
{
foreach (Server server in this.servers)
{
if (server.canOfferInvite())
server.offerInvite();
}
}
public bool connected()
{
foreach (Server server in this.servers)
{
if (!server.connected())
return false;
}
return true;
}
public void sendMessage(long peerId, byte messageType, Farmer sourceFarmer, params object[] data)
{
this.sendMessage(peerId, new OutgoingMessage(messageType, sourceFarmer, data));
}
public void sendMessages()
{
foreach (Farmer farmer in (IEnumerable<Farmer>)Game1.otherFarmers.Values)
{
foreach (OutgoingMessage message in (IEnumerable<OutgoingMessage>)farmer.messageQueue)
this.sendMessage(farmer.UniqueMultiplayerID, message);
farmer.messageQueue.Clear();
}
}
public void startServer()
{
Console.WriteLine("Starting server. Protocol version: " + ModCore.multiplayer.protocolVersion);
this.initialize();
if ((NetFieldBase<Farmer, NetRef<Farmer>>)Game1.serverHost == (NetRef<Farmer>)null)
Game1.serverHost = new NetFarmerRoot();
Game1.serverHost.Value = Game1.player;
Game1.serverHost.MarkClean();
Game1.serverHost.Clock.InterpolationTicks = ModCore.multiplayer.defaultInterpolationTicks;
if ((NetFieldBase<IWorldState, NetRef<IWorldState>>)Game1.netWorldState == (NetRef<IWorldState>)null)
Game1.netWorldState = new NetRoot<IWorldState>((IWorldState)new NetWorldState());
Game1.netWorldState.Clock.InterpolationTicks = 0;
Game1.netWorldState.Value.UpdateFromGame1();
}
public void sendServerIntroduction(long peer)
{
this.sendLocation(peer, (GameLocation)Game1.getFarm());
this.sendLocation(peer, Game1.getLocationFromName("FarmHouse"));
this.sendMessage(peer, new OutgoingMessage((byte)1, Game1.serverHost.Value, new object[3]
{
(object) ModCore.multiplayer.writeObjectFullBytes<Farmer>((NetRoot<Farmer>) Game1.serverHost, new long?(peer)),
(object) ModCore.multiplayer.writeObjectFullBytes<FarmerTeam>(Game1.player.teamRoot, new long?(peer)),
(object) ModCore.multiplayer.writeObjectFullBytes<IWorldState>(Game1.netWorldState, new long?(peer))
}));
foreach (KeyValuePair<long, NetRoot<Farmer>> keyValuePair in Game1.otherFarmers.Roots)
{
if (keyValuePair.Key != Game1.player.UniqueMultiplayerID && keyValuePair.Key != peer)
this.sendMessage(peer, new OutgoingMessage((byte)2, keyValuePair.Value.Value, new object[2]
{
(object) this.getUserName(keyValuePair.Value.Value.UniqueMultiplayerID),
(object) ModCore.multiplayer.writeObjectFullBytes<Farmer>(keyValuePair.Value, new long?(peer))
}));
}
}
public void playerDisconnected(long disconnectee)
{
Farmer sourceFarmer = (Farmer)null;
Game1.otherFarmers.TryGetValue(disconnectee, out sourceFarmer);
ModCore.multiplayer.playerDisconnected(disconnectee);
if (sourceFarmer == null)
return;
OutgoingMessage message = new OutgoingMessage((byte)19, sourceFarmer, new object[0]);
foreach (long peerId in (IEnumerable<long>)Game1.otherFarmers.Keys)
{
if (peerId != disconnectee)
this.sendMessage(peerId, message);
}
}
public bool isGameAvailable()
{
bool flag1 = Game1.currentMinigame is Intro || Game1.Date.DayOfMonth == 0;
bool flag2 = Game1.CurrentEvent != null && Game1.CurrentEvent.isWedding;
bool flag3 = Game1.newDaySync != null && !Game1.newDaySync.hasFinished();
if (!Game1.isFestival() && !flag2 && !flag1)
return !flag3;
return false;
}
public bool whenGameAvailable(Action action)
{
if (this.isGameAvailable())
{
action();
return true;
}
this.pendingGameAvailableActions.Add(action);
return false;
}
private void rejectFarmhandRequest(string userID, NetFarmerRoot farmer, Action<OutgoingMessage> sendMessage)
{
this.sendAvailableFarmhands(userID, sendMessage);
Console.WriteLine("Rejected request for farmhand " + (farmer.Value != null ? farmer.Value.UniqueMultiplayerID.ToString() : "???"));
}
private IEnumerable<Cabin> cabins()
{
if (Game1.getFarm() != null)
{
foreach (Building building in Game1.getFarm().buildings)
{
if ((int)((NetFieldBase<int, NetInt>)building.daysOfConstructionLeft) <= 0 && building.indoors.Value is Cabin)
yield return building.indoors.Value as Cabin;
}
}
}
private bool authCheck(string userID, Farmer farmhand)
{
if (!Game1.options.enableFarmhandCreation && !(bool)((NetFieldBase<bool, NetBool>)farmhand.isCustomized))
return false;
if (!(userID == "") && !(farmhand.userID.Value == ""))
return farmhand.userID.Value == userID;
return true;
}
private Farmer findOriginalFarmhand(Farmer farmhand)
{
foreach (Cabin cabin in this.cabins())
{
if (cabin.getFarmhand().Value.UniqueMultiplayerID == farmhand.UniqueMultiplayerID)
return cabin.getFarmhand().Value;
}
return (Farmer)null;
}
public void checkFarmhandRequest(string userID, NetFarmerRoot farmer, Action<OutgoingMessage> sendMessage, Action approve)
{
if (farmer.Value == null)
{
this.rejectFarmhandRequest(userID, farmer, sendMessage);
}
else
{
long id = farmer.Value.UniqueMultiplayerID;
if (this.whenGameAvailable((Action)(() =>
{
Farmer originalFarmhand = this.findOriginalFarmhand(farmer.Value);
if (originalFarmhand == null)
{
Console.WriteLine("Rejected request for farmhand " + (object)id + ": doesn't exist");
this.rejectFarmhandRequest(userID, farmer, sendMessage);
}
else if (!this.authCheck(userID, originalFarmhand))
{
Console.WriteLine("Rejected request for farmhand " + (object)id + ": authorization failure");
this.rejectFarmhandRequest(userID, farmer, sendMessage);
}
else if (Game1.otherFarmers.ContainsKey(id) && !ModCore.multiplayer.isDisconnecting(id) || Game1.serverHost.Value.UniqueMultiplayerID == id)
{
Console.WriteLine("Rejected request for farmhand " + (object)id + ": already in use");
this.rejectFarmhandRequest(userID, farmer, sendMessage);
}
else
{
Console.WriteLine("Approved request for farmhand " + (object)id);
approve();
ModCore.multiplayer.addPlayer(farmer);
ModCore.multiplayer.broadcastPlayerIntroduction(farmer);
this.sendServerIntroduction(id);
this.updateLobbyData();
}
})))
return;
Console.WriteLine("Postponing request for farmhand " + (object)id);
sendMessage(new OutgoingMessage((byte)11, Game1.player, new object[1]
{
(object) "Strings\\UI:Client_WaitForHostAvailability"
}));
}
}
public void sendAvailableFarmhands(string userID, Action<OutgoingMessage> sendMessage)
{
List<NetRef<Farmer>> list = new List<NetRef<Farmer>>();
Game1.getFarm();
foreach (Cabin cabin in this.cabins())
{
NetRef<Farmer> farmhand = cabin.getFarmhand();
if ((!farmhand.Value.isActive() || ModCore.multiplayer.isDisconnecting(farmhand.Value.UniqueMultiplayerID)) && this.authCheck(userID, farmhand.Value))
list.Add(farmhand);
}
using (MemoryStream memoryStream = new MemoryStream())
{
using (BinaryWriter writer = new BinaryWriter((Stream)memoryStream))
{
writer.Write(Game1.year);
writer.Write(Utility.getSeasonNumber(Game1.currentSeason));
writer.Write(Game1.dayOfMonth);
writer.Write((byte)list.Count);
foreach (NetRef<Farmer> netRef in list)
{
try
{
netRef.Serializer = SaveGame.farmerSerializer;
netRef.WriteFull(writer);
}
finally
{
netRef.Serializer = (XmlSerializer)null;
}
}
memoryStream.Seek(0L, SeekOrigin.Begin);
sendMessage(new OutgoingMessage((byte)9, Game1.player, new object[1]
{
(object) memoryStream.ToArray()
}));
}
}
}
private void sendLocation(long peer, GameLocation location)
{
this.sendMessage(peer, (byte)3, Game1.serverHost.Value, (object)ModCore.multiplayer.writeObjectFullBytes<GameLocation>(ModCore.multiplayer.locationRoot(location), new long?(peer)));
}
private void warpFarmer(Farmer farmer, short x, short y, string name, bool isStructure)
{
GameLocation locationFromName = Game1.getLocationFromName(name, isStructure);
farmer.currentLocation = locationFromName;
farmer.Position = new Vector2((float)((int)x * 64), (float)((int)y * 64 - (farmer.Sprite.getHeight() - 32) + 16));
this.sendLocation(farmer.UniqueMultiplayerID, locationFromName);
}
public void processIncomingMessage(IncomingMessage message)
{
//ModCore.monitor.Log("MESSAGES????");
switch (message.MessageType)
{
case 2:
message.Reader.ReadString();
ModCore.multiplayer.processIncomingMessage(message);
break;
case 5:
this.warpFarmer(message.SourceFarmer, message.Reader.ReadInt16(), message.Reader.ReadInt16(), message.Reader.ReadString(), (int)message.Reader.ReadByte() == 1);
break;
case 20:
object[] obj = message.Reader.ReadModdedInfoPacket();
string functionName = (string)obj[0];
string classType = (string)obj[1];
object actualObject = ModCore.processTypes(message.Reader, classType);
ModCore.processVoidFunction(functionName, actualObject);
break;
default:
ModCore.multiplayer.processIncomingMessage(message);
break;
}
this.rebroadcastClientMessage(message);
}
private void rebroadcastClientMessage(IncomingMessage message)
{
OutgoingMessage message1 = new OutgoingMessage(message);
foreach (long peerId in (IEnumerable<long>)Game1.otherFarmers.Keys)
{
if (peerId != message.FarmerID)
this.sendMessage(peerId, message1);
}
}
private void setLobbyData(string key, string value)
{
foreach (Server server in this.servers)
server.setLobbyData(key, value);
}
private bool unclaimedFarmhandsExist()
{
foreach (Cabin cabin in this.cabins())
{
if (cabin.farmhand.Value == null || cabin.farmhand.Value.userID.Value == "")
return true;
}
return false;
}
public void updateLobbyData()
{
this.setLobbyData("farmName", Game1.player.farmName.Value);
this.setLobbyData("farmType", Convert.ToString(Game1.whichFarm));
this.setLobbyData("date", Convert.ToString(new WorldDate(Game1.year, Game1.currentSeason, Game1.dayOfMonth).TotalDays));
this.setLobbyData("farmhands", string.Join(",", Enumerable.Where<string>(Enumerable.Select<Farmer, string>(Game1.getAllFarmhands(), (Func<Farmer, string>)(farmhand => farmhand.userID.Value)), (Func<string, bool>)(user => user != ""))));
this.setLobbyData("newFarmhands", Convert.ToString(Game1.options.enableFarmhandCreation && this.unclaimedFarmhandsExist()));
}
}
}

View File

@ -0,0 +1,214 @@
using Lidgren.Network;
using ModdedUtilitiesNetworking.Framework.Network;
using StardewValley;
using StardewValley.Network;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ModdedUtilitiesNetworking.Framework.Servers
{
class CustomLidgrenServer : LidgrenServer
{
private HashSet<NetConnection> introductionsSent = new HashSet<NetConnection>();
private Bimap<long, NetConnection> peers = new Bimap<long, NetConnection>();
public const int defaultPort = 24642;
private NetServer server;
public override int connectionsCount
{
get
{
if (this.server == null)
return 0;
return this.server.ConnectionsCount;
}
}
public CustomLidgrenServer(IGameServer gameServer)
: base(gameServer)
{
}
public override string getUserName(long farmerId)
{
if (!this.peers.ContainsLeft(farmerId))
return (string)null;
return this.peers[farmerId].RemoteEndPoint.Address.ToString();
}
public override void setPrivacy(ServerPrivacy privacy)
{
}
public override bool canAcceptIPConnections()
{
return true;
}
public override bool connected()
{
return this.server != null;
}
public override void initialize()
{
Console.WriteLine("Starting LAN server");
NetPeerConfiguration config = new NetPeerConfiguration("StardewValley");
config.EnableMessageType(NetIncomingMessageType.DiscoveryRequest);
config.EnableMessageType(NetIncomingMessageType.ConnectionApproval);
config.Port = 24642;
config.ConnectionTimeout = 30f;
config.PingInterval = 5f;
config.MaximumConnections = ModCore.multiplayer.playerLimit * 2;
config.MaximumTransmissionUnit = 1200;
this.server = new NetServer(config);
this.server.Start();
}
public override void stopServer()
{
Console.WriteLine("Stopping LAN server");
this.server.Shutdown("Server shutting down...");
this.server.FlushSendQueue();
this.introductionsSent.Clear();
this.peers.Clear();
}
public override void receiveMessages()
{
NetIncomingMessage netIncomingMessage;
while ((netIncomingMessage = this.server.ReadMessage()) != null)
{
int i = (int)netIncomingMessage.MessageType;
//ModCore.monitor.Log("Message Type: " + i.ToString());
switch (netIncomingMessage.MessageType)
{
case NetIncomingMessageType.WarningMessage:
case NetIncomingMessageType.ErrorMessage:
case NetIncomingMessageType.DebugMessage:
string str = netIncomingMessage.ReadString();
Console.WriteLine("{0}: {1}", (object)netIncomingMessage.MessageType, (object)str);
Game1.debugOutput = str;
break;
case NetIncomingMessageType.DiscoveryRequest:
if (Game1.options.ipConnectionsEnabled)
{
this.sendVersionInfo(netIncomingMessage);
break;
}
break;
case NetIncomingMessageType.StatusChanged:
this.statusChanged(netIncomingMessage);
break;
case NetIncomingMessageType.ConnectionApproval:
if (Game1.options.ipConnectionsEnabled)
{
netIncomingMessage.SenderConnection.Approve();
break;
}
netIncomingMessage.SenderConnection.Deny();
break;
case NetIncomingMessageType.Data:
//ModCore.monitor.Log("GOT DATA~~");
this.parseDataMessageFromClient(netIncomingMessage);
break;
default:
//ModCore.monitor.Log(netIncomingMessage.ToString());
break;
}
this.server.Recycle(netIncomingMessage);
}
foreach (NetConnection netConnection in this.server.Connections)
{
NetConnection conn = netConnection;
if (conn.Status == NetConnectionStatus.Connected && !this.introductionsSent.Contains(conn))
{
this.gameServer.sendAvailableFarmhands("", (Action<OutgoingMessage>)(msg => this.sendMessage(conn, msg)));
this.introductionsSent.Add(conn);
}
}
}
private void sendVersionInfo(NetIncomingMessage message)
{
NetOutgoingMessage message1 = this.server.CreateMessage();
message1.Write(ModCore.multiplayer.protocolVersion);
message1.Write("StardewValley");
this.server.SendDiscoveryResponse(message1, message.SenderEndPoint);
}
private void statusChanged(NetIncomingMessage message)
{
switch ((NetConnectionStatus)message.ReadByte())
{
case NetConnectionStatus.Disconnected:
case NetConnectionStatus.Disconnecting:
if (!this.peers.ContainsRight(message.SenderConnection))
break;
this.playerDisconnected(this.peers[message.SenderConnection]);
break;
}
}
protected override void playerDisconnected(long disconnectee)
{
base.playerDisconnected(disconnectee);
this.introductionsSent.Remove(this.peers[disconnectee]);
this.peers.RemoveLeft(disconnectee);
}
private void parseDataMessageFromClient(NetIncomingMessage dataMsg)
{
//ModCore.monitor.Log("DATA MSG: "+dataMsg.ToString());
NetConnection peer = dataMsg.SenderConnection;
using (IncomingMessage message = new IncomingMessage())
{
using (NetBufferReadStream bufferReadStream = new NetBufferReadStream((NetBuffer)dataMsg))
{
using (BinaryReader reader = new BinaryReader((Stream)bufferReadStream))
{
while ((long)dataMsg.LengthBits - dataMsg.Position >= 8L)
{
message.Read(reader);
int type = message.MessageType;
ModCore.monitor.Log("INCOMING MESSAGE TYPE: "+type.ToString());
if (this.peers.ContainsLeft(message.FarmerID) && this.peers[message.FarmerID] == peer)
this.gameServer.processIncomingMessage(message);
else if ((int)message.MessageType == 2)
{
NetFarmerRoot farmer = ModCore.multiplayer.readFarmer(message.Reader);
this.gameServer.checkFarmhandRequest("", farmer, (msg => this.sendMessage(peer, msg)), (Action)(() => this.peers[farmer.Value.UniqueMultiplayerID] = peer));
}
}
}
}
}
}
public override void sendMessage(long peerId, OutgoingMessage message)
{
if (!this.peers.ContainsLeft(peerId))
return;
this.sendMessage(this.peers[peerId], message);
}
protected void sendMessage(NetConnection connection, OutgoingMessage message)
{
NetOutgoingMessage message1 = this.server.CreateMessage();
using (NetBufferWriteStream bufferWriteStream = new NetBufferWriteStream((NetBuffer)message1))
{
using (BinaryWriter writer = new BinaryWriter((Stream)bufferWriteStream))
message.Write(writer);
}
int num = (int)this.server.SendMessage(message1, connection, NetDeliveryMethod.ReliableOrdered);
}
public override void setLobbyData(string key, string value)
{
}
}
}

View File

@ -0,0 +1,81 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{8DB124E3-E892-4E7C-A782-2DA47771338C}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>ModdedUtilitiesNetworking</RootNamespace>
<AssemblyName>ModdedUtilitiesNetworking</AssemblyName>
<TargetFrameworkVersion>v4.6.1</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<NuGetPackageImportStamp>
</NuGetPackageImportStamp>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="GalaxyCSharp">
<HintPath>..\..\..\..\..\..\..\Desktop\GalaxyCSharp.dll</HintPath>
</Reference>
<Reference Include="Lidgren.Network, Version=3.6.0.1625, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion>
<HintPath>..\..\..\..\..\..\..\..\..\Program Files (x86)\Steam\steamapps\common\Stardew Valley\Lidgren.Network.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="System.Core" />
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="Microsoft.CSharp" />
<Reference Include="System.Data" />
<Reference Include="System.Net.Http" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="Class1.cs" />
<Compile Include="Framework\Clients\CustomGalaxyClient.cs" />
<Compile Include="Framework\Clients\CustomLidgrenClient.cs" />
<Compile Include="Framework\Delegates\DelegateInfo.cs" />
<Compile Include="Framework\Extentions\BinaryReadWriteExtentions.cs" />
<Compile Include="Framework\Messages\OutgoingMessageBase.cs" />
<Compile Include="Framework\CustomMultiplayer.cs" />
<Compile Include="Framework\Network\NetBufferReadStream.cs" />
<Compile Include="Framework\Network\NetBufferWriteStream.cs" />
<Compile Include="Framework\Servers\CustomGameServer.cs" />
<Compile Include="Framework\Servers\CustomLidgrenServer.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<None Include="manifest.json" />
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Analyzer Include="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\analyzers\dotnet\cs\StardewModdingAPI.ModBuildConfig.Analyzer.dll" />
</ItemGroup>
<ItemGroup />
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets" Condition="Exists('..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets')" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets'))" />
</Target>
</Project>

View File

@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("ModdedUtilitiesNetworking")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("ModdedUtilitiesNetworking")]
[assembly: AssemblyCopyright("Copyright © 2018")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]
// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("8db124e3-e892-4e7c-a782-2da47771338c")]
// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

View File

@ -0,0 +1,10 @@
{
"Name": "ModdedUtilitiesNetworking",
"Author": "Alpha_Omegasis",
"Version": "0.0.1",
"Description": "A dumb attempt at networking",
"UniqueID": "Omegasis.ModdedUtilitiesNetworking",
"EntryDll": "ModdedUtilitiesNetworking.dll",
"MinimumApiVersion": "2.0",
"UpdateKeys": [ "" ]
}

View File

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Pathoschild.Stardew.ModBuildConfig" version="2.1.0-beta-20180428" targetFramework="net461" />
</packages>

View File

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace NetworkMod
{
public class Class1
{
}
}

View File

@ -0,0 +1,53 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>60730e3f-3448-4f0b-9a84-9aa0488061e5</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>NetworkMod</RootNamespace>
<AssemblyName>NetworkMod</AssemblyName>
<TargetFrameworkVersion>v4.6.1</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="System"/>
<Reference Include="System.Core"/>
<Reference Include="System.Xml.Linq"/>
<Reference Include="System.Data.DataSetExtensions"/>
<Reference Include="Microsoft.CSharp"/>
<Reference Include="System.Data"/>
<Reference Include="System.Net.Http"/>
<Reference Include="System.Xml"/>
</ItemGroup>
<ItemGroup>
<Compile Include="Class1.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
</Project>

View File

@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("NetworkMod")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("NetworkMod")]
[assembly: AssemblyCopyright("Copyright © 2018")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]
// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("60730e3f-3448-4f0b-9a84-9aa0488061e5")]
// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

View File

@ -0,0 +1,37 @@
using NetworkNightmare.Framework;
using StardewModdingAPI;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace NetworkNightmare
{
public class NetworkNightmare : Mod
{
public static IModHelper helper;
public static IMonitor monitor;
public override void Entry(IModHelper helper)
{
helper = this.Helper;
monitor = this.Monitor;
StardewModdingAPI.Events.MultiplayerEvents.BeforeMainSync += MultiplayerEvents_BeforeMainSync;
}
private void MultiplayerEvents_BeforeMainSync(object sender, EventArgs e)
{
CustomMultiplayer player = new CustomMultiplayer();
CustomMultiplayer.forceCustomMultiplayer(player);
}
private void GameEvents_FirstUpdateTick(object sender, EventArgs e)
{
}
}
}

View File

@ -0,0 +1,39 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using StardewModdingAPI;
using StardewValley;
using StardewValley.Network;
namespace NetworkNightmare.Framework
{
public class CustomMultiplayer : StardewValley.Multiplayer
{
public CustomMultiplayer() : base()
{
}
public override void processIncomingMessage(IncomingMessage msg)
{
base.processIncomingMessage(msg);
}
public static bool forceCustomMultiplayer(CustomMultiplayer custom)
{
if (custom == null)
{
NetworkNightmare.monitor.Log("WELL I GIVE UP");
}
// Get a PropertyInfo of specific property type(T).GetProperty(....)
IReflectedField<Multiplayer> propertyInfo = NetworkNightmare.helper.Reflection.GetField<Multiplayer>(typeof(StardewValley.Game1), "multiplayer",false);
propertyInfo.SetValue(custom);
return true;
}
}
}

View File

@ -0,0 +1,32 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace NetworkNightmare.Framework
{
public enum MultiplayerPacket
{
ReadFarmerRoot,
UnusedByte1,
ReceivePlayerIntroduction,
ReadActiveLocation,
ReadWarp,
UnsedByte5,
ReadLocation,
ReadSpritesAtLocation,
WarpNPCS,
UnusedByte9,
ReceiveChatMessage,
UnusedByte11,
ReceiveWorldState,
ReceiveTeamDelta,
ReceiveNewDaySync,
ReceiveChatInfoMessage,
Unused16,
ReceiveFarmerGainExperience,
ParseServerToClientsMessage,
PlayerDisconnected
}
}

View File

@ -0,0 +1,65 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{27DAB9BB-92E0-4FC1-BC79-F513CE1F3262}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>NetworkNightmare</RootNamespace>
<AssemblyName>NetworkNightmare</AssemblyName>
<TargetFrameworkVersion>v4.6.1</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<NuGetPackageImportStamp>
</NuGetPackageImportStamp>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="System" />
<Reference Include="System.Core" />
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="Microsoft.CSharp" />
<Reference Include="System.Data" />
<Reference Include="System.Net.Http" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="Class1.cs" />
<Compile Include="Framework\CustomMultiplayer.cs" />
<Compile Include="Framework\MultiplayerPacket.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<None Include="manifest.json" />
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Analyzer Include="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\analyzers\dotnet\cs\StardewModdingAPI.ModBuildConfig.Analyzer.dll" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets" Condition="Exists('..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets')" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets'))" />
</Target>
</Project>

View File

@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("NetworkNightmare")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("NetworkNightmare")]
[assembly: AssemblyCopyright("Copyright © 2018")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]
// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("27dab9bb-92e0-4fc1-bc79-f513ce1f3262")]
// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

View File

@ -0,0 +1,10 @@
{
"Name": "Network Nightmare",
"Author": "Alpha_Omegasis",
"Version": "0.0.1",
"Description": "A dumb experiment.",
"UniqueID": "Omegasis.NetworkNightmare",
"EntryDll": "NetworkNightmare.dll",
"MinimumApiVersion": "2.0",
"UpdateKeys": [ "" ]
}

View File

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Pathoschild.Stardew.ModBuildConfig" version="2.1.0-beta-20180428" targetFramework="net461" />
</packages>

View File

@ -76,6 +76,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "DebugSandBoxAndReferences",
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AdditionalCropsFramework", "AdditionalCropsFramework\AdditionalCropsFramework.csproj", "{C5F88D48-EA20-40CD-91E2-C8725DC11795}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ModdedUtilitiesNetworking", "ModdedUtilitiesNetworking\ModdedUtilitiesNetworking.csproj", "{8DB124E3-E892-4E7C-A782-2DA47771338C}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@ -398,6 +400,18 @@ Global
{C5F88D48-EA20-40CD-91E2-C8725DC11795}.x86|Any CPU.Build.0 = x86|Any CPU
{C5F88D48-EA20-40CD-91E2-C8725DC11795}.x86|x86.ActiveCfg = x86|x86
{C5F88D48-EA20-40CD-91E2-C8725DC11795}.x86|x86.Build.0 = x86|x86
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Debug|x86.ActiveCfg = Debug|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Debug|x86.Build.0 = Debug|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Release|Any CPU.Build.0 = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Release|x86.ActiveCfg = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.Release|x86.Build.0 = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.x86|Any CPU.ActiveCfg = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.x86|Any CPU.Build.0 = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.x86|x86.ActiveCfg = Release|Any CPU
{8DB124E3-E892-4E7C-A782-2DA47771338C}.x86|x86.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE

View File

@ -168,8 +168,8 @@ namespace StardewSymphonyRemastered.Framework
var farm = (Farm)Game1.getLocationFromName("Farm");
foreach(var building in farm.buildings)
{
locations.Add(building.nameOfIndoors.Value);
StardewSymphony.ModMonitor.Log("Adding in song triggers for location: " + building.nameOfIndoors.Value);
locations.Add(building.nameOfIndoors);
StardewSymphony.ModMonitor.Log("Adding in song triggers for location: " + building.nameOfIndoors);
}
}
catch(Exception err)

View File

@ -223,7 +223,7 @@ namespace StardustCore.Serialization
foreach (Building building in Game1.getFarm().buildings)
{
GameLocation loc =Game1.getLocationFromName(building.nameOfIndoors.Value,true);
GameLocation loc =Game1.getLocationFromName(building.nameOfIndoors,true);
ModCore.ModMonitor.Log("Cleaning up farm building: "+loc.uniqueName.Value);
int i = loc.objects.Pairs.Count();
int j = 0;
@ -248,7 +248,7 @@ namespace StardustCore.Serialization
SerializerDataNode t;
if(acceptedTypes.ContainsKey((v as CoreObject).serializationName)){
acceptedTypes.TryGetValue((v as CoreObject).serializationName, out t);
string s = Path.Combine(building.nameOfIndoors.Value, "Chest,"+Convert.ToString( (int)obj.Key.X)+","+Convert.ToString((int)obj.Key.Y));
string s = Path.Combine(building.nameOfIndoors, "Chest,"+Convert.ToString( (int)obj.Key.X)+","+Convert.ToString((int)obj.Key.Y));
string s2 = Path.Combine(ModCore.SerializationManager.storageContainerPath, s);
if (!Directory.Exists(s)) Directory.CreateDirectory(s2);
t.serializeToContainer.Invoke(v, s2);

View File

@ -119,6 +119,7 @@
<ItemGroup>
<Analyzer Include="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\analyzers\dotnet\cs\StardewModdingAPI.ModBuildConfig.Analyzer.dll" />
</ItemGroup>
<ItemGroup />
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="$(SolutionDir)\deploy.targets" />
<Import Project="..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets" Condition="Exists('..\packages\Pathoschild.Stardew.ModBuildConfig.2.1.0-beta-20180428\build\Pathoschild.Stardew.ModBuildConfig.targets')" />