(f2e516dfe) v0.9.3.2

This commit is contained in:
Joonas Rikkonen
2019-09-20 20:11:18 +03:00
parent 80698b58b0
commit 9aa12bcac2
144 changed files with 1653 additions and 1559 deletions
@@ -105,15 +105,15 @@ namespace Barotrauma
switch ((NetEntityEvent.Type)extraData[0])
{
case NetEntityEvent.Type.InventoryState:
msg.WriteRangedIntegerDeprecated(0, 3, 0);
msg.WriteRangedInteger(0, 0, 3);
Inventory.ClientWrite(msg, extraData);
break;
case NetEntityEvent.Type.Treatment:
msg.WriteRangedIntegerDeprecated(0, 3, 1);
msg.WriteRangedInteger(1, 0, 3);
msg.Write(AnimController.Anim == AnimController.Animation.CPR);
break;
case NetEntityEvent.Type.Status:
msg.WriteRangedIntegerDeprecated(0, 3, 2);
msg.WriteRangedInteger(2, 0, 3);
break;
}
}
@@ -131,7 +131,7 @@ namespace Barotrauma
msg.Write(inputCount);
for (int i = 0; i < inputCount; i++)
{
msg.WriteRangedIntegerDeprecated(0, (int)InputNetFlags.MaxVal, (int)memInput[i].states);
msg.WriteRangedInteger((int)memInput[i].states, 0, (int)InputNetFlags.MaxVal);
msg.Write(memInput[i].intAim);
if (memInput[i].states.HasFlag(InputNetFlags.Select) ||
memInput[i].states.HasFlag(InputNetFlags.Deselect) ||
@@ -283,9 +283,16 @@ namespace Barotrauma
case 0:
if (Inventory == null)
{
string errorMsg = "Received an inventory update message for an entity with no inventory (" + Name + ")";
string errorMsg = "Received an inventory update message for an entity with no inventory (" + Name + ", removed: " + Removed + ")";
DebugConsole.ThrowError(errorMsg);
GameAnalyticsManager.AddErrorEventOnce("CharacterNetworking.ClientRead:NoInventory" + ID, GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
//read anyway to prevent messing up reading the rest of the message
byte itemCount = msg.ReadByte();
for (int i = 0; i < itemCount; i++)
{
msg.ReadUInt16();
}
}
else
{
@@ -337,7 +344,7 @@ namespace Barotrauma
public static Character ReadSpawnData(IReadMessage inc, bool spawn = true)
{
DebugConsole.NewMessage("READING CHARACTER SPAWN DATA", Color.Cyan);
DebugConsole.Log("Reading character spawn data");
if (GameMain.Client == null) return null;
@@ -433,7 +440,16 @@ namespace Barotrauma
if (causeOfDeathType == CauseOfDeathType.Affliction)
{
int afflictionIndex = msg.ReadRangedInteger(0, AfflictionPrefab.List.Count - 1);
causeOfDeathAffliction = AfflictionPrefab.List[afflictionIndex];
if (afflictionIndex < 0 || afflictionIndex >= AfflictionPrefab.List.Count)
{
string errorMsg = $"Error in CharacterNetworking.ReadStatus: affliction index out of bounds (index: {afflictionIndex}, affliction count: {AfflictionPrefab.List.Count})";
causeOfDeathType = CauseOfDeathType.Unknown;
GameAnalyticsManager.AddErrorEventOnce("CharacterNetworking.ReadStatus:AfflictionIndexOutOfBounts", GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
}
else
{
causeOfDeathAffliction = AfflictionPrefab.List[afflictionIndex];
}
}
byte severedLimbCount = msg.ReadByte();
@@ -452,13 +468,20 @@ namespace Barotrauma
for (int i = 0; i < severedLimbCount; i++)
{
int severedJointIndex = msg.ReadByte();
AnimController.SeverLimbJoint(AnimController.LimbJoints[severedJointIndex]);
if (severedJointIndex < 0 || severedJointIndex >= AnimController.LimbJoints.Length)
{
string errorMsg = $"Error in CharacterNetworking.ReadStatus: severed joint index out of bounds (index: {severedJointIndex}, joint count: {AnimController.LimbJoints.Length})";
GameAnalyticsManager.AddErrorEventOnce("CharacterNetworking.ReadStatus:JointIndexOutOfBounts", GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
}
else
{
AnimController.SeverLimbJoint(AnimController.LimbJoints[severedJointIndex]);
}
}
}
else
{
if (IsDead) Revive();
if (IsDead) { Revive(); }
CharacterHealth.ClientRead(msg);
}
}
@@ -1359,7 +1359,7 @@ namespace Barotrauma
}
ShowQuestionPrompt("Permission to grant to client #" + id + "?", (perm) =>
{
GameMain.Client.SendConsoleCommand("giveperm " + id + " " + perm);
GameMain.Client?.SendConsoleCommand("giveperm " + id + " " + perm);
});
}
);
@@ -1384,7 +1384,7 @@ namespace Barotrauma
ShowQuestionPrompt("Permission to revoke from client #" + id + "?", (perm) =>
{
GameMain.Client.SendConsoleCommand("revokeperm " + id + " " + perm);
GameMain.Client?.SendConsoleCommand("revokeperm " + id + " " + perm);
});
}
);
@@ -1408,7 +1408,7 @@ namespace Barotrauma
}
ShowQuestionPrompt("Rank to grant to client #" + id + "?", (rank) =>
{
GameMain.Client.SendConsoleCommand("giverank " + id + " " + rank);
GameMain.Client?.SendConsoleCommand("giverank " + id + " " + rank);
});
}
);
@@ -1427,7 +1427,7 @@ namespace Barotrauma
ShowQuestionPrompt("Console command permissions to grant to client #" + id + "? You may enter multiple commands separated with a space.", (commandNames) =>
{
GameMain.Client.SendConsoleCommand("givecommandperm " + id + " " + commandNames);
GameMain.Client?.SendConsoleCommand("givecommandperm " + id + " " + commandNames);
});
}
);
@@ -1446,7 +1446,7 @@ namespace Barotrauma
ShowQuestionPrompt("Console command permissions to revoke from client #" + id + "? You may enter multiple commands separated with a space.", (commandNames) =>
{
GameMain.Client.SendConsoleCommand("revokecommandperm " + id + " " + commandNames);
GameMain.Client?.SendConsoleCommand("revokecommandperm " + id + " " + commandNames);
});
}
);
@@ -1487,7 +1487,7 @@ namespace Barotrauma
banDuration = parsedBanDuration;
}
GameMain.Client.SendConsoleCommand(
GameMain.Client?.SendConsoleCommand(
"banendpoint " +
args[0] + " " +
(banDuration.HasValue ? banDuration.Value.TotalSeconds.ToString() : "0") + " " +
@@ -1538,7 +1538,7 @@ namespace Barotrauma
NewMessage("Index out of bounds!", Color.Red);
return;
}
GameMain.Client.SendConsoleCommand("campaigndestination " + destinationIndex);
GameMain.Client?.SendConsoleCommand("campaigndestination " + destinationIndex);
});
}
else
@@ -32,6 +32,12 @@ namespace Barotrauma
private set;
}
public bool IsCJK
{
get;
private set;
}
public uint Size
{
get
@@ -58,11 +64,16 @@ namespace Barotrauma
}
public ScalableFont(XElement element, GraphicsDevice gd = null)
: this (element.GetAttributeString("file", ""), (uint)element.GetAttributeInt("size", 14), gd, element.GetAttributeBool("dynamicloading", false))
{
: this(
element.GetAttributeString("file", ""),
(uint)element.GetAttributeInt("size", 14),
gd,
element.GetAttributeBool("dynamicloading", false),
element.GetAttributeBool("iscjk", false))
{
}
public ScalableFont(string filename, uint size, GraphicsDevice gd = null, bool dynamicLoading = false)
public ScalableFont(string filename, uint size, GraphicsDevice gd = null, bool dynamicLoading = false, bool isCJK = false)
{
lock (mutex)
{
@@ -85,6 +96,7 @@ namespace Barotrauma
this.textures = new List<Texture2D>();
this.texCoords = new Dictionary<uint, GlyphData>();
this.DynamicLoading = dynamicLoading;
this.IsCJK = isCJK;
this.graphicsDevice = gd;
if (gd != null && !dynamicLoading)
+11 -3
View File
@@ -83,6 +83,7 @@ namespace Barotrauma
public static ScalableFont VideoTitleFont => Style?.VideoTitleFont;
public static ScalableFont ObjectiveTitleFont => Style?.ObjectiveTitleFont;
public static ScalableFont ObjectiveNameFont => Style?.ObjectiveNameFont;
public static ScalableFont CJKFont { get; private set; }
public static UISprite UIGlow => Style.UIGlow;
@@ -154,6 +155,7 @@ namespace Barotrauma
{
GUI.graphicsDevice = graphicsDevice;
var uiStyles = ContentPackage.GetFilesOfType(selectedContentPackages, ContentType.UIStyle).ToList();
if (uiStyles.Count == 0)
{
DebugConsole.ThrowError("No UI styles defined in the selected content package!");
@@ -165,6 +167,11 @@ namespace Barotrauma
}
Style = new GUIStyle(uiStyles[0], graphicsDevice);
if (CJKFont == null)
{
CJKFont = new ScalableFont("Content/Fonts/NotoSans/NotoSansCJKsc-Bold.otf",
Font.Size, graphicsDevice, dynamicLoading: true, isCJK: true);
}
}
public static void LoadContent(bool loadSounds = true)
@@ -408,7 +415,7 @@ namespace Barotrauma
if (Character.Controlled?.Inventory != null)
{
if (!Character.Controlled.LockHands && Character.Controlled.Stun >= -0.1f && !Character.Controlled.IsDead)
if (!Character.Controlled.LockHands && Character.Controlled.Stun < 0.1f && !Character.Controlled.IsDead)
{
Inventory.DrawFront(spriteBatch);
}
@@ -1563,9 +1570,10 @@ namespace Barotrauma
button.OnClicked += (btn, userData) =>
{
var quitButton = button;
if (GameMain.GameSession != null)
if (GameMain.GameSession != null || (Screen.Selected is CharacterEditorScreen charEditScreen || Screen.Selected is SubEditorScreen subEditScreen))
{
var msgBox = new GUIMessageBox("", TextManager.Get("PauseMenuQuitVerification"), new string[] { TextManager.Get("Yes"), TextManager.Get("Cancel") })
string text = GameMain.GameSession == null ? "PauseMenuQuitVerificationEditor" : "PauseMenuQuitVerification";
var msgBox = new GUIMessageBox("", TextManager.Get(text), new string[] { TextManager.Get("Yes"), TextManager.Get("Cancel") })
{
UserData = "verificationprompt"
};
@@ -188,7 +188,7 @@ namespace Barotrauma
{
if (!Visible) return;
base.Update(deltaTime);
if (Rect.Contains(PlayerInput.MousePosition) && CanBeSelected && Enabled && GUI.IsMouseOn(this))
if (Rect.Contains(PlayerInput.MousePosition) && CanBeSelected && CanBeFocused && Enabled && GUI.IsMouseOn(this))
{
state = ComponentState.Hover;
if (PlayerInput.LeftButtonDown())
@@ -22,10 +22,9 @@ namespace Barotrauma
public GUIScrollBar ScrollBar { get; private set; }
public GUIFrame Content { get; private set; }
private Dictionary<GUIComponent, bool> childVisible = new Dictionary<GUIComponent, bool>();
private int totalSize;
private int spacing;
private bool childrenNeedsRecalculation;
private bool scrollBarNeedsRecalculation;
@@ -95,11 +94,7 @@ namespace Barotrauma
get { return totalSize; }
}
public int Spacing
{
get { return spacing; }
set { spacing = value; }
}
public int Spacing { get; set; }
public override Color Color
{
@@ -244,37 +239,37 @@ namespace Barotrauma
{
if (ScrollBar.IsHorizontal)
{
if (y + child.Rect.Height + spacing > Content.Rect.Height)
if (y + child.Rect.Height + Spacing > Content.Rect.Height)
{
y = 0;
x += child.Rect.Width + spacing;
x += child.Rect.Width + Spacing;
if (child.RectTransform.AbsoluteOffset.X != x || child.RectTransform.AbsoluteOffset.Y != y)
{
child.RectTransform.AbsoluteOffset = new Point(x, y);
}
y += child.Rect.Height + spacing;
y += child.Rect.Height + Spacing;
}
else
{
y += child.Rect.Height + spacing;
y += child.Rect.Height + Spacing;
}
}
else
{
if (x + child.Rect.Width + spacing > Content.Rect.Width)
if (x + child.Rect.Width + Spacing > Content.Rect.Width)
{
x = 0;
y += child.Rect.Height + spacing;
y += child.Rect.Height + Spacing;
if (child.RectTransform.AbsoluteOffset.X != x || child.RectTransform.AbsoluteOffset.Y != y)
{
child.RectTransform.AbsoluteOffset = new Point(x, y);
}
x += child.Rect.Width + spacing;
x += child.Rect.Width + Spacing;
}
else
{
x += child.Rect.Width + spacing;
x += child.Rect.Width + Spacing;
}
}
}
@@ -282,11 +277,11 @@ namespace Barotrauma
{
if (ScrollBar.IsHorizontal)
{
x += child.Rect.Width + spacing;
x += child.Rect.Width + Spacing;
}
else
{
y += child.Rect.Height + spacing;
y += child.Rect.Height + Spacing;
}
}
}
@@ -327,10 +322,23 @@ namespace Barotrauma
public override void AddToGUIUpdateList(bool ignoreChildren = false, int order = 0)
{
if (!Visible) { return; }
foreach (GUIComponent child in Content.Children)
{
if (!childVisible.ContainsKey(child)) { childVisible[child] = child.Visible; }
if (childVisible[child] != child.Visible)
{
childVisible[child] = child.Visible;
childrenNeedsRecalculation = true;
scrollBarNeedsRecalculation = true;
break;
}
}
if (childrenNeedsRecalculation)
{
RecalculateChildren();
childVisible.Clear();
}
UpdateOrder = order;
@@ -511,30 +519,30 @@ namespace Barotrauma
{
if (ScrollBar.IsHorizontal)
{
if (pos + child.Rect.Height + spacing > Content.Rect.Height)
if (pos + child.Rect.Height + Spacing > Content.Rect.Height)
{
pos = 0;
totalSize += child.Rect.Width + spacing;
totalSize += child.Rect.Width + Spacing;
}
pos += child.Rect.Height + spacing;
pos += child.Rect.Height + Spacing;
if (child == children.Last())
{
totalSize += child.Rect.Width + spacing;
totalSize += child.Rect.Width + Spacing;
}
}
else
{
if (pos + child.Rect.Width + spacing > Content.Rect.Width)
if (pos + child.Rect.Width + Spacing > Content.Rect.Width)
{
pos = 0;
totalSize += child.Rect.Height + spacing;
totalSize += child.Rect.Height + Spacing;
}
pos += child.Rect.Width + spacing;
pos += child.Rect.Width + Spacing;
if (child == children.Last())
{
totalSize += child.Rect.Height + spacing;
totalSize += child.Rect.Height + Spacing;
}
}
}
@@ -545,7 +553,7 @@ namespace Barotrauma
{
totalSize += (ScrollBar.IsHorizontal) ? child.Rect.Width : child.Rect.Height;
}
totalSize += Content.CountChildren * spacing;
totalSize += Content.CountChildren * Spacing;
}
@@ -56,7 +56,21 @@ namespace Barotrauma
{
if (!Visible) return;
if (ProgressGetter != null) BarSize = ProgressGetter();
if (ProgressGetter != null)
{
float newSize = MathHelper.Clamp(ProgressGetter(), 0.0f, 1.0f);
if (!MathUtils.IsValid(newSize))
{
GameAnalyticsManager.AddErrorEventOnce(
"GUIProgressBar.Draw:GetProgress",
GameAnalyticsSDK.Net.EGAErrorSeverity.Error,
"ProgressGetter of a GUIProgressBar (" + ProgressGetter.Target.ToString() + " - " + ProgressGetter.Method.ToString() + ") returned an invalid value (" + newSize + ")\n" + Environment.StackTrace);
}
else
{
BarSize = newSize;
}
}
Rectangle sliderRect = new Rectangle(
frame.Rect.X,
@@ -155,7 +155,8 @@ namespace Barotrauma
string file = GetFontFilePath(element);
uint size = GetFontSize(element);
bool dynamicLoading = GetFontDynamicLoading(element);
return new ScalableFont(file, size, graphicsDevice, dynamicLoading);
bool isCJK = GetIsCJK(element);
return new ScalableFont(file, size, graphicsDevice, dynamicLoading, isCJK);
}
private uint GetFontSize(XElement element)
@@ -200,6 +201,20 @@ namespace Barotrauma
return element.GetAttributeBool("dynamicloading", false);
}
private bool GetIsCJK(XElement element)
{
foreach (XElement subElement in element.Elements())
{
if (subElement.Name.ToString().ToLowerInvariant() != "override") { continue; }
string language = subElement.GetAttributeString("language", "").ToLowerInvariant();
if (GameMain.Config.Language.ToLowerInvariant() == language)
{
return subElement.GetAttributeBool("iscjk", false);
}
}
return element.GetAttributeBool("iscjk", false);
}
public GUIComponentStyle GetComponentStyle(string name)
{
componentStyles.TryGetValue(name.ToLowerInvariant(), out GUIComponentStyle style);
@@ -204,8 +204,13 @@ namespace Barotrauma
if (textColor.HasValue)
{
this.textColor = textColor.Value;
}
this.Font = font ?? GUI.Font;
}
//if the text is in chinese/korean/japanese and we're not using a CJK-compatible font,
//use the default CJK font as a fallback
var selectedFont = font ?? GUI.Font;
if (TextManager.IsCJK(text) && !selectedFont.IsCJK) { selectedFont = GUI.CJKFont; }
this.Font = selectedFont;
this.textAlignment = textAlignment;
this.Wrap = wrap;
this.Text = text ?? "";
@@ -190,7 +190,8 @@ namespace Barotrauma
{
if (Character.Controlled == null || Character.Controlled.SpeechImpediment >= 100.0f) { return false; }
SetCharacterOrder(null, order, null, Character.Controlled);
foreach (var hull in Character.Controlled.GetVisibleHulls())
var visibleHulls = new List<Hull>(Character.Controlled.GetVisibleHulls());
foreach (var hull in visibleHulls)
{
HumanAIController.PropagateHullSafety(Character.Controlled, hull);
HumanAIController.RefreshTargets(Character.Controlled, order, hull);
@@ -199,6 +199,7 @@ namespace Barotrauma.Tutorials
SetHighlight(captain_navConsole.Item, true);
SetHighlight(captain_sonar.Item, true);
SetHighlight(captain_statusMonitor, true);
captain_navConsole.UseAutoDocking = false;
do
{
//captain_navConsoleCustomInterface.HighlightElement(0, uiHighlightColor, duration: 1.0f, pulsateAmount: 0.0f);
@@ -221,6 +222,7 @@ namespace Barotrauma.Tutorials
} while (captain_sonar.CurrentMode != Sonar.Mode.Active);
do { yield return null; } while (Vector2.Distance(Submarine.MainSub.WorldPosition, Level.Loaded.EndPosition) > 4000f);
RemoveCompletedObjective(segments[5]);
captain_navConsole.UseAutoDocking = true;
yield return new WaitForSeconds(4f, false);
TriggerTutorialSegment(6); // Docking
do
@@ -256,6 +256,7 @@ namespace Barotrauma.Tutorials
GameMain.GameSession.CrewManager.AddCharacter(doctor);
GameMain.GameSession.CrewManager.AddCharacter(patient1);
GameMain.GameSession.CrewManager.ToggleCrewAreaOpen = true;
patient1.CharacterHealth.UseHealthWindow = false;
yield return new WaitForSeconds(3.0f, false);
patient1.AIController.Enabled = true;
@@ -277,6 +278,7 @@ namespace Barotrauma.Tutorials
RemoveCompletedObjective(segments[3]);
SetHighlight(doctor_medBayCabinet.Item, true);
SetDoorAccess(doctor_thirdDoor, doctor_thirdDoorLight, true);
patient1.CharacterHealth.UseHealthWindow = true;
yield return new WaitForSeconds(2.0f, false);
@@ -169,7 +169,9 @@ namespace Barotrauma.Tutorials
}
engineer_wire_1 = Item.ItemList.Find(i => i.HasTag("engineer_wire_1"));
engineer_wire_1.SpriteColor = Color.Transparent;
engineer_wire_2 = Item.ItemList.Find(i => i.HasTag("engineer_wire_2"));
engineer_wire_2.SpriteColor = Color.Transparent;
engineer_lamp_1 = Item.ItemList.Find(i => i.HasTag("engineer_lamp_1")).GetComponent<Powered>();
engineer_lamp_2 = Item.ItemList.Find(i => i.HasTag("engineer_lamp_2")).GetComponent<Powered>();
engineer_fourthDoor = Item.ItemList.Find(i => i.HasTag("engineer_fourthdoor")).GetComponent<Door>();
@@ -416,6 +418,8 @@ namespace Barotrauma.Tutorials
do { CheckJunctionBoxHighlights(); yield return null; } while (!engineer_submarineJunctionBox_1.IsFullCondition || !engineer_submarineJunctionBox_2.IsFullCondition || !engineer_submarineJunctionBox_3.IsFullCondition);
CheckJunctionBoxHighlights();
RemoveCompletedObjective(segments[4]);
yield return new WaitForSeconds(2f, false);
TriggerTutorialSegment(5); // Powerup reactor
SetHighlight(engineer_submarineReactor.Item, true);
engineer.AddActiveObjectiveEntity(engineer_submarineReactor.Item, engineer_reactorIcon, engineer_reactorIconColor);
@@ -425,6 +429,8 @@ namespace Barotrauma.Tutorials
RemoveCompletedObjective(segments[5]);
GameMain.GameSession.CrewManager.AddSinglePlayerChatMessage(radioSpeakerName, TextManager.Get("Engineer.Radio.Complete"), ChatMessageType.Radio, null);
yield return new WaitForSeconds(4f, false);
CoroutineManager.StartCoroutine(TutorialCompleted());
}
@@ -472,17 +478,31 @@ namespace Barotrauma.Tutorials
private void CheckGhostWires()
{
if (engineer_wire_1 != null && engineer_lamp_1.Voltage > engineer_lamp_1.MinVoltage)
Color wireColor =
Color.Orange *
MathHelper.Lerp(0.25f, 0.75f, (float)(Math.Sin((Timing.TotalTime * 4.0f)) + 1.0f) / 2.0f);
if (engineer_wire_1 != null)
{
engineer_wire_1.Remove();
engineer_wire_1 = null;
engineer_wire_1.SpriteColor = wireColor;
if (engineer_lamp_1.Voltage > engineer_lamp_1.MinVoltage)
{
engineer_wire_1.Remove();
engineer_wire_1 = null;
}
}
if (engineer_wire_2 != null && engineer_lamp_2.Voltage > engineer_lamp_2.MinVoltage)
if (engineer_wire_2 != null)
{
engineer_wire_2.Remove();
engineer_wire_2 = null;
engineer_wire_2.SpriteColor = wireColor;
if (engineer_lamp_2.Voltage > engineer_lamp_2.MinVoltage)
{
engineer_wire_2.Remove();
engineer_wire_2 = null;
}
}
}
private void HandleJunctionBoxWiringHighlights()
@@ -526,6 +526,8 @@ namespace Barotrauma.Tutorials
mechanic.AddActiveObjectiveEntity(mechanic_brokenWall_2, mechanic_weldIcon, mechanic_repairIconColor);
do { yield return null; } while (WallHasDamagedSections(mechanic_brokenWall_2));
mechanic.RemoveActiveObjectiveEntity(mechanic_brokenWall_2);
yield return new WaitForSeconds(2f, false);
TriggerTutorialSegment(9, GameMain.Config.KeyBind(InputType.Use)); // Repairing machinery (pump)
SetHighlight(mechanic_brokenPump.Item, true);
mechanic_brokenPump.CanBeSelected = true;
@@ -373,7 +373,7 @@ namespace Barotrauma.Tutorials
HighlightInventorySlot(officer.Inventory, "harpoongun", highlightColor, 0.5f, 0.5f, 0f);
}
yield return null;
} while (!harpoonGunChamber.Inventory.IsFull()); // Wait until all five harpons loaded
} while (!harpoonGunChamber.Inventory.IsFull()); // Wait until all six harpoons loaded
RemoveCompletedObjective(segments[5]);
SetHighlight(officer_rangedWeaponCabinet.Item, false);
SetDoorAccess(officer_fourthDoor, officer_fourthDoorLight, true);
@@ -113,8 +113,8 @@ namespace Barotrauma
var tickBox = new GUITickBox(new RectTransform(tickBoxScale, contentPackageList.Content.RectTransform, scaleBasis: ScaleBasis.BothHeight), contentPackage.Name)
{
UserData = contentPackage,
OnSelected = SelectContentPackage,
Selected = SelectedContentPackages.Contains(contentPackage)
Selected = SelectedContentPackages.Contains(contentPackage),
OnSelected = SelectContentPackage
};
if (contentPackage.CorePackage)
{
@@ -153,11 +153,6 @@ namespace Barotrauma
UnsavedSettings = true;
var msgBox = new GUIMessageBox(TextManager.Get("RestartRequiredLabel"), TextManager.Get("RestartRequiredLanguage"));
//change fonts to the default font of the new language to make sure
//they can be displayed when for example changing from English to Chinese
var defaultFont = GUI.Style.LoadCurrentDefaultFont();
msgBox.Header.Font = defaultFont;
msgBox.Text.Font = defaultFont;
return true;
};
@@ -445,17 +440,11 @@ namespace Barotrauma
};
voiceChatScrollBar.OnMoved(voiceChatScrollBar, voiceChatScrollBar.BarScroll);
var leftTickBoxes = new GUILayoutGroup(new RectTransform(new Vector2(0.28f, 0.06f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopLeft)
{ RelativeOffset = new Vector2(0.02f, 0.32f) })
{ RelativeSpacing = 0.01f };
var centerTickBoxes = new GUILayoutGroup(new RectTransform(new Vector2(0.4f, 0.06f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopLeft)
{ RelativeOffset = new Vector2(0.3f, 0.32f) })
{ RelativeSpacing = 0.01f };
var rightTickBoxes = new GUILayoutGroup(new RectTransform(new Vector2(0.3f, 0.06f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopRight)
var tickBoxes = new GUILayoutGroup(new RectTransform(new Vector2(0.28f, 0.15f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopLeft)
{ RelativeOffset = new Vector2(0.02f, 0.32f) })
{ RelativeSpacing = 0.01f };
GUITickBox muteOnFocusLostBox = new GUITickBox(new RectTransform(tickBoxScale / 0.06f, leftTickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("MuteOnFocusLost"));
GUITickBox muteOnFocusLostBox = new GUITickBox(new RectTransform(tickBoxScale / 0.18f, tickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("MuteOnFocusLost"));
muteOnFocusLostBox.Selected = MuteOnFocusLost;
muteOnFocusLostBox.ToolTip = TextManager.Get("MuteOnFocusLostToolTip");
muteOnFocusLostBox.OnSelected = (tickBox) =>
@@ -465,7 +454,7 @@ namespace Barotrauma
return true;
};
GUITickBox dynamicRangeCompressionTickBox = new GUITickBox(new RectTransform(tickBoxScale / 0.06f, centerTickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("DynamicRangeCompression"));
GUITickBox dynamicRangeCompressionTickBox = new GUITickBox(new RectTransform(tickBoxScale / 0.18f, tickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("DynamicRangeCompression"));
dynamicRangeCompressionTickBox.Selected = DynamicRangeCompressionEnabled;
dynamicRangeCompressionTickBox.ToolTip = TextManager.Get("DynamicRangeCompressionToolTip");
dynamicRangeCompressionTickBox.OnSelected = (tickBox) =>
@@ -475,7 +464,7 @@ namespace Barotrauma
return true;
};
GUITickBox voipAttenuationTickBox = new GUITickBox(new RectTransform(tickBoxScale / 0.06f, rightTickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("VoipAttenuation"));
GUITickBox voipAttenuationTickBox = new GUITickBox(new RectTransform(tickBoxScale / 0.18f, tickBoxes.RectTransform, scaleBasis: ScaleBasis.BothHeight), TextManager.Get("VoipAttenuation"));
voipAttenuationTickBox.Selected = VoipAttenuationEnabled;
voipAttenuationTickBox.ToolTip = TextManager.Get("VoipAttenuationToolTip");
voipAttenuationTickBox.OnSelected = (tickBox) =>
@@ -485,8 +474,8 @@ namespace Barotrauma
return true;
};
var voipSettings = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.4f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopCenter)
{ RelativeOffset = new Vector2(0.0f, 0.38f) })
var voipSettings = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.35f), tabs[(int)Tab.Audio].RectTransform, Anchor.TopCenter)
{ RelativeOffset = new Vector2(0.0f, 0.47f) })
{ RelativeSpacing = 0.01f };
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.15f), voipSettings.RectTransform), TextManager.Get("VoiceChat"));
@@ -631,18 +620,21 @@ namespace Barotrauma
var dbMeter = new GUIProgressBar(new RectTransform(new Vector2(1.0f, 0.25f), voiceActivityGroup.RectTransform), 0.0f, Color.Lime);
dbMeter.ProgressGetter = () =>
{
if (VoipCapture.Instance == null) return 0.0f;
if (VoipCapture.Instance == null) { return 0.0f; }
dbMeter.Color = VoipCapture.Instance.LastdB > NoiseGateThreshold ? Color.Lime : Color.Orange; //TODO: i'm a filthy hack
return ((float)VoipCapture.Instance.LastdB + 100.0f) / 100.0f;
float scrollVal = double.IsNegativeInfinity(VoipCapture.Instance.LastdB) ? 0.0f : ((float)VoipCapture.Instance.LastdB + 100.0f) / 100.0f;
return scrollVal * scrollVal;
};
var noiseGateSlider = new GUIScrollBar(new RectTransform(Vector2.One, dbMeter.RectTransform, Anchor.Center), color: Color.White, barSize: 0.03f);
noiseGateSlider.Frame.Visible = false;
noiseGateSlider.Step = 0.01f;
noiseGateSlider.Range = new Vector2(-100.0f, 0.0f);
noiseGateSlider.BarScrollValue = NoiseGateThreshold;
noiseGateSlider.BarScroll = MathUtils.InverseLerp(-1.0f, 0.0f, NoiseGateThreshold);
noiseGateSlider.BarScroll *= noiseGateSlider.BarScroll;
noiseGateSlider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
NoiseGateThreshold = scrollBar.BarScrollValue;
NoiseGateThreshold = MathHelper.Lerp(-100.0f, 0.0f, (float)Math.Sqrt(scrollBar.BarScroll));
UnsavedSettings = true;
return true;
};
@@ -1018,6 +1010,7 @@ namespace Barotrauma
SelectedContentPackages.Remove(contentPackage);
}
}
if (contentPackage.GetFilesOfType(ContentType.Submarine).Any()) { Submarine.RefreshSavedSubs(); }
UnsavedSettings = true;
return true;
}
@@ -126,6 +126,7 @@ namespace Barotrauma
public override void RemoveItem(Item item)
{
if (!Items.Contains(item)) { return; }
base.RemoveItem(item);
CreateSlots();
}
@@ -175,7 +176,12 @@ namespace Barotrauma
AssignQuickUseNumKeys();
highlightedSubInventorySlots.Clear();
highlightedSubInventorySlots.RemoveWhere(s => s.Inventory.OpenState <= 0.0f);
foreach (var subSlot in highlightedSubInventorySlots)
{
subSlot.Slot = slots[subSlot.SlotIndex];
}
//highlightedSubInventorySlots.Clear();
screenResolution = new Point(GameMain.GraphicsWidth, GameMain.GraphicsHeight);
CalculateBackgroundFrame();
@@ -469,6 +475,7 @@ namespace Barotrauma
}
List<SlotReference> hideSubInventories = new List<SlotReference>();
highlightedSubInventorySlots.RemoveWhere(s => s.SlotIndex < 0 || s.SlotIndex >= Items.Length || Items[s.SlotIndex] == null);
foreach (var highlightedSubInventorySlot in highlightedSubInventorySlots)
{
if (highlightedSubInventorySlot.ParentInventory == this)
@@ -646,7 +653,10 @@ namespace Barotrauma
}
}
slotRef.Inventory.OpenState = isEquippedSubInventory ? 1f : 0f; // Reset animation when initially equipped
if (isEquippedSubInventory)
{
slotRef.Inventory.OpenState = 1.0f; // Reset animation when initially equipped
}
highlightedSubInventorySlots.Add(slotRef);
slotRef.Inventory.HideTimer = 1f;
@@ -146,14 +146,24 @@ namespace Barotrauma.Items.Components
if (item.body == null)
{
transformedItemPos = new Vector2(item.Rect.X, item.Rect.Y);
if (item.Submarine != null) transformedItemPos += item.Submarine.DrawPosition;
transformedItemPos = transformedItemPos + ItemPos * item.Scale;
if (item.FlippedX)
{
transformedItemPos.X = -transformedItemPos.X;
transformedItemPos.X += item.Rect.Width;
transformedItemInterval.X = -transformedItemInterval.X;
}
if (item.FlippedY)
{
transformedItemPos.Y = -transformedItemPos.Y;
transformedItemPos.Y -= item.Rect.Height;
transformedItemInterval.Y = -transformedItemInterval.Y;
}
transformedItemPos += new Vector2(item.Rect.X, item.Rect.Y);
if (item.Submarine != null) { transformedItemPos += item.Submarine.DrawPosition; }
}
else
{
Matrix transform = Matrix.CreateRotationZ(item.body.Rotation);
if (item.body.Dir == -1.0f)
{
transformedItemPos.X = -transformedItemPos.X;
@@ -169,6 +179,10 @@ namespace Barotrauma.Items.Components
Vector2 currentItemPos = transformedItemPos;
SpriteEffects spriteEffects = SpriteEffects.None;
if ((item.body != null && item.body.Dir == -1) || item.FlippedX) { spriteEffects |= SpriteEffects.FlipHorizontally; }
if (item.FlippedY) { spriteEffects |= SpriteEffects.FlipVertically; }
int i = 0;
foreach (Item containedItem in Inventory.Items)
{
@@ -192,7 +206,7 @@ namespace Barotrauma.Items.Components
containedItem.GetSpriteColor(),
-currentRotation,
containedItem.Scale,
(item.body != null && item.body.Dir == -1) ? SpriteEffects.FlipHorizontally : SpriteEffects.None,
spriteEffects,
depth: ContainedSpriteDepth < 0.0f ? containedItem.Sprite.Depth : ContainedSpriteDepth);
foreach (ItemContainer ic in containedItem.GetComponents<ItemContainer>())
@@ -1,4 +1,5 @@
using Microsoft.Xna.Framework.Graphics;
using Barotrauma.Networking;
using Microsoft.Xna.Framework.Graphics;
namespace Barotrauma.Items.Components
{
@@ -72,5 +73,10 @@ namespace Barotrauma.Items.Components
GameMain.Client.ChatBox.ToggleOpen = value;
}
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
{
state = msg.ReadBoolean();
}
}
}
@@ -136,7 +136,7 @@ namespace Barotrauma.Items.Components
public void ClientWrite(IWriteMessage msg, object[] extraData = null)
{
//targetForce can only be adjusted at 10% intervals -> no need for more accuracy than this
msg.WriteRangedIntegerDeprecated(-10, 10, (int)(targetForce / 10.0f));
msg.WriteRangedInteger((int)(targetForce / 10.0f), -10, 10);
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
@@ -44,6 +44,16 @@ namespace Barotrauma.Items.Components
Stretch = true,
RelativeSpacing = 0.02f
};
itemList = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.5f), paddedFrame.RectTransform))
{
OnSelected = (GUIComponent component, object userdata) =>
{
selectedItem = userdata as FabricationRecipe;
if (selectedItem != null) { SelectItem(Character.Controlled, selectedItem); }
return true;
}
};
var filterArea = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.06f), paddedFrame.RectTransform), isHorizontal: true)
{
@@ -58,16 +68,6 @@ namespace Barotrauma.Items.Components
OnClicked = (btn, userdata) => { ClearFilter(); itemFilterBox.Flash(Color.White); return true; }
};
itemList = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.5f), paddedFrame.RectTransform))
{
OnSelected = (GUIComponent component, object userdata) =>
{
selectedItem = userdata as FabricationRecipe;
if (selectedItem != null) { SelectItem(Character.Controlled, selectedItem); }
return true;
}
};
inputInventoryHolder = new GUIFrame(new RectTransform(new Vector2(0.7f, 0.15f), paddedFrame.RectTransform), style: null);
inputInventoryOverlay = new GUICustomComponent(new RectTransform(Vector2.One, inputInventoryHolder.RectTransform), DrawInputOverLay, null)
{
@@ -462,7 +462,7 @@ namespace Barotrauma.Items.Components
public void ClientWrite(IWriteMessage msg, object[] extraData = null)
{
int itemIndex = pendingFabricatedItem == null ? -1 : fabricationRecipes.IndexOf(pendingFabricatedItem);
msg.WriteRangedIntegerDeprecated(-1, fabricationRecipes.Count - 1, itemIndex);
msg.WriteRangedInteger(itemIndex, -1, fabricationRecipes.Count - 1);
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
@@ -179,7 +179,7 @@ namespace Barotrauma.Items.Components
public void ClientWrite(IWriteMessage msg, object[] extraData = null)
{
//flowpercentage can only be adjusted at 10% intervals -> no need for more accuracy than this
msg.WriteRangedIntegerDeprecated(-10, 10, (int)(flowPercentage / 10.0f));
msg.WriteRangedInteger((int)(flowPercentage / 10.0f), -10, 10);
msg.Write(IsActive);
}
@@ -451,7 +451,10 @@ namespace Barotrauma.Items.Components
if (PlayerInput.KeyDown(InputType.Right)) input.X += 1.0f;
if (PlayerInput.KeyDown(InputType.Up)) input.Y += 1.0f;
if (PlayerInput.KeyDown(InputType.Down)) input.Y += -1.0f;
if (PlayerInput.KeyDown(InputType.Run)) rate = 200.0f;
if (PlayerInput.KeyDown(InputType.Run))
rate = 200.0f;
else if (PlayerInput.KeyDown(InputType.Crouch))
rate = 20.0f;
rate *= deltaTime;
input.X *= rate;
@@ -73,11 +73,18 @@ namespace Barotrauma.Items.Components
set { maintainPosTickBox.Selected = value; }
}
private bool dockingModeEnabled;
public bool DockingModeEnabled
{
get { return UseAutoDocking && dockingModeEnabled; }
set { dockingModeEnabled = value; }
}
public bool UseAutoDocking
{
get;
set;
}
} = true;
public List<DockingPort> DockingSources = new List<DockingPort>();
public DockingPort ActiveDockingSource, DockingTarget;
@@ -726,6 +733,8 @@ namespace Barotrauma.Items.Components
inputCumulation = 0;
keyboardInput = Vector2.Zero;
}
if (!UseAutoDocking) { return; }
float closestDist = DockingAssistThreshold * DockingAssistThreshold;
DockingModeEnabled = false;
@@ -129,7 +129,7 @@ namespace Barotrauma.Items.Components
public void ClientWrite(IWriteMessage msg, object[] extraData)
{
msg.WriteRangedIntegerDeprecated(0, 10, (int)(rechargeSpeed / MaxRechargeSpeed * 10));
msg.WriteRangedInteger((int)(rechargeSpeed / MaxRechargeSpeed * 10), 0, 10);
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
@@ -140,7 +140,11 @@ namespace Barotrauma.Items.Components
return;
}
RechargeSpeed = msg.ReadRangedInteger(0, 10) / 10.0f * maxRechargeSpeed;
float rechargeRate = msg.ReadRangedInteger(0, 10) / 10.0f;
RechargeSpeed = rechargeRate * MaxRechargeSpeed;
#if CLIENT
rechargeSpeedSlider.BarScroll = rechargeRate;
#endif
Charge = msg.ReadRangedSingle(0.0f, 1.0f, 8) * capacity;
}
}
@@ -65,13 +65,13 @@ namespace Barotrauma.Items.Components
}
partial void UseProjSpecific(float deltaTime)
partial void UseProjSpecific(float deltaTime, Vector2 raystart)
{
if (ParticleEmitter != null)
{
float particleAngle = item.body.Rotation + ((item.body.Dir > 0.0f) ? 0.0f : MathHelper.Pi);
ParticleEmitter.Emit(
deltaTime, item.WorldPosition + TransformedBarrelPos,
deltaTime, ConvertUnits.ToDisplayUnits(raystart),
item.CurrentHull, particleAngle, ParticleEmitter.Prefab.CopyEntityAngle ? -particleAngle : 0);
}
}
@@ -1,5 +1,6 @@
using Barotrauma.Networking;
using Barotrauma.Particles;
using Barotrauma.Sounds;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using System.Collections.Generic;
@@ -25,6 +26,8 @@ namespace Barotrauma.Items.Components
//the corresponding particle emitter is active when the condition is within this range
private List<Vector2> particleEmitterConditionRanges = new List<Vector2>();
private SoundChannel repairSoundChannel;
private string repairButtonText, repairingText;
private string sabotageButtonText, sabotagingText;
@@ -140,6 +143,19 @@ namespace Barotrauma.Items.Components
particleEmitters[i].Emit(deltaTime, item.WorldPosition, item.CurrentHull);
}
}
if (CurrentFixer != null && CurrentFixer.SelectedConstruction == item)
{
if (repairSoundChannel == null || !repairSoundChannel.IsPlaying)
{
repairSoundChannel = SoundPlayer.PlaySound("repair", item.WorldPosition, hullGuess: item.CurrentHull);
}
}
else
{
repairSoundChannel?.FadeOutAndDispose();
repairSoundChannel = null;
}
}
public override void DrawHUD(SpriteBatch spriteBatch, Character character)
@@ -177,20 +193,6 @@ namespace Barotrauma.Items.Components
}
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
{
deteriorationTimer = msg.ReadSingle();
deteriorateAlwaysResetTimer = msg.ReadSingle();
DeteriorateAlways = msg.ReadBoolean();
CurrentFixer = msg.ReadBoolean() ? Character.Controlled : null;
currentFixerAction = (FixActions)msg.ReadRangedInteger(0, 2);
}
public void ClientWrite(IWriteMessage msg, object[] extraData = null)
{
msg.WriteRangedInteger((int)requestStartFixAction, 0, 2);
}
public void Draw(SpriteBatch spriteBatch, bool editing)
{
if (GameMain.DebugDraw && Character.Controlled?.FocusedItem == item)
@@ -213,5 +215,25 @@ namespace Barotrauma.Items.Components
Color.Orange);
}
}
protected override void RemoveComponentSpecific()
{
repairSoundChannel?.FadeOutAndDispose();
repairSoundChannel = null;
}
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
{
deteriorationTimer = msg.ReadSingle();
deteriorateAlwaysResetTimer = msg.ReadSingle();
DeteriorateAlways = msg.ReadBoolean();
CurrentFixer = msg.ReadBoolean() ? Character.Controlled : null;
currentFixerAction = (FixActions)msg.ReadRangedInteger(0, 2);
}
public void ClientWrite(IWriteMessage msg, object[] extraData = null)
{
msg.WriteRangedInteger((int)requestStartFixAction, 0, 2);
}
}
}
@@ -1,4 +1,5 @@
using Barotrauma.Networking;
using Barotrauma.Sounds;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using System;
@@ -12,6 +13,8 @@ namespace Barotrauma.Items.Components
{
public static Wire HighlightedWire;
private SoundChannel rewireSoundChannel;
partial void InitProjSpecific(XElement element)
{
if (GuiFrame == null) return;
@@ -20,7 +23,37 @@ namespace Barotrauma.Items.Components
UserData = this
};
}
partial void UpdateProjSpecific(float deltaTime)
{
foreach (Wire wire in DisconnectedWires)
{
if (Rand.Range(0.0f, 500.0f) < 1.0f)
{
SoundPlayer.PlaySound("zap", item.WorldPosition, hullGuess: item.CurrentHull);
Vector2 baseVel = new Vector2(0.0f, -100.0f);
for (int i = 0; i < 5; i++)
{
var particle = GameMain.ParticleManager.CreateParticle("spark", item.WorldPosition,
baseVel + Rand.Vector(100.0f), 0.0f, item.CurrentHull);
if (particle != null) { particle.Size *= Rand.Range(0.5f, 1.0f); }
}
}
}
if (user != null && user.SelectedConstruction == item && HasRequiredItems(user, addMessage: false))
{
if (rewireSoundChannel == null || !rewireSoundChannel.IsPlaying)
{
rewireSoundChannel = SoundPlayer.PlaySound("rewire", item.WorldPosition, hullGuess: item.CurrentHull);
}
}
else
{
rewireSoundChannel?.FadeOutAndDispose();
rewireSoundChannel = null;
}
}
public override void Move(Vector2 amount)
{
if (item.Submarine == null || item.Submarine.Loading || Screen.Selected != GameMain.SubEditorScreen) return;
@@ -155,8 +155,8 @@ namespace Barotrauma
public class SlotReference
{
public readonly Inventory ParentInventory;
public readonly InventorySlot Slot;
public readonly int SlotIndex;
public InventorySlot Slot;
public Inventory Inventory;
@@ -741,17 +741,37 @@ namespace Barotrauma
{
Inventory selectedInventory = selectedSlot.ParentInventory;
int slotIndex = selectedSlot.SlotIndex;
if (selectedInventory.TryPutItem(draggingItem, slotIndex, true, true, Character.Controlled))
//if attempting to drop into an invalid slot in the same inventory, try to move to the correct slot
if (selectedInventory.Items[slotIndex] == null &&
selectedInventory == Character.Controlled.Inventory &&
!draggingItem.AllowedSlots.Any(a => a.HasFlag(Character.Controlled.Inventory.SlotTypes[slotIndex])) &&
selectedInventory.TryPutItem(draggingItem, Character.Controlled, draggingItem.AllowedSlots))
{
if (selectedInventory.slots != null) selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.White, 0.1f, 0.4f);
if (selectedInventory.slots != null)
{
for (int i = 0; i < selectedInventory.slots.Length; i++)
{
if (selectedInventory.Items[i] == draggingItem)
{
selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.White, 0.1f, 0.4f);
}
}
selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.Red, 0.1f, 0.9f);
}
GUI.PlayUISound(GUISoundType.PickItem);
}
else if (selectedInventory.TryPutItem(draggingItem, slotIndex, true, true, Character.Controlled))
{
if (selectedInventory.slots != null) { selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.White, 0.1f, 0.4f); }
GUI.PlayUISound(GUISoundType.PickItem);
}
else
{
if (selectedInventory.slots != null) selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.Red, 0.1f, 0.9f);
if (selectedInventory.slots != null){ selectedInventory.slots[slotIndex].ShowBorderHighlight(Color.Red, 0.1f, 0.9f); }
GUI.PlayUISound(GUISoundType.PickItemFail);
}
selectedInventory.HideTimer = 1.0f;
selectedInventory.HideTimer = 2.0f;
if (selectedSlot.ParentInventory?.Owner is Item parentItem && parentItem.ParentInventory != null)
{
for (int i = 0; i < parentItem.ParentInventory.capacity; i++)
@@ -960,7 +980,7 @@ namespace Barotrauma
{
GUI.DrawRectangle(spriteBatch, new Rectangle(rect.X, rect.Bottom - 8, rect.Width, 8), Color.Black * 0.8f, true);
GUI.DrawRectangle(spriteBatch,
new Rectangle(rect.X, rect.Bottom - 8, (int)(rect.Width * item.Condition / item.MaxCondition), 8),
new Rectangle(rect.X, rect.Bottom - 8, (int)(rect.Width * (item.Condition / item.MaxCondition)), 8),
Color.Lerp(Color.Red, Color.Green, item.Condition / item.MaxCondition) * 0.8f, true);
}
@@ -1080,9 +1100,9 @@ namespace Barotrauma
public void ClientRead(ServerNetObject type, IReadMessage msg, float sendingTime)
{
receivedItemIDs = new ushort[capacity];
for (int i = 0; i < capacity; i++)
byte itemCount = msg.ReadByte();
receivedItemIDs = new ushort[itemCount];
for (int i = 0; i < itemCount; i++)
{
receivedItemIDs[i] = msg.ReadUInt16();
}
@@ -930,17 +930,17 @@ namespace Barotrauma
}
NetEntityEvent.Type eventType = (NetEntityEvent.Type)extraData[0];
msg.WriteRangedIntegerDeprecated(0, Enum.GetValues(typeof(NetEntityEvent.Type)).Length - 1, (int)eventType);
msg.WriteRangedInteger((int)eventType, 0, Enum.GetValues(typeof(NetEntityEvent.Type)).Length - 1);
switch (eventType)
{
case NetEntityEvent.Type.ComponentState:
int componentIndex = (int)extraData[1];
msg.WriteRangedIntegerDeprecated(0, components.Count - 1, componentIndex);
msg.WriteRangedInteger(componentIndex, 0, components.Count - 1);
(components[componentIndex] as IClientSerializable).ClientWrite(msg, extraData);
break;
case NetEntityEvent.Type.InventoryState:
int containerIndex = (int)extraData[1];
msg.WriteRangedIntegerDeprecated(0, components.Count - 1, containerIndex);
msg.WriteRangedInteger(containerIndex, 0, components.Count - 1);
(components[containerIndex] as ItemContainer).Inventory.ClientWrite(msg, extraData);
break;
case NetEntityEvent.Type.Treatment:
@@ -1114,7 +1114,8 @@ namespace Barotrauma
MapEntityPrefab.Find(itemName, itemIdentifier, showErrorMessages: false) as ItemPrefab;
if (itemPrefab == null)
{
string errorMsg = "Failed to spawn item (name: " + (itemName ?? "null") + ", identifier: " + (itemIdentifier ?? "null");
string errorMsg = "Failed to spawn item, prefab not found (name: " + (itemName ?? "null") + ", identifier: " + (itemIdentifier ?? "null") + ")";
errorMsg += "\n" + string.Join(", ", GameMain.Config.SelectedContentPackages.Select(cp => cp.Name));
GameAnalyticsManager.AddErrorEventOnce("Item.ReadSpawnData:PrefabNotFound" + (itemName ?? "null") + (itemIdentifier ?? "null"),
GameAnalyticsSDK.Net.EGAErrorSeverity.Critical,
errorMsg);
@@ -534,7 +534,7 @@ namespace Barotrauma
msg.Write(FireSources.Count > 0);
if (FireSources.Count > 0)
{
msg.WriteRangedIntegerDeprecated(0, 16, Math.Min(FireSources.Count, 16));
msg.WriteRangedInteger(Math.Min(FireSources.Count, 16), 0, 16);
for (int i = 0; i < Math.Min(FireSources.Count, 16); i++)
{
var fireSource = FireSources[i];
@@ -45,7 +45,9 @@ namespace Barotrauma
if (string.IsNullOrEmpty(filename))
{
DebugConsole.ThrowError("Error when loading round sound (" + element + ") - file path not set");
string errorMsg = "Error when loading round sound (" + element + ") - file path not set";
DebugConsole.ThrowError(errorMsg);
GameAnalyticsManager.AddErrorEventOnce("Submarine.LoadRoundSound:FilePathEmpty" + element.ToString(), GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg + "\n" + Environment.StackTrace);
return null;
}
@@ -69,7 +71,9 @@ namespace Barotrauma
}
catch (FileNotFoundException e)
{
DebugConsole.ThrowError("Failed to load sound file \"" + filename + "\".", e);
string errorMsg = "Failed to load sound file \"" + filename + "\".";
DebugConsole.ThrowError(errorMsg, e);
GameAnalyticsManager.AddErrorEventOnce("Submarine.LoadRoundSound:FileNotFound" + filename, GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg + "\n" + Environment.StackTrace);
return null;
}
}
@@ -84,14 +84,12 @@ namespace Barotrauma.Networking
font: GUI.SmallFont);
var reasonText = new GUITextBlock(new RectTransform(new Vector2(0.6f, 0.0f), paddedPlayerFrame.RectTransform),
TextManager.Get("BanReason") +
TextManager.Get("BanReason") + " " +
(string.IsNullOrEmpty(bannedPlayer.Reason) ? TextManager.Get("None") : ToolBox.LimitString(bannedPlayer.Reason, GUI.SmallFont, 170)),
font: GUI.SmallFont, wrap: true)
{
ToolTip = bannedPlayer.Reason
};
}
return banFrame;
@@ -100,34 +98,29 @@ namespace Barotrauma.Networking
private bool RemoveBan(GUIButton button, object obj)
{
BannedPlayer banned = obj as BannedPlayer;
if (banned == null) return false;
if (banned == null) { return false; }
localRemovedBans.Add(banned.UniqueIdentifier);
RecreateBanFrame();
GameMain.Client?.ServerSettings?.ClientAdminWrite(ServerSettings.NetFlags.Properties);
return true;
}
private bool RangeBan(GUIButton button, object obj)
{
BannedPlayer banned = obj as BannedPlayer;
if (banned == null) return false;
if (banned == null) { return false; }
localRangeBans.Add(banned.UniqueIdentifier);
RecreateBanFrame();
return true;
}
private bool CloseFrame(GUIButton button, object obj)
{
banFrame = null;
GameMain.Client?.ServerSettings?.ClientAdminWrite(ServerSettings.NetFlags.Properties);
return true;
}
public void ClientAdminRead(IReadMessage incMsg)
{
bool hasPermission = incMsg.ReadBoolean();
@@ -460,13 +460,13 @@ namespace Barotrauma.Networking
}
catch (Exception e)
{
ErrorMessage = "Loading received submarine ''" + fileTransfer.FileName + "'' failed! {" + e.Message + "}";
ErrorMessage = "Loading received submarine \"" + fileTransfer.FileName + "\" failed! {" + e.Message + "}";
return false;
}
if (stream == null)
{
ErrorMessage = "Decompressing received submarine file''" + fileTransfer.FilePath + "'' failed!";
ErrorMessage = "Decompressing received submarine file \"" + fileTransfer.FilePath + "\" failed!";
return false;
}
@@ -490,7 +490,7 @@ namespace Barotrauma.Networking
stream.Close();
stream.Dispose();
ErrorMessage = "Parsing file ''" + fileTransfer.FilePath + "'' failed! The file may not be a valid submarine file.";
ErrorMessage = "Parsing file \"" + fileTransfer.FilePath + "\" failed! The file may not be a valid submarine file.";
return false;
}
@@ -396,15 +396,13 @@ namespace Barotrauma.Networking
private bool connectCancelled;
private void CancelConnect()
{
if (!(GameMain.ServerChildProcess?.HasExited??true))
if (!(GameMain.ServerChildProcess?.HasExited ?? true))
{
GameMain.ServerChildProcess.Kill();
GameMain.ServerChildProcess = null;
}
connectCancelled = true;
clientPeer?.Close();
clientPeer = null;
Disconnect();
}
// Before main looping starts, we loop here and wait for approval message
@@ -554,14 +552,20 @@ namespace Barotrauma.Networking
UpdateHUD(deltaTime);
base.Update(deltaTime);
try
{
clientPeer?.Update(deltaTime);
}
catch (Exception e)
{
string errorMsg = "Error while reading a message from server. {" + e + "}\n" + e.StackTrace;
string errorMsg = "Error while reading a message from server. {" + e + "}. ";
if (GameMain.Client == null) { errorMsg += "Client disposed."; }
errorMsg += "\n" + e.StackTrace;
if (e.InnerException != null)
{
errorMsg += "\nInner exception: " + e.InnerException.Message + "\n" + e.InnerException.StackTrace;
}
GameAnalyticsManager.AddErrorEventOnce("GameClient.Update:CheckServerMessagesException" + e.TargetSite.ToString(), GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
DebugConsole.ThrowError("Error while reading a message from server.", e);
new GUIMessageBox(TextManager.Get("Error"), TextManager.GetWithVariables("MessageReadError", new string[2] { "[message]", "[targetsite]" }, new string[2] { e.Message, e.TargetSite.ToString() }));
@@ -603,7 +607,7 @@ namespace Barotrauma.Networking
if (IsServerOwner && connected && !connectCancelled)
{
if (GameMain.ServerChildProcess?.HasExited??true)
if (GameMain.ServerChildProcess?.HasExited ?? true)
{
Disconnect();
var msgBox = new GUIMessageBox(TextManager.Get("ConnectionLost"), TextManager.Get("ServerProcessClosed"));
@@ -626,9 +630,34 @@ namespace Barotrauma.Networking
ReadLobbyUpdate(inc);
break;
case ServerPacketHeader.UPDATE_INGAME:
ReadIngameUpdate(inc);
try
{
ReadIngameUpdate(inc);
}
catch (Exception e)
{
string errorMsg = "Error while reading an ingame update message from server. {" + e + "}\n" + e.StackTrace;
if (e.InnerException != null)
{
errorMsg += "\nInner exception: " + e.InnerException.Message + "\n" + e.InnerException.StackTrace;
}
GameAnalyticsManager.AddErrorEventOnce("GameClient.ReadDataMessage:ReadIngameUpdate", GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
throw;
}
break;
case ServerPacketHeader.VOICE:
if (VoipClient == null)
{
string errorMsg = "Failed to read a voice packet from the server (VoipClient == null). ";
if (GameMain.Client == null) { errorMsg += "Client disposed. "; }
errorMsg += "\n" + Environment.StackTrace;
GameAnalyticsManager.AddErrorEventOnce(
"GameClient.ReadDataMessage:VoipClientNull",
GameMain.Client == null ? GameAnalyticsSDK.Net.EGAErrorSeverity.Error : GameAnalyticsSDK.Net.EGAErrorSeverity.Warning,
errorMsg);
return;
}
VoipClient.Read(inc);
break;
case ServerPacketHeader.QUERY_STARTGAME:
@@ -728,7 +757,7 @@ namespace Barotrauma.Networking
string[] splitMsg = disconnectMsg.Split('/');
DisconnectReason disconnectReason = DisconnectReason.Unknown;
if (splitMsg.Length > 0) Enum.TryParse(splitMsg[0], out disconnectReason);
if (splitMsg.Length > 0) { Enum.TryParse(splitMsg[0], out disconnectReason); }
if (disconnectMsg == Lidgren.Network.NetConnection.NoResponseMessage)
{
@@ -737,6 +766,19 @@ namespace Barotrauma.Networking
DebugConsole.NewMessage("Received a disconnect message (" + disconnectMsg + ")");
if (disconnectReason != DisconnectReason.Banned &&
disconnectReason != DisconnectReason.ServerShutdown &&
disconnectReason != DisconnectReason.TooManyFailedLogins &&
disconnectReason != DisconnectReason.NotOnWhitelist &&
disconnectReason != DisconnectReason.MissingContentPackage &&
disconnectReason != DisconnectReason.InvalidVersion)
{
GameAnalyticsManager.AddErrorEventOnce(
"GameClient.HandleDisconnectMessage",
GameAnalyticsSDK.Net.EGAErrorSeverity.Debug,
"Client received a disconnect message. Reason: " + disconnectReason.ToString() + ", message: " + disconnectMsg);
}
if (disconnectReason == DisconnectReason.ServerFull)
{
CoroutineManager.StopCoroutines("WaitForStartingInfo");
@@ -1059,6 +1101,28 @@ namespace Barotrauma.Networking
if (campaign == null)
{
//this shouldn't happen, TrySelectSub should stop the coroutine if the correct sub/shuttle cannot be found
if (GameMain.NetLobbyScreen.SelectedSub == null ||
GameMain.NetLobbyScreen.SelectedSub.Name != subName ||
GameMain.NetLobbyScreen.SelectedSub.MD5Hash?.Hash != subHash)
{
string errorMsg = "Failed to select submarine \"" + subName + "\" (hash: " + subHash + ").";
DebugConsole.ThrowError(errorMsg);
GameAnalyticsManager.AddErrorEventOnce("GameClient.StartGame:FailedToSelectSub" + subName, GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
CoroutineManager.StartCoroutine(EndGame(""));
yield return CoroutineStatus.Failure;
}
if (GameMain.NetLobbyScreen.SelectedShuttle == null ||
GameMain.NetLobbyScreen.SelectedShuttle.Name != shuttleName ||
GameMain.NetLobbyScreen.SelectedShuttle.MD5Hash?.Hash != shuttleHash)
{
string errorMsg = "Failed to select shuttle \"" + shuttleName + "\" (hash: " + shuttleHash + ").";
DebugConsole.ThrowError(errorMsg);
GameAnalyticsManager.AddErrorEventOnce("GameClient.StartGame:FailedToSelectShuttle" + shuttleName, GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
CoroutineManager.StartCoroutine(EndGame(""));
yield return CoroutineStatus.Failure;
}
GameMain.GameSession = missionIndex < 0 ?
new GameSession(GameMain.NetLobbyScreen.SelectedSub, "", gameMode, MissionType.None) :
new GameSession(GameMain.NetLobbyScreen.SelectedSub, "", gameMode, MissionPrefab.List[missionIndex]);
@@ -1252,7 +1316,8 @@ namespace Barotrauma.Networking
{
existingClient.SetPermissions(permissions, permittedConsoleCommands);
name = tc.Name;
if (GameMain.NetLobbyScreen.CharacterNameBox != null)
if (GameMain.NetLobbyScreen.CharacterNameBox != null &&
!GameMain.NetLobbyScreen.CharacterNameBox.Selected)
{
GameMain.NetLobbyScreen.CharacterNameBox.Text = name;
}
@@ -9,6 +9,11 @@ namespace Barotrauma
{
public void CreateSettingsFrame(GUIComponent parent)
{
if (TextManager.ContainsTag("Karma.ResetKarmaBetweenRounds"))
{
CreateLabeledTickBox(parent, "ResetKarmaBetweenRounds");
}
CreateLabeledSlider(parent, 0.0f, 40.0f, 1.0f, "KickBanThreshold");
if (TextManager.ContainsTag("Karma.KicksBeforeBan"))
{
@@ -102,5 +107,14 @@ namespace Barotrauma
};
GameMain.NetworkMember.ServerSettings.AssignGUIComponent(propertyName, numInput);
}
private void CreateLabeledTickBox(GUIComponent parent, string propertyName)
{
var tickBox = new GUITickBox(new RectTransform(new Vector2(0.3f, 0.1f), parent.RectTransform), TextManager.Get("Karma." + propertyName))
{
ToolTip = TextManager.Get("Karma." + propertyName + "ToolTip", returnNull: true) ?? ""
};
GameMain.NetworkMember.ServerSettings.AssignGUIComponent(propertyName, tickBox);
}
}
}
@@ -96,7 +96,7 @@ namespace Barotrauma.Networking
//find the first event that hasn't been sent in roundtriptime or at all
eventLastSent.TryGetValue(events[i].ID, out float lastSent);
if (lastSent > Lidgren.Network.NetTime.Now - 50) //TODO: reimplement serverConnection.AverageRoundtripTime
if (lastSent > Lidgren.Network.NetTime.Now - 0.2) //TODO: reimplement serverConnection.AverageRoundtripTime
{
continue;
}
@@ -176,7 +176,11 @@ namespace Barotrauma.Networking
outMsg.Write(contentPackage.MD5hash.Hash);
}
netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
NetSendResult result = netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send "+initializationStep.ToString()+" message to host: " + result);
}
break;
case ConnectionInitialization.Password:
if (initializationStep == ConnectionInitialization.SteamTicketAndVersion) { initializationStep = ConnectionInitialization.Password; }
@@ -207,7 +211,11 @@ namespace Barotrauma.Networking
byte[] saltedPw = ServerSettings.SaltPassword(NetUtility.ComputeSHAHash(Encoding.UTF8.GetBytes(password)), passwordSalt);
outMsg.Write((byte)saltedPw.Length);
outMsg.Write(saltedPw, 0, saltedPw.Length);
netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
NetSendResult result = netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send " + initializationStep.ToString() + " message to host: " + result);
}
}
public override void Close(string msg = null)
@@ -247,7 +255,11 @@ namespace Barotrauma.Networking
lidgrenMsg.Write((UInt16)length);
lidgrenMsg.Write(msgData, 0, length);
netClient.SendMessage(lidgrenMsg, lidgrenDeliveryMethod);
NetSendResult result = netClient.SendMessage(lidgrenMsg, lidgrenDeliveryMethod);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send message to host: " + result);
}
}
}
}
@@ -66,7 +66,7 @@ namespace Barotrauma.Networking
initializationStep = ConnectionInitialization.SteamTicketAndVersion;
timeout = 20.0;
timeout = NetworkConnection.TimeoutThreshold;
heartbeatTimer = 1.0;
isActive = true;
@@ -83,7 +83,7 @@ namespace Barotrauma.Networking
if (!isActive) { return; }
if (steamId != hostSteamId) { return; }
timeout = 20.0;
timeout = NetworkConnection.TimeoutThreshold;
byte incByte = data[0];
bool isCompressed = (incByte & (byte)PacketHeader.IsCompressed) != 0;
@@ -87,7 +87,7 @@ namespace Barotrauma.Networking
private void OnAuthChange(ulong steamID, ulong ownerID, ClientAuthStatus status)
{
RemotePeer remotePeer = remotePeers.Find(p => p.SteamID == steamID);
DebugConsole.NewMessage(steamID + " validation: " + status + ", " + (remotePeer != null));
DebugConsole.Log(steamID + " validation: " + status + ", " + (remotePeer != null));
if (remotePeer == null) { return; }
@@ -106,7 +106,11 @@ namespace Barotrauma.Networking
remotePeer.Authenticating = false;
foreach (var msg in remotePeer.UnauthedMessages)
{
netClient.SendMessage(msg.Second, msg.First);
NetSendResult result = netClient.SendMessage(msg.Second, msg.First);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send unauthed message to host: " + result);
}
}
remotePeer.UnauthedMessages.Clear();
}
@@ -200,7 +204,11 @@ namespace Barotrauma.Networking
}
else
{
netClient.SendMessage(outMsg, lidgrenDeliveryMethod);
NetSendResult result = netClient.SendMessage(outMsg, lidgrenDeliveryMethod);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send message from "+SteamManager.SteamIDUInt64ToString(remotePeer.SteamID)+" to host: " + result);
}
}
}
@@ -344,7 +352,11 @@ namespace Barotrauma.Networking
outMsg.Write(selfSteamID);
outMsg.Write((byte)(PacketHeader.IsConnectionInitializationStep));
outMsg.Write(Name);
netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
NetSendResult result = netClient.SendMessage(outMsg, NetDeliveryMethod.ReliableUnordered);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send initialization message to host: " + result);
}
return;
}
@@ -466,7 +478,11 @@ namespace Barotrauma.Networking
lidgrenMsg.Write((UInt16)length);
lidgrenMsg.Write(msgData, 0, length);
netClient.SendMessage(lidgrenMsg, lidgrenDeliveryMethod);
NetSendResult result = netClient.SendMessage(lidgrenMsg, lidgrenDeliveryMethod);
if (result != NetSendResult.Queued && result != NetSendResult.Sent)
{
DebugConsole.NewMessage("Failed to send own message to host: " + result);
}
}
}
}
@@ -218,9 +218,9 @@ namespace Barotrauma.Steam
instance.client.Lobby.CurrentLobbyData.SetData("allowrespawn", serverSettings.AllowRespawn.ToString());
instance.client.Lobby.CurrentLobbyData.SetData("traitors", serverSettings.TraitorsEnabled.ToString());
instance.client.Lobby.CurrentLobbyData.SetData("gamestarted", GameMain.Client.GameStarted.ToString());
instance.client.Lobby.CurrentLobbyData.SetData("gamemode", serverSettings.GameModeIdentifier);
instance.client.Lobby.CurrentLobbyData.SetData("gamemode", GameMain.NetLobbyScreen?.SelectedMode?.Identifier??"");
DebugConsole.NewMessage("Lobby updated!", Microsoft.Xna.Framework.Color.Lime);
DebugConsole.Log("Lobby updated!");
}
public static void LeaveLobby()
@@ -770,6 +770,14 @@ namespace Barotrauma.Steam
ContentPackage tempContentPackage = new ContentPackage(Path.Combine(existingItem.Directory.FullName, MetadataFileName));
string installedContentPackagePath = Path.GetFullPath(GetWorkshopItemContentPackagePath(tempContentPackage));
contentPackage = ContentPackage.List.Find(cp => Path.GetFullPath(cp.Path) == installedContentPackagePath);
if (contentPackage == null && tempContentPackage.GameVersion <= new Version(0, 9, 1, 0))
{
//try finding the content package in the lega
installedContentPackagePath = Path.GetFullPath(GetWorkshopItemContentPackagePath(tempContentPackage, legacy: false));
contentPackage = ContentPackage.List.Find(cp => Path.GetFullPath(cp.Path) == installedContentPackagePath);
}
if (tempContentPackage.GameVersion > new Version(0, 9, 1, 0))
{
itemEditor.Folder = Path.GetDirectoryName(installedContentPackagePath);
@@ -784,6 +792,7 @@ namespace Barotrauma.Steam
contentPackage.Path = newPath;
itemEditor.Folder = newDir;
if (!Directory.Exists(newDir)) { Directory.CreateDirectory(newDir); }
if (File.Exists(newPath)) { File.Delete(newPath); }
File.Move(installedContentPackagePath, newPath);
//move all files inside the Mods folder
foreach (ContentFile cf in contentPackage.Files)
@@ -793,10 +802,12 @@ namespace Barotrauma.Steam
{
string destinationPath = Path.Combine(newDir, cf.Path);
if (!Directory.Exists(Path.GetDirectoryName(destinationPath))) { Directory.CreateDirectory(Path.GetDirectoryName(destinationPath)); }
if (File.Exists(destinationPath)) { File.Delete(destinationPath); }
File.Move(cf.Path, destinationPath);
cf.Path = destinationPath;
}
}
contentPackage.GameVersion = GameMain.Version;
contentPackage.Save(contentPackage.Path);
}
catch (Exception e)
@@ -1202,7 +1213,22 @@ namespace Barotrauma.Steam
return false;
}
string metaDataPath = Path.Combine(item.Directory.FullName, MetadataFileName);
string metaDataPath = "";
try
{
metaDataPath = Path.Combine(item.Directory.FullName, MetadataFileName);
}
catch (ArgumentException e)
{
string errorMessage = "Metadata file for the Workshop item \"" + item.Title +
"\" not found. Could not combine path (" + (item.Directory.FullName ?? "directory name empty") + ").";
DebugConsole.ThrowError(errorMessage);
GameAnalyticsManager.AddErrorEventOnce("SteamManager.CheckWorkshopItemEnabled:PathCombineException" + item.Title,
GameAnalyticsSDK.Net.EGAErrorSeverity.Error,
errorMessage);
return false;
}
if (!File.Exists(metaDataPath))
{
DebugConsole.ThrowError("Metadata file for the Workshop item \"" + item.Title + "\" not found. The file may be corrupted.");
@@ -1309,12 +1335,18 @@ namespace Barotrauma.Steam
}
public static string GetWorkshopItemContentPackagePath(ContentPackage contentPackage)
{
return GetWorkshopItemContentPackagePath(contentPackage, legacy: contentPackage.GameVersion <= new Version(0, 9, 1, 0));
}
private static string GetWorkshopItemContentPackagePath(ContentPackage contentPackage, bool legacy)
{
string fileName = contentPackage.Name;
string invalidChars = ToolBox.RemoveInvalidFileNameChars(fileName);
return contentPackage.GameVersion > new Version(0, 9, 1, 0) ?
Path.Combine("Mods", fileName, MetadataFileName) :
Path.Combine("Data", "ContentPackages", fileName + ".xml"); //legacy support
fileName = ToolBox.RemoveInvalidFileNameChars(fileName);
return legacy ?
Path.Combine("Data", "ContentPackages", fileName + ".xml") :
Path.Combine("Mods", fileName, MetadataFileName);
}
#endregion
@@ -94,7 +94,7 @@ namespace Barotrauma.Networking
client.VoipSound = new VoipSound(GameMain.SoundManager, client.VoipQueue);
}
if (client.Character != null && !client.Character.IsDead && client.Character.SpeechImpediment <= 100.0f)
if (client.Character != null && !client.Character.IsDead && !client.Character.Removed && client.Character.SpeechImpediment <= 100.0f)
{
var messageType = ChatMessage.CanUseRadio(client.Character, out WifiComponent radio) ? ChatMessageType.Radio : ChatMessageType.Default;
client.Character.ShowSpeechBubble(1.25f, ChatMessage.MessageColor[(int)messageType]);
@@ -119,7 +119,7 @@ namespace Barotrauma.Networking
if (client.VoipSound.CurrentAmplitude > 0.1f) //TODO: might need to tweak
{
if (client.Character != null)
if (client.Character != null && !client.Character.Removed)
{
Vector3 clientPos = new Vector3(client.Character.WorldPosition.X, client.Character.WorldPosition.Y, 0.0f);
Vector3 listenerPos = GameMain.SoundManager.ListenerPosition;
@@ -859,6 +859,9 @@ namespace Barotrauma
private void FillStoreItemList()
{
float prevStoreItemScroll = storeItemList.BarScroll;
float prevMyItemScroll = myItemList.BarScroll;
int width = storeItemList.Rect.Width;
HashSet<GUIComponent> existingItemFrames = new HashSet<GUIComponent>();
foreach (MapEntityPrefab mapEntityPrefab in MapEntityPrefab.List)
@@ -883,6 +886,9 @@ namespace Barotrauma
storeItemList.Content.RectTransform.SortChildren(
(x, y) => (x.GUIComponent.UserData as PurchasedItem).ItemPrefab.Name.CompareTo((y.GUIComponent.UserData as PurchasedItem).ItemPrefab.Name));
storeItemList.BarScroll = prevStoreItemScroll;
myItemList.BarScroll = prevMyItemScroll;
}
private void FilterStoreItems(MapEntityCategory? category, string filter)
@@ -904,7 +910,7 @@ namespace Barotrauma
btn.Selected = (MapEntityCategory)btn.UserData == selectedItemCategory;
}
storeItemList.UpdateScrollBarSize();
storeItemList.BarScroll = 0.0f;
//storeItemList.BarScroll = 0.0f;
}
public string GetMoney()
@@ -1216,7 +1216,7 @@ namespace Barotrauma
CanBeFocused = false
};
var matchingSub = Submarine.SavedSubmarines.FirstOrDefault(s => s.Name == sub.Name && s.MD5Hash.Hash == sub.MD5Hash.Hash);
var matchingSub = Submarine.SavedSubmarines.FirstOrDefault(s => s.Name == sub.Name && s.MD5Hash?.Hash == sub.MD5Hash?.Hash);
if (matchingSub == null) matchingSub = Submarine.SavedSubmarines.FirstOrDefault(s => s.Name == sub.Name);
if (matchingSub == null)
@@ -1224,7 +1224,7 @@ namespace Barotrauma
subTextBlock.TextColor = new Color(subTextBlock.TextColor, 0.5f);
frame.ToolTip = TextManager.Get("SubNotFound");
}
else if (matchingSub.MD5Hash.Hash != sub.MD5Hash.Hash)
else if (matchingSub?.MD5Hash == null || matchingSub.MD5Hash?.Hash != sub.MD5Hash?.Hash)
{
subTextBlock.TextColor = new Color(subTextBlock.TextColor, 0.5f);
frame.ToolTip = TextManager.Get("SubDoesntMatch");
@@ -1383,25 +1383,44 @@ namespace Barotrauma
OnClicked = (btn, userdata) => { if (GUI.MouseOn == btn || GUI.MouseOn == btn.TextBlock) ClosePlayerFrame(btn, userdata); return true; }
};
Vector2 frameSize = GameMain.Client.HasPermission(ClientPermissions.ManagePermissions) ? new Vector2(.24f, .44f) : new Vector2(.24f, .24f);
Vector2 frameSize = GameMain.Client.HasPermission(ClientPermissions.ManagePermissions) ? new Vector2(.24f, .5f) : new Vector2(.24f, .24f);
var playerFrameInner = new GUIFrame(new RectTransform(frameSize, playerFrame.RectTransform, Anchor.Center));
var paddedPlayerFrame = new GUILayoutGroup(new RectTransform(new Vector2(0.9f, 0.85f), playerFrameInner.RectTransform, Anchor.Center))
var playerFrameInner = new GUIFrame(new RectTransform(frameSize, playerFrame.RectTransform, Anchor.Center) { MinSize = new Point(550, 0) });
var paddedPlayerFrame = new GUILayoutGroup(new RectTransform(new Vector2(0.9f, 0.88f), playerFrameInner.RectTransform, Anchor.Center))
{
Stretch = true,
RelativeSpacing = 0.05f
RelativeSpacing = 0.03f
};
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform),
var headerContainer = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform), isHorizontal: true)
{
Stretch = true
};
var nameText = new GUITextBlock(new RectTransform(new Vector2(0.75f, 1.0f), headerContainer.RectTransform),
text: selectedClient.Name, font: GUI.LargeFont);
//TODO: UI for client permission management
if (selectedClient.SteamID != 0 && Steam.SteamManager.IsInitialized)
{
var viewSteamProfileButton = new GUIButton(new RectTransform(new Vector2(0.25f, 1.0f), headerContainer.RectTransform, Anchor.TopCenter),
TextManager.Get("ViewSteamProfile"))
{
UserData = selectedClient
};
GUITextBlock.AutoScaleAndNormalize(nameText, viewSteamProfileButton.TextBlock);
viewSteamProfileButton.OnClicked = (bt, userdata) =>
{
Steam.SteamManager.Instance.Overlay.OpenUrl("https://steamcommunity.com/profiles/" + selectedClient.SteamID.ToString());
return true;
};
}
if (GameMain.Client.HasPermission(ClientPermissions.ManagePermissions))
{
playerFrame.UserData = selectedClient;
//new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform), selectedClient.Connection.RemoteEndPoint.Address.ToString());
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), paddedPlayerFrame.RectTransform),
TextManager.Get("Rank"));
var rankDropDown = new GUIDropDown(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform),
@@ -1441,16 +1460,45 @@ namespace Barotrauma
Stretch = true,
RelativeSpacing = 0.05f
};
new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), permissionLabels.RectTransform), TextManager.Get("Permissions"));
new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), permissionLabels.RectTransform), TextManager.Get("PermittedConsoleCommands"));
var permissionLabel = new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), permissionLabels.RectTransform), TextManager.Get("Permissions"));
var consoleCommandLabel = new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), permissionLabels.RectTransform), TextManager.Get("PermittedConsoleCommands"));
GUITextBlock.AutoScaleAndNormalize(permissionLabel, consoleCommandLabel);
var permissionContainer = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.4f), paddedPlayerFrame.RectTransform), isHorizontal: true)
{
Stretch = true,
RelativeSpacing = 0.05f
};
var permissionsBox = new GUIListBox(new RectTransform(new Vector2(0.5f, 1.0f), permissionContainer.RectTransform))
var listBoxContainerLeft = new GUILayoutGroup(new RectTransform(new Vector2(0.5f, 1.0f), permissionContainer.RectTransform))
{
Stretch = true,
RelativeSpacing = 0.05f
};
new GUITickBox(new RectTransform(new Vector2(0.15f, 0.15f), listBoxContainerLeft.RectTransform), TextManager.Get("all", fallBackTag: "clientpermission.all"))
{
Enabled = !myClient,
OnSelected = (tickbox) =>
{
//reset rank to custom
rankDropDown.SelectItem(null);
var client = playerFrame.UserData as Client;
if (client == null) { return false; }
foreach (GUIComponent child in tickbox.Parent.GetChild<GUIListBox>().Content.Children)
{
var permissionTickBox = child as GUITickBox;
permissionTickBox.Enabled = false;
permissionTickBox.Selected = tickbox.Selected;
permissionTickBox.Enabled = true;
}
GameMain.Client.UpdateClientPermissions(client);
return true;
}
};
var permissionsBox = new GUIListBox(new RectTransform(new Vector2(1.0f, 1.0f), listBoxContainerLeft.RectTransform))
{
UserData = selectedClient
};
@@ -1471,10 +1519,9 @@ namespace Barotrauma
rankDropDown.SelectItem(null);
var client = playerFrame.UserData as Client;
if (client == null) return false;
if (client == null) { return false; }
var thisPermission = (ClientPermissions)tickBox.UserData;
if (tickBox.Selected)
{
client.GivePermission(thisPermission);
@@ -1483,15 +1530,44 @@ namespace Barotrauma
{
client.RemovePermission(thisPermission);
}
GameMain.Client.UpdateClientPermissions(client);
if (tickBox.Enabled)
{
GameMain.Client.UpdateClientPermissions(client);
}
return true;
}
};
}
var commandList = new GUIListBox(new RectTransform(new Vector2(0.5f, 1.0f), permissionContainer.RectTransform))
var listBoxContainerRight = new GUILayoutGroup(new RectTransform(new Vector2(0.5f, 1.0f), permissionContainer.RectTransform))
{
Stretch = true,
RelativeSpacing = 0.05f
};
new GUITickBox(new RectTransform(new Vector2(0.15f, 0.15f), listBoxContainerRight.RectTransform), TextManager.Get("all", fallBackTag: "clientpermission.all"))
{
Enabled = !myClient,
OnSelected = (tickbox) =>
{
//reset rank to custom
rankDropDown.SelectItem(null);
var client = playerFrame.UserData as Client;
if (client == null) { return false; }
foreach (GUIComponent child in tickbox.Parent.GetChild<GUIListBox>().Content.Children)
{
var commandTickBox = child as GUITickBox;
commandTickBox.Enabled = false;
commandTickBox.Selected = tickbox.Selected;
commandTickBox.Enabled = true;
}
GameMain.Client.UpdateClientPermissions(client);
return true;
}
};
var commandList = new GUIListBox(new RectTransform(new Vector2(1.0f, 1.0f), listBoxContainerRight.RectTransform))
{
UserData = selectedClient
};
@@ -1522,37 +1598,23 @@ namespace Barotrauma
{
client.PermittedConsoleCommands.Add(selectedCommand);
}
GameMain.Client.UpdateClientPermissions(client);
if (tickBox.Enabled)
{
GameMain.Client.UpdateClientPermissions(client);
}
return true;
};
}
}
var buttonAreaUpper = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform), isHorizontal: true);
var buttonAreaMiddle = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform), isHorizontal: true);
var buttonAreaLower = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.1f), paddedPlayerFrame.RectTransform), isHorizontal: true);
if (selectedClient.SteamID != 0 && Steam.SteamManager.IsInitialized)
{
var viewSteamProfileButton = new GUIButton(new RectTransform(new Vector2(0.8f, 1.0f), buttonAreaUpper.RectTransform, Anchor.TopCenter),
TextManager.Get("ViewSteamProfile"))
{
UserData = selectedClient
};
viewSteamProfileButton.OnClicked = (bt, userdata) =>
{
Steam.SteamManager.Instance.Overlay.OpenUrl("https://steamcommunity.com/profiles/" + selectedClient.SteamID.ToString());
return true;
};
}
var buttonAreaTop = myClient ? null : new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.08f), paddedPlayerFrame.RectTransform), isHorizontal: true);
var buttonAreaLower = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.08f), paddedPlayerFrame.RectTransform), isHorizontal: true);
if (!myClient)
{
if (GameMain.Client.HasPermission(ClientPermissions.Ban))
{
var banButton = new GUIButton(new RectTransform(new Vector2(0.3f, 1.0f), buttonAreaMiddle.RectTransform),
var banButton = new GUIButton(new RectTransform(new Vector2(0.3f, 1.0f), buttonAreaTop.RectTransform),
TextManager.Get("Ban"))
{
UserData = selectedClient
@@ -1560,7 +1622,7 @@ namespace Barotrauma
banButton.OnClicked = (bt, userdata) => { BanPlayer(selectedClient); return true; };
banButton.OnClicked += ClosePlayerFrame;
var rangebanButton = new GUIButton(new RectTransform(new Vector2(0.3f, 1.0f), buttonAreaMiddle.RectTransform),
var rangebanButton = new GUIButton(new RectTransform(new Vector2(0.3f, 1.0f), buttonAreaTop.RectTransform),
TextManager.Get("BanRange"))
{
UserData = selectedClient
@@ -1594,7 +1656,7 @@ namespace Barotrauma
kickButton.OnClicked += ClosePlayerFrame;
}
new GUITickBox(new RectTransform(new Vector2(0.25f, 1.0f), buttonAreaMiddle.RectTransform, Anchor.TopRight),
new GUITickBox(new RectTransform(new Vector2(0.25f, 1.0f), buttonAreaTop.RectTransform, Anchor.TopRight),
TextManager.Get("Mute"))
{
IgnoreLayoutGroups = true,
@@ -1982,24 +2044,34 @@ namespace Barotrauma
public bool TrySelectSub(string subName, string md5Hash, GUIListBox subList)
{
if (GameMain.Client == null) return false;
if (GameMain.Client == null) { return false; }
//already downloading the selected sub file
if (GameMain.Client.FileReceiver.ActiveTransfers.Any(t => t.FileName == subName + ".sub"))
{
return false;
}
Submarine sub = subList.Content.Children
.FirstOrDefault(c => c.UserData is Submarine s && s.Name == subName && s.MD5Hash?.Hash == md5Hash)?
.UserData as Submarine;
Submarine sub = Submarine.SavedSubmarines.FirstOrDefault(m => m.Name == subName && m.MD5Hash.Hash == md5Hash);
if (sub == null) sub = Submarine.SavedSubmarines.FirstOrDefault(m => m.Name == subName);
var matchingListSub = subList.Content.GetChildByUserData(sub);
if (sub != null && subList.SelectedData as Submarine == sub)
//matching sub found and already selected, all good
if (sub != null && subList.SelectedData is Submarine selectedSub && selectedSub.MD5Hash?.Hash == md5Hash)
{
return true;
}
if (matchingListSub != null)
//sub not found, see if we have a sub with the same name
if (sub == null)
{
sub = subList.Content.Children
.FirstOrDefault(c => c.UserData is Submarine s && s.Name == subName)?
.UserData as Submarine;
}
//found a sub that at least has the same name, select it
if (sub != null)
{
if (subList.Parent is GUIDropDown subDropDown)
{
@@ -2008,7 +2080,7 @@ namespace Barotrauma
else
{
subList.OnSelected -= VotableClicked;
subList.Select(subList.Content.GetChildIndex(matchingListSub), true);
subList.Select(sub, force: true);
subList.OnSelected += VotableClicked;
}
@@ -2016,58 +2088,62 @@ namespace Barotrauma
FailedSelectedSub = null;
else
FailedSelectedShuttle = null;
//hashes match, all good
if (sub.MD5Hash?.Hash == md5Hash)
{
return true;
}
}
//-------------------------------------------------------------------------------------
//if we get to this point, a matching sub was not found or it has an incorrect MD5 hash
if (subList == SubList)
FailedSelectedSub = new Pair<string, string>(subName, md5Hash);
else
FailedSelectedShuttle = new Pair<string, string>(subName, md5Hash);
string errorMsg = "";
if (sub == null)
{
errorMsg = TextManager.GetWithVariable("SubNotFoundError", "[subname]", subName) + " ";
}
else if (sub.MD5Hash?.Hash == null)
{
errorMsg = TextManager.GetWithVariable("SubLoadError", "[subname]", subName) + " ";
subList.Content.GetChildByUserData(sub).GetChild<GUITextBox>().TextColor = Color.Red;
}
else
{
errorMsg = TextManager.GetWithVariables("SubDoesntMatchError", new string[3] { "[subname]" , "[myhash]", "[serverhash]" },
new string[3] { sub.Name, sub.MD5Hash.ShortHash, Md5Hash.GetShortHash(md5Hash) }) + " ";
}
if (sub == null || sub.MD5Hash.Hash != md5Hash)
errorMsg += TextManager.Get("DownloadSubQuestion");
//already showing a message about the same sub
if (GUIMessageBox.MessageBoxes.Any(mb => mb.UserData as string == "request" + subName))
{
if (subList == SubList)
FailedSelectedSub = new Pair<string, string>(subName, md5Hash);
else
FailedSelectedShuttle = new Pair<string, string>(subName, md5Hash);
string errorMsg = "";
if (sub == null)
{
errorMsg = TextManager.GetWithVariable("SubNotFoundError", "[subname]", subName) + " ";
}
else if (sub.MD5Hash.Hash == null)
{
errorMsg = TextManager.GetWithVariable("SubLoadError", "[subname]", subName) + " ";
if (matchingListSub != null) matchingListSub.GetChild<GUITextBox>().TextColor = Color.Red;
}
else
{
errorMsg = TextManager.GetWithVariables("SubDoesntMatchError", new string[3] { "[subname]" , "[myhash]", "[serverhash]" },
new string[3] { sub.Name, sub.MD5Hash.ShortHash, Md5Hash.GetShortHash(md5Hash) }) + " ";
}
errorMsg += TextManager.Get("DownloadSubQuestion");
//already showing a message about the same sub
if (GUIMessageBox.MessageBoxes.Any(mb => mb.UserData as string == "request" + subName))
{
return false;
}
var requestFileBox = new GUIMessageBox(TextManager.Get("DownloadSubLabel"), errorMsg,
new string[] { TextManager.Get("Yes"), TextManager.Get("No") })
{
UserData = "request" + subName
};
requestFileBox.Buttons[0].UserData = new string[] { subName, md5Hash };
requestFileBox.Buttons[0].OnClicked += requestFileBox.Close;
requestFileBox.Buttons[0].OnClicked += (GUIButton button, object userdata) =>
{
string[] fileInfo = (string[])userdata;
GameMain.Client?.RequestFile(FileTransferType.Submarine, fileInfo[0], fileInfo[1]);
return true;
};
requestFileBox.Buttons[1].OnClicked += requestFileBox.Close;
return false;
}
return true;
var requestFileBox = new GUIMessageBox(TextManager.Get("DownloadSubLabel"), errorMsg,
new string[] { TextManager.Get("Yes"), TextManager.Get("No") })
{
UserData = "request" + subName
};
requestFileBox.Buttons[0].UserData = new string[] { subName, md5Hash };
requestFileBox.Buttons[0].OnClicked += requestFileBox.Close;
requestFileBox.Buttons[0].OnClicked += (GUIButton button, object userdata) =>
{
string[] fileInfo = (string[])userdata;
GameMain.Client?.RequestFile(FileTransferType.Submarine, fileInfo[0], fileInfo[1]);
return true;
};
requestFileBox.Buttons[1].OnClicked += requestFileBox.Close;
return false;
}
}
@@ -1297,13 +1297,13 @@ namespace Barotrauma
string modFolder = Path.GetDirectoryName(itemContentPackage.Path);
string filePathRelativeToModFolder = UpdaterUtil.GetRelativePath(file, Path.Combine(Environment.CurrentDirectory, modFolder));
string destinationPath = Path.Combine(modFolder, Path.GetFileName(file));
string destinationPath;
//file is not inside the mod folder, we need to move it
if (filePathRelativeToModFolder.StartsWith("..") ||
Path.GetPathRoot(Environment.CurrentDirectory) != Path.GetPathRoot(file))
{
string tryPath = destinationPath;
destinationPath = Path.Combine(modFolder, Path.GetFileName(file));
//add a number to the filename if a file with the same name already exists
i = 2;
while (File.Exists(destinationPath))
@@ -1317,10 +1317,14 @@ namespace Barotrauma
}
catch (Exception e)
{
DebugConsole.ThrowError("Copying the file \""+file+"\" to the mod folder failed.", e);
DebugConsole.ThrowError("Copying the file \"" + file + "\" to the mod folder failed.", e);
return;
}
}
else
{
destinationPath = Path.Combine(modFolder, filePathRelativeToModFolder);
}
itemContentPackage.AddFile(destinationPath, ContentType.None);
}
itemContentPackage.Save(itemContentPackage.Path);
@@ -23,7 +23,7 @@ namespace Barotrauma
"CrewExperienceHigh"
};
private readonly Point defaultPreviewImageSize = new Point(512, 368);
private readonly Point defaultPreviewImageSize = new Point(640, 368);
private Camera cam;
@@ -158,7 +158,26 @@ namespace Barotrauma
var button = new GUIButton(new RectTransform(new Vector2(0.07f, 0.9f), paddedTopPanel.RectTransform, Anchor.CenterLeft), TextManager.Get("Back"))
{
OnClicked = GameMain.MainMenuScreen.ReturnToMainMenu
OnClicked = (b, d) =>
{
var msgBox = new GUIMessageBox("", TextManager.Get("PauseMenuQuitVerificationEditor"), new string[] { TextManager.Get("Yes"), TextManager.Get("Cancel") })
{
UserData = "verificationprompt"
};
msgBox.Buttons[0].OnClicked = (yesBtn, userdata) =>
{
GUIMessageBox.CloseAll();
GameMain.MainMenuScreen.Select();
return true;
};
msgBox.Buttons[0].OnClicked += msgBox.Close;
msgBox.Buttons[1].OnClicked = (_, userdata) =>
{
msgBox.Close();
return true;
};
return true;
}
};
button = new GUIButton(new RectTransform(new Vector2(0.07f, 0.9f), paddedTopPanel.RectTransform, Anchor.CenterLeft) { RelativeOffset = new Vector2(0.07f, 0.0f) }, TextManager.Get("OpenSubButton"))
@@ -497,9 +516,8 @@ namespace Barotrauma
foreach (MapEntityPrefab ep in MapEntityPrefab.List)
{
var itemAssemblyPrefab = ep as ItemAssemblyPrefab;
#if !DEBUG
if (itemAssemblyPrefab != null && itemAssemblyPrefab.HideInMenus) { continue; }
if (ep.HideInMenus) { continue; }
#endif
bool legacy = ep.Category == MapEntityCategory.Legacy;
@@ -548,7 +566,7 @@ namespace Barotrauma
};
}
if (ep.Category == MapEntityCategory.ItemAssembly)
if (ep is ItemAssemblyPrefab itemAssemblyPrefab)
{
new GUICustomComponent(new RectTransform(new Vector2(1.0f, 0.75f),
paddedFrame.RectTransform, Anchor.TopCenter), onDraw: itemAssemblyPrefab.DrawIcon, onUpdate: null)
@@ -2448,7 +2466,7 @@ namespace Barotrauma
Matrix.CreateScale(new Vector3(scale, scale, 1)) *
viewMatrix;
Sprite backgroundSprite = LevelGenerationParams.LevelParams.Find(l => l.BackgroundTopSprite != null).BackgroundTopSprite;
/*Sprite backgroundSprite = LevelGenerationParams.LevelParams.Find(l => l.BackgroundTopSprite != null).BackgroundTopSprite;*/
using (RenderTarget2D rt = new RenderTarget2D(
GameMain.Instance.GraphicsDevice,
@@ -2457,14 +2475,14 @@ namespace Barotrauma
{
GameMain.Instance.GraphicsDevice.SetRenderTarget(rt);
GameMain.Instance.GraphicsDevice.Clear(Color.Black);
GameMain.Instance.GraphicsDevice.Clear(new Color(8, 13, 19));
if (backgroundSprite != null)
/*if (backgroundSprite != null)
{
spriteBatch.Begin();
backgroundSprite.DrawTiled(spriteBatch, Vector2.Zero, new Vector2(width, height), color: new Color(0.025f, 0.075f, 0.131f, 1.0f));
spriteBatch.End();
}
}*/
spriteBatch.Begin(SpriteSortMode.BackToFront, BlendState.AlphaBlend, null, null, null, null, transform);
Submarine.Draw(spriteBatch, false);
@@ -484,12 +484,19 @@ namespace Barotrauma
public static SoundChannel PlaySound(string soundTag, Vector2 position, float? volume = null, float? range = null, Hull hullGuess = null)
{
var sound = GetSound(soundTag);
if (sound == null) return null;
if (sound == null) { return null; }
return PlaySound(sound, position, volume ?? sound.BaseGain, range ?? sound.BaseFar, hullGuess);
}
public static SoundChannel PlaySound(Sound sound, Vector2 position, float? volume = null, float? range = null, Hull hullGuess = null)
{
if (sound == null)
{
string errorMsg = "Error in SoundPlayer.PlaySound (sound was null)\n" + Environment.StackTrace;
GameAnalyticsManager.AddErrorEventOnce("SoundPlayer.PlaySound:SoundNull" + Environment.StackTrace, GameAnalyticsSDK.Net.EGAErrorSeverity.Error, errorMsg);
return null;
}
float far = range ?? sound.BaseFar;
if (Vector2.DistanceSquared(new Vector2(GameMain.SoundManager.ListenerPosition.X, GameMain.SoundManager.ListenerPosition.Y), position) > far * far) return null;
@@ -35,7 +35,7 @@ namespace Barotrauma
break;
case "sound":
var sound = Submarine.LoadRoundSound(subElement);
if (sound != null)
if (sound?.Sound != null)
{
loopSound = subElement.GetAttributeBool("loop", false);
if (subElement.Attribute("selectionmode") != null)