Modding:Migrate to Stardew Valley 1.3

From Stardew Valley Wiki
Revision as of 03:08, 20 April 2018 by Pathoschild (talk | contribs) (split Content Patcher and XNB updates to Modding:Migrate XNB changes to Stardew Valley 1.3)
Jump to navigation Jump to search

Index

This page is for modders. Players: see Modding:SMAPI compatibility instead. For updating Content Patcher or XNB mods, see Migrate XNB changes to Stardew Valley 1.3.

This page explains how to update your SMAPI mod code for compatibility with Stardew Valley 1.3.

SMAPI mods

Overview

At a high level, here's how to update a SMAPI mod:

  1. Update the mod build NuGet package to 2.1-beta. (You may need to enable the 'include prerelease' checkbox to see the beta.)
    This adds support for Stardew Valley 1.3, and adds code analysis which will report common problems in Stardew Valley 1.3 as compiler warnings.
  2. Rebuild your solution.
  3. Fix any compiler errors and warnings you see in the Error List pane in Visual Studio (or equivalent for other editors).
  4. See below for help with specific changes and warnings.
  5. Test all mod features to make sure they work.

That should take care of compatibility in single-player mode. The game will automatically synchronise most world changes to other players, but you might need further changes to work in multiplayer mode. Questions to consider: will your mod cause any problems if two players both have it installed? Do you have any custom objects/buildings/etc that might get synchronised to other players, and will that synchronisation work correctly? What if they have different configuration? Maybe it should only work for the main player? You can use SMAPI's Context.IsSinglePlayer and Context.IsMainPlayer flags in your logic to avoid conflicts.

If you need help updating your code, feel free to ask questions on the Stardew Valley Discord.

Net types

Stardew Valley 1.3 uses net types (like NetBool and NetInt) to handle multiplayer sync. These types can implicitly convert to their equivalent normal values (like bool x = new NetBool()), but their conversion rules are unintuitive and error-prone. For example, item?.category == null && item?.category != null can both be true at once, and building.indoors != null will be true for a null value in some cases. With the mod build config package installed, rebuild the project and look for warnings in the Error List pane like this:

'{{expression}}' is a {{net type}} field; consider using the {{property name}} property instead. See https://smapi.io/buildmsg/smapi002 for details.

This implicitly converts '{{expression}}' from {{net type}} to {{other type}}, but {{net type}} has unintuitive implicit conversion rules. Consider comparing against the actual value instead to avoid bugs. See https://smapi.io/buildmsg/smapi001 for details.

Suggested fix:

  • Some net fields have an equivalent non-net property, like monster.Health (int) instead of monster.health (NetBool). The mod build package will add a SMAPI002 warning which says which property to use instead.
  • For a reference type (i.e. one that can contain null), you can use the .Value property (or .FieldDict for a NetDictionary):
    if (building.indoors.Value == null)
    

    Or convert the value before comparison:

    GameLocation indoors = building.indoors;
    if(indoors == null)
       // ...
    
  • For a value type (i.e. one that can't contain null), check if the object is null (if applicable) and compare with .Value:
    if (item != null && item.category.Value == 0)
    

Game1.player.friendships

This field is always null in Stardew Valley 1.3. Use the new Game1.player.friendshipData field instead, which wraps the raw data with a model.

Texture constructor arguments

Many constructors which previously accepted Texture2D texture arguments now take a string textureName argument instead. It's usually better to use SMAPI's content API to override textures instead. You can change the cached texture after the object is constructed (may need reflection), but don't change the texture name to avoid multiplayer sync issues.

Common compiler warnings

Make sure you check your Error List pane in Visual Studio (or equivalent in other IDEs) and fix any warnings. Here are some common ones:

  • "There was a mismatch between the processor architecture of the project being built "{0}" and the processor architecture of the reference "{1}". This mismatch may cause runtime failures."
    That warning is normal. The error is saying that your build is set to 'Any CPU', but Stardew Valley is x86-only so it'll only work in x86 anyway. You can either ignore it, or change your platform target to x86.
  • "This implicitly converts '{0}' from {1} to {2}, but {1} has unintuitive implicit conversion rules. Consider comparing against the actual value instead to avoid bugs. See https://smapi.io/buildmsg/smapi001 for details."
    See #Net types.
  • "The '{0}' field is obsolete and should be replaced with '{1}'. See https://smapi.io/buildmsg/smapi003 for details."
    You're referencing a field which should no longer be used. Just use the suggested field name instead to fix it.