(bf212a41f) v0.9.2.0 pre-release test version

This commit is contained in:
Joonas Rikkonen
2019-07-27 21:06:07 +03:00
parent afa2137bd2
commit 0f63da27b2
154 changed files with 3959 additions and 1428 deletions
+17 -1
View File
@@ -1,4 +1,6 @@
using Microsoft.Xna.Framework;
using Barotrauma.Networking;
using Lidgren.Network;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Input;
using System;
@@ -171,6 +173,11 @@ namespace Barotrauma
get { return targetPos; }
set { targetPos = value; }
}
public Vector2 GetPosition()
{
return position;
}
// Auxiliary function to move the camera
public void Translate(Vector2 amount)
@@ -178,6 +185,15 @@ namespace Barotrauma
position += amount;
}
public void ClientWrite(NetOutgoingMessage msg)
{
if (Character.Controlled != null && !Character.Controlled.IsDead) return;
msg.Write((byte)ClientNetObject.SPECTATING_POS);
msg.Write(position.X);
msg.Write(position.Y);
}
private void CreateMatrices()
{
resolution = new Point(GameMain.GraphicsWidth, GameMain.GraphicsHeight);
@@ -14,6 +14,13 @@ namespace Barotrauma
{
if (this != Controlled)
{
if (GameMain.Client.EndCinematic != null) // Freezes the characters during the ending cinematic
{
AnimController.Frozen = true;
memState.Clear();
return;
}
//freeze AI characters if more than 1 seconds have passed since last update from the server
if (lastRecvPositionUpdateTime < NetTime.Now - 1.0f)
{
@@ -128,6 +128,7 @@ namespace Barotrauma
}
public WearableSprite HuskSprite { get; private set; }
public WearableSprite HerpesSprite { get; private set; }
public void LoadHuskSprite()
{
@@ -139,6 +140,16 @@ namespace Barotrauma
HuskSprite = new WearableSprite(element.Element("sprite"), WearableType.Husk);
}
}
public void LoadHerpesSprite()
{
var info = character.Info;
if (info == null) { return; }
var element = info.FilterByTypeAndHeadID(character.Info.FilterElementsByGenderAndRace(character.Info.Wearables), WearableType.Herpes).FirstOrDefault();
if (element != null)
{
HerpesSprite = new WearableSprite(element.Element("sprite"), WearableType.Herpes);
}
}
public float TextureScale => limbParams.Ragdoll.TextureScale;
@@ -387,7 +398,7 @@ namespace Barotrauma
color *= SeveredFadeOutTime - severedFadeOutTimer;
}
}
body.Dir = Dir;
bool hideLimb = wearingItems.Any(w => w != null && w.HideLimb);
@@ -425,10 +436,20 @@ namespace Barotrauma
SpriteEffects spriteEffect = (dir == Direction.Right) ? SpriteEffects.None : SpriteEffects.FlipHorizontally;
if (onlyDrawable == null)
{
if (HerpesSprite != null)
{
float herpesStrength = character.CharacterHealth.GetAfflictionStrength("spaceherpes");
if (herpesStrength > 0.0f)
{
DrawWearable(HerpesSprite, depthStep, spriteBatch, color * (herpesStrength / 100.0f), spriteEffect);
depthStep += 0.000001f;
}
}
if (HuskSprite != null && (character.SpeciesName == "Humanhusk" || (character.SpeciesName == "Human" &&
character.CharacterHealth.GetAffliction<AfflictionHusk>("huskinfection")?.State == AfflictionHusk.InfectionState.Active)))
{
DrawWearable(HuskSprite, depthStep, spriteBatch, color, spriteEffect);
depthStep += 0.000001f;
}
foreach (WearableSprite wearable in OtherWearables)
{
@@ -585,6 +606,9 @@ namespace Barotrauma
HuskSprite?.Sprite.Remove();
HuskSprite = null;
HerpesSprite?.Sprite.Remove();
HerpesSprite = null;
}
}
}
@@ -133,17 +133,7 @@ namespace Barotrauma
if (PlayerInput.KeyHit(Keys.F3))
{
isOpen = !isOpen;
if (isOpen)
{
textBox.Select();
AddToGUIUpdateList();
}
else
{
GUI.ForceMouseOn(null);
textBox.Deselect();
}
Toggle();
}
else if (isOpen && PlayerInput.KeyHit(Keys.Escape))
{
@@ -179,6 +169,21 @@ namespace Barotrauma
}
}
public static void Toggle()
{
isOpen = !isOpen;
if (isOpen)
{
textBox.Select();
AddToGUIUpdateList();
}
else
{
GUI.ForceMouseOn(null);
textBox.Deselect();
}
}
public static void Draw(SpriteBatch spriteBatch)
{
if (!isOpen) return;
@@ -298,9 +303,16 @@ namespace Barotrauma
private static void AssignOnClientExecute(string names, Action<string[]> onClientExecute)
{
Command command = commands.First(c => c.names.Intersect(names.Split('|')).Count() > 0);
command.OnClientExecute = onClientExecute;
command.RelayToServer = false;
Command command = commands.Find(c => c.names.Intersect(names.Split('|')).Count() > 0);
if (command == null)
{
throw new Exception("AssignOnClientExecute failed. Command matching the name(s) \"" + names + "\" not found.");
}
else
{
command.OnClientExecute = onClientExecute;
command.RelayToServer = false;
}
}
private static void AssignRelayToServer(string names, bool relay)
@@ -1797,6 +1809,11 @@ namespace Barotrauma
limb.HuskSprite.Sprite.ReloadXML();
limb.HuskSprite.Sprite.ReloadTexture();
}
if (limb.HerpesSprite != null)
{
limb.HerpesSprite.Sprite.ReloadXML();
limb.HerpesSprite.Sprite.ReloadTexture();
}
}
}
@@ -278,7 +278,7 @@ namespace Barotrauma
Color.White, Color.Black * 0.5f, 0, SmallFont);
DrawString(spriteBatch, new Vector2(10, 40),
"Bodies: " + GameMain.World.BodyList.Count + " (" + GameMain.World.BodyList.FindAll(b => b.Awake && b.Enabled).Count + " awake)",
$"Bodies: {GameMain.World.BodyList.Count} ({GameMain.World.BodyList.FindAll(b => b.Awake && b.Enabled).Count} awake, {GameMain.World.BodyList.FindAll(b => b.Awake && b.BodyType == FarseerPhysics.Dynamics.BodyType.Dynamic && b.Enabled).Count} dynamic)",
Color.White, Color.Black * 0.5f, 0, SmallFont);
if (Screen.Selected.Cam != null)
@@ -1040,6 +1040,8 @@ namespace Barotrauma
public static Texture2D CreateRectangle(int width, int height)
{
width = Math.Max(width, 1);
height = Math.Max(height, 1);
Color[] data = new Color[width * height];
for (int i = 0; i < data.Length; i++)
@@ -1057,7 +1059,6 @@ namespace Barotrauma
TrySetArray(data, (height - 1) * width + x, Color.White);
}
Texture2D texture = null;
CrossThread.RequestExecutionOnMainThread(() =>
{
@@ -178,25 +178,27 @@ namespace Barotrauma
}
else if (DrawLoadingText)
{
string loadText = "";
if (LoadState == 100.0f)
if (TextManager.Initialized)
{
loadText = TextManager.Get("PressAnyKey");
}
else
{
loadText = TextManager.Get("Loading");
if (LoadState != null)
string loadText;
if (LoadState == 100.0f)
{
loadText += " " + (int)LoadState + " %";
loadText = TextManager.Get("PressAnyKey");
}
else
{
loadText = TextManager.Get("Loading");
if (LoadState != null)
{
loadText += " " + (int)LoadState + " %";
}
}
if (GUI.LargeFont != null)
{
GUI.LargeFont.DrawString(spriteBatch, loadText.ToUpper(),
new Vector2(GameMain.GraphicsWidth / 2.0f - GUI.LargeFont.MeasureString(loadText).X / 2.0f, GameMain.GraphicsHeight * 0.7f),
Color.White);
}
}
if (GUI.LargeFont != null)
{
GUI.LargeFont.DrawString(spriteBatch, loadText.ToUpper(),
new Vector2(GameMain.GraphicsWidth / 2.0f - GUI.LargeFont.MeasureString(loadText).X / 2.0f, GameMain.GraphicsHeight * 0.7f),
Color.White);
}
if (GUI.Font != null && selectedTip != null)
@@ -58,6 +58,8 @@ namespace Barotrauma
public event Action<SpriteBatch, float> PreDraw;
public event Action<SpriteBatch, float> PostDraw;
public bool RequireMouseOn = true;
public Action refresh;
public object data;
@@ -109,7 +111,7 @@ namespace Barotrauma
{
PreUpdate?.Invoke(deltaTime);
if (!enabled) { return; }
if (IsMouseOver)
if (IsMouseOver || (!RequireMouseOn && selectedWidgets.Contains(this) && PlayerInput.LeftButtonHeld()))
{
Hovered?.Invoke();
if ((multiselect && !selectedWidgets.Contains(this)) || selectedWidgets.None())
+70 -55
View File
@@ -404,54 +404,13 @@ namespace Barotrauma
DebugConsole.Log("Selected content packages: " + string.Join(", ", SelectedPackages.Select(cp => cp.Name)));
}
/*#if DEBUG
#if DEBUG
GameSettings.ShowUserStatisticsPrompt = false;
GameSettings.SendUserStatistics = false;
#endif*/
#endif
InitUserStats();
yield return CoroutineStatus.Running;
LightManager = new Lights.LightManager(base.GraphicsDevice, Content);
TitleScreen.LoadState = 1.0f;
yield return CoroutineStatus.Running;
GUI.LoadContent();
TitleScreen.LoadState = 2.0f;
yield return CoroutineStatus.Running;
MissionPrefab.Init();
MapEntityPrefab.Init();
Tutorials.Tutorial.Init();
MapGenerationParams.Init();
LevelGenerationParams.LoadPresets();
ScriptedEventSet.LoadPrefabs();
AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
TitleScreen.LoadState = 10.0f;
yield return CoroutineStatus.Running;
StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
TitleScreen.LoadState = 15.0f;
yield return CoroutineStatus.Running;
ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
TitleScreen.LoadState = 25.0f;
yield return CoroutineStatus.Running;
JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
// Add any missing jobs from the prefab into Config.JobNamePreferences.
foreach (JobPrefab job in JobPrefab.List)
{
if (!Config.JobPreferences.Contains(job.Identifier)) { Config.JobPreferences.Add(job.Identifier); }
}
NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));
ItemAssemblyPrefab.LoadAll();
TitleScreen.LoadState = 30.0f;
yield return CoroutineStatus.Running;
Debug.WriteLine("sounds");
@@ -464,55 +423,105 @@ namespace Barotrauma
i++;
TitleScreen.LoadState = SoundPlayer.SoundCount == 0 ?
30.0f :
Math.Min(30.0f + 40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 70.0f);
1.0f :
Math.Min(40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 40.0f);
yield return CoroutineStatus.Running;
}
TitleScreen.LoadState = 70.0f;
TitleScreen.LoadState = 40.0f;
yield return CoroutineStatus.Running;
LightManager = new Lights.LightManager(base.GraphicsDevice, Content);
TitleScreen.LoadState = 41.0f;
yield return CoroutineStatus.Running;
GUI.LoadContent();
TitleScreen.LoadState = 42.0f;
yield return CoroutineStatus.Running;
MissionPrefab.Init();
MapEntityPrefab.Init();
Tutorials.Tutorial.Init();
MapGenerationParams.Init();
LevelGenerationParams.LoadPresets();
ScriptedEventSet.LoadPrefabs();
AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
TitleScreen.LoadState = 50.0f;
yield return CoroutineStatus.Running;
StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
TitleScreen.LoadState = 53.0f;
yield return CoroutineStatus.Running;
ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
TitleScreen.LoadState = 55.0f;
yield return CoroutineStatus.Running;
JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
// Add any missing jobs from the prefab into Config.JobNamePreferences.
foreach (JobPrefab job in JobPrefab.List)
{
if (!Config.JobPreferences.Contains(job.Identifier)) { Config.JobPreferences.Add(job.Identifier); }
}
NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));
ItemAssemblyPrefab.LoadAll();
TitleScreen.LoadState = 60.0f;
yield return CoroutineStatus.Running;
GameModePreset.Init();
Submarine.RefreshSavedSubs();
TitleScreen.LoadState = 80.0f;
TitleScreen.LoadState = 65.0f;
yield return CoroutineStatus.Running;
GameScreen = new GameScreen(GraphicsDeviceManager.GraphicsDevice, Content);
TitleScreen.LoadState = 90.0f;
TitleScreen.LoadState = 68.0f;
yield return CoroutineStatus.Running;
MainMenuScreen = new MainMenuScreen(this);
LobbyScreen = new LobbyScreen();
ServerListScreen = new ServerListScreen();
TitleScreen.LoadState = 70.0f;
yield return CoroutineStatus.Running;
if (SteamManager.USE_STEAM)
{
SteamWorkshopScreen = new SteamWorkshopScreen();
}
SubEditorScreen = new SubEditorScreen();
TitleScreen.LoadState = 75.0f;
yield return CoroutineStatus.Running;
ParticleEditorScreen = new ParticleEditorScreen();
TitleScreen.LoadState = 80.0f;
yield return CoroutineStatus.Running;
LevelEditorScreen = new LevelEditorScreen();
SpriteEditorScreen = new SpriteEditorScreen();
CharacterEditorScreen = new CharacterEditorScreen();
yield return CoroutineStatus.Running;
TitleScreen.LoadState = 95.0f;
TitleScreen.LoadState = 85.0f;
ParticleManager = new ParticleManager(GameScreen.Cam);
ParticleManager.LoadPrefabs();
TitleScreen.LoadState = 97.0f;
TitleScreen.LoadState = 88.0f;
LevelObjectPrefab.LoadAll();
DecalManager = new DecalManager();
TitleScreen.LoadState = 99.0f;
TitleScreen.LoadState = 90.0f;
yield return CoroutineStatus.Running;
DecalManager = new DecalManager();
LocationType.Init();
MainMenuScreen.Select();
@@ -634,6 +643,7 @@ namespace Barotrauma
PlayerInput.Update(Timing.Step);
if (loadingScreenOpen)
{
//reset accumulator if loading
@@ -641,6 +651,11 @@ namespace Barotrauma
// -> no pause caused by leftover time in the accumulator when starting a new shift
GameMain.ResetFrameTime();
if (!TitleScreen.PlayingSplashScreen)
{
SoundPlayer.Update((float)Timing.Step);
}
if (TitleScreen.LoadState >= 100.0f && !TitleScreen.PlayingSplashScreen &&
(!waitForKeyHit || ((PlayerInput.GetKeyboardState.GetPressedKeys().Length > 0 || PlayerInput.LeftButtonClicked()) && WindowActive)))
{
@@ -455,10 +455,14 @@ namespace Barotrauma
isHorizontal: true, childAnchor: Anchor.CenterLeft)
{
AbsoluteSpacing = (int)(10 * GUI.Scale),
UserData = "orderbuttons",
CanBeFocused = false
UserData = "orderbuttons"
};
var spacer = new GUIFrame(new RectTransform(new Point(spacing, orderButtonFrame.Rect.Height), frame.RectTransform)
{
AbsoluteOffset = new Point(characterInfoWidth, 0)
});
//listbox for holding the orders inappropriate for this character
//(so we can easily toggle their visibility)
var wrongOrderList = new GUIListBox(new RectTransform(new Point(50, orderButtonFrame.Rect.Height), orderButtonFrame.RectTransform), isHorizontal: true, style: null)
@@ -32,7 +32,6 @@ namespace Barotrauma.Tutorials
private LightComponent mechanic_thirdDoorLight;
private Structure mechanic_brokenWall_1;
private Hull mechanic_brokenhull_1;
private MotionSensor mechanic_ladderSensor;
// Room 4
private MotionSensor mechanic_craftingObjectiveSensor;
@@ -752,11 +752,11 @@ namespace Barotrauma
character.SelectedBy.Inventory != null)
{
//item is in the inventory of another character -> attempt to get the item from there
success = character.SelectedBy.Inventory.TryPutItem(item, Character.Controlled, item.AllowedSlots, true);
success = character.SelectedBy.Inventory.TryPutItemWithAutoEquipCheck(item, Character.Controlled, item.AllowedSlots, true);
}
break;
case QuickUseAction.TakeFromContainer:
success = TryPutItem(item, Character.Controlled, item.AllowedSlots, true);
success = TryPutItemWithAutoEquipCheck(item, Character.Controlled, item.AllowedSlots, true);
break;
}
@@ -182,7 +182,7 @@ namespace Barotrauma.Items.Components
}
partial void SetState(bool open, bool isNetworkMessage, bool sendNetworkMessage)
partial void SetState(bool open, bool isNetworkMessage, bool sendNetworkMessage, bool forcedOpen)
{
if (isStuck ||
(PredictedState == null && isOpen == open) ||
@@ -200,12 +200,16 @@ namespace Barotrauma.Items.Components
//sent by the server, or reverting it back to its old state if no msg from server was received
PredictedState = open;
resetPredictionTimer = CorrectionDelay;
if (stateChanged) PlaySound(ActionType.OnUse, item.WorldPosition);
if (stateChanged) PlaySound(forcedOpen ? ActionType.OnPicked : ActionType.OnUse, item.WorldPosition);
}
else
{
isOpen = open;
if (!isNetworkMessage || open != PredictedState) PlaySound(ActionType.OnUse, item.WorldPosition);
if (!isNetworkMessage || open != PredictedState)
{
StopPicking(null);
PlaySound(forcedOpen ? ActionType.OnPicked : ActionType.OnUse, item.WorldPosition);
}
}
//opening a partially stuck door makes it less stuck
@@ -217,7 +221,9 @@ namespace Barotrauma.Items.Components
{
base.ClientRead(type, msg, sendingTime);
SetState(msg.ReadBoolean(), isNetworkMessage: true, sendNetworkMessage: false);
bool open = msg.ReadBoolean();
bool forcedOpen = msg.ReadBoolean();
SetState(open, isNetworkMessage: true, sendNetworkMessage: false, forcedOpen: forcedOpen);
Stuck = msg.ReadRangedSingle(0.0f, 100.0f, 8);
PredictedState = null;
@@ -291,16 +291,16 @@ namespace Barotrauma.Items.Components
else
{
float volume = GetSoundVolume(itemSound);
if (volume <= 0.0f) return;
if (volume <= 0.0f) { return; }
SoundPlayer.PlaySound(itemSound.RoundSound.Sound, position, volume, itemSound.Range, item.CurrentHull);
}
}
public void StopSounds(ActionType type)
{
if (loopingSound == null) return;
if (loopingSound == null) { return; }
if (loopingSound.Type != type) return;
if (loopingSound.Type != type) { return; }
if (loopingSoundChannel != null)
{
@@ -25,12 +25,12 @@ namespace Barotrauma.Items.Components
{
noPowerTip = TextManager.Get("SteeringNoPowerTip");
GuiFrame.RectTransform.RelativeOffset = new Vector2(0.4f, 0.0f);
new GUICustomComponent(new RectTransform(new Vector2(0.9f, 0.85f), GuiFrame.RectTransform, Anchor.Center),
GuiFrame.RectTransform.RelativeOffset = new Vector2(0.05f, 0.0f);
new GUICustomComponent(new RectTransform(new Vector2(0.95f, 0.9f), GuiFrame.RectTransform, Anchor.Center),
DrawHUDBack, null);
submarineContainer = new GUIFrame(new RectTransform(new Vector2(0.9f, 0.85f), GuiFrame.RectTransform, Anchor.Center), style: null);
submarineContainer = new GUIFrame(new RectTransform(new Vector2(0.95f, 0.9f), GuiFrame.RectTransform, Anchor.Center), style: null);
new GUICustomComponent(new RectTransform(new Vector2(0.9f, 0.85f), GuiFrame.RectTransform, Anchor.Center),
new GUICustomComponent(new RectTransform(new Vector2(0.95f, 0.9f), GuiFrame.RectTransform, Anchor.Center),
DrawHUDFront, null)
{
CanBeFocused = false
@@ -179,11 +179,21 @@ namespace Barotrauma.Items.Components
GetLinkedHulls(hull, hullData.LinkedHulls);
hullDatas.Add(hull, hullData);
}
Color neutralColor = Color.DarkCyan;
if (hull.RoomName != null)
{
if (hull.RoomName.Contains("ballast") || hull.RoomName.Contains("Ballast") ||
hull.RoomName.Contains("airlock") || hull.RoomName.Contains("Airlock"))
{
neutralColor = new Color(9, 80, 159);
}
}
if (hullData.Distort)
{
hullFrame.Children.First().Color = Color.Lerp(Color.Black, Color.DarkGray * 0.5f, Rand.Range(0.0f, 1.0f));
hullFrame.Color = Color.DarkGray * 0.5f;
hullFrame.Color = neutralColor * 0.5f;
continue;
}
@@ -192,20 +202,23 @@ namespace Barotrauma.Items.Components
hullFrame.Parent.Rect.Width / (float)hull.Submarine.Borders.Width,
hullFrame.Parent.Rect.Height / (float)hull.Submarine.Borders.Height);
Color borderColor = Color.DarkCyan;
Color borderColor = neutralColor;
float? gapOpenSum = 0.0f;
if (ShowHullIntegrity)
{
gapOpenSum = hull.ConnectedGaps.Where(g => !g.IsRoomToRoom).Sum(g => g.Open);
borderColor = Color.Lerp(Color.DarkCyan, Color.Red, Math.Min((float)gapOpenSum, 1.0f));
borderColor = Color.Lerp(neutralColor, Color.Red, Math.Min((float)gapOpenSum, 1.0f));
}
float? oxygenAmount = null;
if (!RequireOxygenDetectors || hullData?.Oxygen != null)
{
oxygenAmount = RequireOxygenDetectors ? hullData.Oxygen : hull.OxygenPercentage;
GUI.DrawRectangle(spriteBatch, hullFrame.Rect, Color.Lerp(Color.Red * 0.5f, Color.Green * 0.3f, (float)oxygenAmount / 100.0f), true);
GUI.DrawRectangle(
spriteBatch, hullFrame.Rect,
Color.Lerp(Color.Red * 0.5f, Color.Green * 0.3f, (float)oxygenAmount / 100.0f),
true);
}
float? waterAmount = null;
@@ -234,7 +247,7 @@ namespace Barotrauma.Items.Components
}
else
{
hullFrame.Children.First().Color = Color.DarkCyan * 0.8f;
hullFrame.Children.First().Color = neutralColor * 0.8f;
}
if (mouseOnHull == hull)
@@ -291,8 +304,6 @@ namespace Barotrauma.Items.Components
GUI.DrawLine(spriteBatch, center + start, center + end, Color.DarkCyan * Rand.Range(0.3f, 0.35f), width: (int)(10 * GUI.Scale));
}
}
}
private void GetLinkedHulls(Hull hull, List<Hull> linkedHulls)
@@ -58,6 +58,10 @@ namespace Barotrauma.Items.Components
private GUIFrame inventoryContainer;
private GUIComponent leftHUDColumn;
private GUIComponent midHUDColumn;
private GUIComponent rightHUDColumn;
private GUILayoutGroup sliderControlsContainer;
private Dictionary<string, GUIButton> warningButtons = new Dictionary<string, GUIButton>();
@@ -107,11 +111,13 @@ namespace Barotrauma.Items.Components
RelativeSpacing = 0.012f,
Stretch = true
};
GUIFrame columnLeft = new GUIFrame(new RectTransform(new Vector2(0.25f, 1.0f), paddedFrame.RectTransform), style: null);
leftHUDColumn = columnLeft;
GUIFrame columnMid = new GUIFrame(new RectTransform(new Vector2(0.45f, 1.0f), paddedFrame.RectTransform), style: null);
GUIFrame columnRight = new GUIFrame(new RectTransform(new Vector2(0.3f, 1.0f), paddedFrame.RectTransform), style: null);
leftHUDColumn = columnLeft;
midHUDColumn = columnMid;
rightHUDColumn = columnRight;
//----------------------------------------------------------
//left column
@@ -180,9 +186,16 @@ namespace Barotrauma.Items.Components
ToolTip = TextManager.Get("ReactorTipTurbineOutput")
};
new GUITextBlock(new RectTransform(new Point(0, (int)(20 * GUI.Scale)), columnMid.RectTransform, Anchor.BottomLeft) { AbsoluteOffset = new Point(0, (int)(90 * GUI.Scale)) },
GUILayoutGroup sliderControls = new GUILayoutGroup(new RectTransform(new Point(columnMid.Rect.Width, (int)(114 * GUI.Scale)), columnMid.RectTransform, Anchor.BottomCenter))
{
Stretch = true,
AbsoluteSpacing = (int)(5 * GUI.Scale)
};
sliderControlsContainer = sliderControls;
new GUITextBlock(new RectTransform(new Point(0, (int)(20 * GUI.Scale)), sliderControls.RectTransform, Anchor.TopLeft),
TextManager.Get("ReactorFissionRate"));
fissionRateScrollBar = new GUIScrollBar(new RectTransform(new Point(columnMid.Rect.Width, (int)(30 * GUI.Scale)), columnMid.RectTransform, Anchor.BottomCenter) { AbsoluteOffset = new Point(0, (int)(60 * GUI.Scale)) },
fissionRateScrollBar = new GUIScrollBar(new RectTransform(new Point(sliderControls.Rect.Width, (int)(30 * GUI.Scale)), sliderControls.RectTransform, Anchor.TopCenter),
style: "GUISlider", barSize: 0.1f)
{
OnMoved = (GUIScrollBar bar, float scrollAmount) =>
@@ -194,10 +207,10 @@ namespace Barotrauma.Items.Components
return false;
}
};
new GUITextBlock(new RectTransform(new Point(0, (int)(20 * GUI.Scale)), columnMid.RectTransform, Anchor.BottomLeft) { AbsoluteOffset = new Point(0, (int)(30 * GUI.Scale)) },
new GUITextBlock(new RectTransform(new Point(0, (int)(20 * GUI.Scale)), sliderControls.RectTransform, Anchor.BottomLeft),
TextManager.Get("ReactorTurbineOutput"));
turbineOutputScrollBar = new GUIScrollBar(new RectTransform(new Point(columnMid.Rect.Width, (int)(30 * GUI.Scale)), columnMid.RectTransform, Anchor.BottomCenter),
turbineOutputScrollBar = new GUIScrollBar(new RectTransform(new Point(sliderControls.Rect.Width, (int)(30 * GUI.Scale)), sliderControls.RectTransform, Anchor.BottomCenter),
style: "GUISlider", barSize: 0.1f, isHorizontal: true)
{
OnMoved = (GUIScrollBar bar, float scrollAmount) =>
@@ -263,11 +276,11 @@ namespace Barotrauma.Items.Components
"Load", textColor: Color.LightBlue, textAlignment: Alignment.CenterLeft)
{
ToolTip = TextManager.Get("ReactorTipLoad")
};
};
string loadStr = TextManager.Get("ReactorLoad");
loadText.TextGetter += () => { return loadStr.Replace("[kw]", ((int)load).ToString()); };
var outputText = new GUITextBlock(new RectTransform(textSize, graphArea.RectTransform, Anchor.BottomLeft, Pivot.TopLeft),
var outputText = new GUITextBlock(new RectTransform(textSize, graphArea.RectTransform, Anchor.BottomLeft, Pivot.TopLeft),
"Output", textColor: Color.LightGreen, textAlignment: Alignment.CenterLeft)
{
ToolTip = TextManager.Get("ReactorTipPower")
@@ -321,9 +334,9 @@ namespace Barotrauma.Items.Components
if (temperature > optimalTemperature.Y)
{
GUI.DrawRectangle(spriteBatch,
new Vector2(graphArea.X - 30, graphArea.Y),
new Vector2(tempMeterFrame.SourceRect.Width, (graphArea.Bottom - graphArea.Height * optimalTemperature.Y / 100.0f) - graphArea.Y),
GUI.DrawRectangle(spriteBatch,
new Vector2(graphArea.X - 30, graphArea.Y),
new Vector2(tempMeterFrame.SourceRect.Width, (graphArea.Bottom - graphArea.Height * optimalTemperature.Y / 100.0f) - graphArea.Y),
Color.Red * (float)Math.Sin(Timing.TotalTime * 5.0f) * 0.7f, isFilled: true);
}
if (temperature < optimalTemperature.X)
@@ -415,15 +428,52 @@ namespace Barotrauma.Items.Components
warningButtons["ReactorWarningLowFuel"].Selected = prevAvailableFuel < fissionRate && lightOn;
warningButtons["ReactorWarningMeltdown"].Selected = meltDownTimer > MeltdownDelay * 0.5f || item.Condition == 0.0f && lightOn;
warningButtons["ReactorWarningSCRAM"].Selected = temperature > 0.1f && onOffSwitch.BarScroll > 0.5f;
AutoTemp = autoTempSlider.BarScroll < 0.5f;
shutDown = onOffSwitch.BarScroll > 0.5f;
if ((sliderControlsContainer.Rect.Contains(PlayerInput.MousePosition) || sliderControlsContainer.Children.Contains(GUIScrollBar.draggingBar)) &&
!PlayerInput.KeyDown(InputType.Deselect) && !PlayerInput.KeyHit(InputType.Deselect))
{
Character.DisableControls = true;
}
if (shutDown)
{
fissionRateScrollBar.BarScroll = FissionRate / 100.0f;
turbineOutputScrollBar.BarScroll = TurbineOutput / 100.0f;
}
}
else if (!autoTemp && Character.DisableControls && GUI.KeyboardDispatcher.Subscriber == null)
{
Vector2 input = Vector2.Zero;
float rate = 50.0f; //percentage per second
if (PlayerInput.KeyDown(InputType.Left)) input.X += -1.0f;
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;
rate *= deltaTime;
input.X *= rate;
input.Y *= rate;
if (input.LengthSquared() > 0)
{
LastUser = Character.Controlled;
unsentChanges = true;
if (input.X != 0.0f && GUIScrollBar.draggingBar != fissionRateScrollBar)
{
targetFissionRate = MathHelper.Clamp(targetFissionRate + input.X, 0.0f, 100.0f);
fissionRateScrollBar.BarScroll += input.X / 100.0f;
}
if (input.Y != 0.0f && GUIScrollBar.draggingBar != turbineOutputScrollBar)
{
targetTurbineOutput = MathHelper.Clamp(targetTurbineOutput + input.Y, 0.0f, 100.0f);
turbineOutputScrollBar.BarScroll += input.Y / 100.0f;
}
}
}
}
private bool ToggleAutoTemp(GUITickBox tickBox)
@@ -11,12 +11,6 @@ namespace Barotrauma.Items.Components
{
partial class Sonar : Powered, IServerSerializable, IClientSerializable
{
enum Mode
{
Active,
Passive
};
private bool dynamicDockingIndicator = true;
private bool unsentChanges;
@@ -43,8 +37,6 @@ namespace Barotrauma.Items.Components
private List<SonarBlip> sonarBlips;
private float prevPingRadius;
private float prevPassivePingRadius;
private Vector2 center;
@@ -102,7 +94,7 @@ namespace Barotrauma.Items.Components
ToolTip = TextManager.Get("SonarTipActive"),
OnSelected = (GUITickBox box) =>
{
IsActive = box.Selected;
CurrentMode = box.Selected ? Mode.Active : Mode.Passive;
if (GameMain.Client != null)
{
unsentChanges = true;
@@ -262,7 +254,7 @@ namespace Barotrauma.Items.Components
{
if (component is GUITextBlock textBlock)
{
textBlock.TextColor = IsActive ? textBlock.Style.textColor : textBlock.Style.textColor * 0.5f;
textBlock.TextColor = currentMode == Mode.Active ? textBlock.Style.textColor : textBlock.Style.textColor * 0.5f;
}
}
@@ -281,14 +273,21 @@ namespace Barotrauma.Items.Components
if (Level.Loaded != null)
{
Dictionary<LevelTrigger, Vector2> levelTriggerFlows = new Dictionary<LevelTrigger, Vector2>();
foreach (LevelObject levelObject in Level.Loaded.LevelObjectManager.GetAllObjects(transducerCenter, range * pingState / zoom))
for (var pingIndex = 0; pingIndex < activePingsCount; ++pingIndex)
{
//gather all nearby triggers that are causing the water to flow into the dictionary
foreach (LevelTrigger trigger in levelObject.Triggers)
var activePing = activePings[pingIndex];
foreach (LevelObject levelObject in Level.Loaded.LevelObjectManager.GetAllObjects(transducerCenter, range * activePing.State / zoom))
{
Vector2 flow = trigger.GetWaterFlowVelocity();
//ignore ones that are barely doing anything (flow^2 < 1)
if (flow.LengthSquared() > 1.0f) levelTriggerFlows.Add(trigger, flow);
//gather all nearby triggers that are causing the water to flow into the dictionary
foreach (LevelTrigger trigger in levelObject.Triggers)
{
Vector2 flow = trigger.GetWaterFlowVelocity();
//ignore ones that are barely doing anything (flow^2 < 1)
if (flow.LengthSquared() > 1.0f && !levelTriggerFlows.ContainsKey(trigger))
{
levelTriggerFlows.Add(trigger, flow);
}
}
}
}
@@ -350,13 +349,18 @@ namespace Barotrauma.Items.Components
prevDockingDist = float.MaxValue;
}
if (IsActive)
for (var pingIndex = 0; pingIndex < activePingsCount; ++pingIndex)
{
var activePing = activePings[pingIndex];
float pingRadius = DisplayRadius * activePing.State / zoom;
UpdateDisruptions(transducerCenter, pingRadius / displayScale, activePing.PrevPingRadius / displayScale);
Ping(transducerCenter, transducerCenter,
pingRadius, activePing.PrevPingRadius, displayScale, range / zoom, passive: false, pingStrength: 2.0f);
activePing.PrevPingRadius = pingRadius;
}
if (currentMode == Mode.Active && currentPingIndex != -1)
{
float pingRadius = DisplayRadius * pingState / zoom;
UpdateDisruptions(transducerCenter, pingRadius / displayScale, prevPingRadius / displayScale);
Ping(transducerCenter, transducerCenter,
pingRadius, prevPingRadius, displayScale, range / zoom, passive: false, pingStrength: 2.0f);
prevPingRadius = pingRadius;
return;
}
@@ -396,17 +400,18 @@ namespace Barotrauma.Items.Components
screenBackground.Draw(spriteBatch, center, 0.0f, rect.Width / screenBackground.size.X);
}
if (IsActive)
if (currentMode == Mode.Active && currentPingIndex != -1)
{
if (isLastPingDirectional && directionalPingCircle != null)
var activePing = activePings[currentPingIndex];
if (activePing.IsDirectional && directionalPingCircle != null)
{
directionalPingCircle.Draw(spriteBatch, center, Color.White * (1.0f - pingState),
rotate: MathUtils.VectorToAngle(lastPingDirection),
scale: (DisplayRadius / directionalPingCircle.size.X) * pingState);
directionalPingCircle.Draw(spriteBatch, center, Color.White * (1.0f - activePing.State),
rotate: MathUtils.VectorToAngle(activePing.Direction),
scale: (DisplayRadius / directionalPingCircle.size.X) * activePing.State);
}
else
{
pingCircle.Draw(spriteBatch, center, Color.White * (1.0f - pingState), 0.0f, (DisplayRadius * 2 / pingCircle.size.X) * pingState);
pingCircle.Draw(spriteBatch, center, Color.White * (1.0f - activePing.State), 0.0f, (DisplayRadius * 2 / pingCircle.size.X) * activePing.State);
}
}
@@ -448,7 +453,7 @@ namespace Barotrauma.Items.Components
spriteBatch.Begin(SpriteSortMode.Deferred, BlendState.AlphaBlend);
}
float directionalPingVisibility = useDirectionalPing && IsActive ? 1.0f : showDirectionalIndicatorTimer;
float directionalPingVisibility = useDirectionalPing && currentMode == Mode.Active ? 1.0f : showDirectionalIndicatorTimer;
if (directionalPingVisibility > 0.0f)
{
Vector2 sector1 = MathUtils.RotatePointAroundTarget(pingDirection * DisplayRadius, Vector2.Zero, DirectionalPingSector * 0.5f);
@@ -753,24 +758,47 @@ namespace Barotrauma.Items.Components
disruptedDirections.Clear();
if (Level.Loaded == null) { return; }
foreach (LevelObject levelObject in Level.Loaded.LevelObjectManager.GetAllObjects(pingSource, range * pingState))
for (var pingIndex = 0; pingIndex < activePingsCount; ++pingIndex)
{
if (levelObject.ActivePrefab?.SonarDisruption <= 0.0f) { continue; }
float disruptionStrength = levelObject.ActivePrefab.SonarDisruption;
Vector2 disruptionPos = new Vector2(levelObject.Position.X, levelObject.Position.Y);
float disruptionDist = Vector2.Distance(pingSource, disruptionPos);
disruptedDirections.Add(new Pair<Vector2, float>((disruptionPos - pingSource) / disruptionDist, disruptionStrength));
if (disruptionDist > worldPrevPingRadius && disruptionDist <= worldPingRadius)
var activePing = activePings[pingIndex];
foreach (LevelObject levelObject in Level.Loaded.LevelObjectManager.GetAllObjects(pingSource, range * activePing.State))
{
for (int i = 0; i < disruptionStrength * Level.GridCellSize * 0.02f; i++)
if (levelObject.ActivePrefab?.SonarDisruption <= 0.0f) { continue; }
float disruptionStrength = levelObject.ActivePrefab.SonarDisruption;
Vector2 disruptionPos = new Vector2(levelObject.Position.X, levelObject.Position.Y);
float disruptionDist = Vector2.Distance(pingSource, disruptionPos);
disruptedDirections.Add(new Pair<Vector2, float>((disruptionPos - pingSource) / disruptionDist, disruptionStrength));
if (disruptionDist > worldPrevPingRadius && disruptionDist <= worldPingRadius)
{
var blip = new SonarBlip(disruptionPos + Rand.Vector(Rand.Range(0.0f, Level.GridCellSize * 4 * disruptionStrength)), MathHelper.Lerp(1.0f, 1.5f, disruptionStrength), Rand.Range(1.0f, 2.0f + disruptionStrength));
sonarBlips.Add(blip);
CreateBlipsForDisruption(disruptionPos, disruptionStrength);
}
}
foreach (AITarget aiTarget in AITarget.List)
{
if (aiTarget.SonarDisruption <= 0.0f || !aiTarget.Enabled) { continue; }
float distSqr = Vector2.DistanceSquared(aiTarget.WorldPosition, pingSource);
if (distSqr > worldPingRadiusSqr) { continue; }
float disruptionDist = (float)Math.Sqrt(distSqr);
disruptedDirections.Add(new Pair<Vector2, float>((aiTarget.WorldPosition - pingSource) / disruptionDist, aiTarget.SonarDisruption));
if (disruptionDist > worldPrevPingRadius && disruptionDist <= worldPingRadius)
{
CreateBlipsForDisruption(aiTarget.WorldPosition, aiTarget.SonarDisruption);
}
}
}
void CreateBlipsForDisruption(Vector2 disruptionPos, float disruptionStrength)
{
for (int i = 0; i < disruptionStrength * Level.GridCellSize * 0.02f; i++)
{
var blip = new SonarBlip(disruptionPos + Rand.Vector(Rand.Range(0.0f, Level.GridCellSize * 4 * disruptionStrength)), MathHelper.Lerp(1.0f, 1.5f, disruptionStrength), Rand.Range(1.0f, 2.0f + disruptionStrength));
sonarBlips.Add(blip);
}
}
}
@@ -1045,9 +1073,9 @@ namespace Barotrauma.Items.Components
}
Vector2 dir = pos / (float)Math.Sqrt(posDistSqr);
if (isLastPingDirectional)
if (currentPingIndex != -1 && activePings[currentPingIndex].IsDirectional)
{
if (Vector2.Dot(lastPingDirection, dir) < DirectionalPingDotProduct)
if (Vector2.Dot(activePings[currentPingIndex].Direction, dir) < DirectionalPingDotProduct)
{
blip.FadeTimer = 0.0f;
return false;
@@ -1155,8 +1183,8 @@ namespace Barotrauma.Items.Components
public void ClientWrite(Lidgren.Network.NetBuffer msg, object[] extraData = null)
{
msg.Write(IsActive);
if (IsActive)
msg.Write(currentMode == Mode.Active);
if (currentMode == Mode.Active)
{
msg.WriteRangedSingle(zoom, MinZoom, MaxZoom, 8);
msg.Write(useDirectionalPing);
@@ -1192,8 +1220,8 @@ namespace Barotrauma.Items.Components
StartDelayedCorrection(type, msg.ExtractBits(msgLength), sendingTime);
return;
}
IsActive = isActive;
CurrentMode = isActive ? Mode.Active : Mode.Passive;
if (isActive)
{
activeTickBox.Selected = true;
@@ -735,9 +735,7 @@ namespace Barotrauma.Items.Components
if (sourcePort.Docked || sourcePort.Item.Submarine == null) { continue; }
if (sourcePort.Item.Submarine != controlledSub) { continue; }
int sourceDir = sourcePort.IsHorizontal ?
Math.Sign(sourcePort.Item.WorldPosition.X - sourcePort.Item.Submarine.WorldPosition.X) :
Math.Sign(sourcePort.Item.WorldPosition.Y - sourcePort.Item.Submarine.WorldPosition.Y);
int sourceDir = sourcePort.GetDir();
foreach (DockingPort targetPort in DockingPort.List)
{
@@ -745,9 +743,7 @@ namespace Barotrauma.Items.Components
if (targetPort.Item.Submarine == controlledSub || targetPort.IsHorizontal != sourcePort.IsHorizontal) { continue; }
if (Level.Loaded != null && targetPort.Item.Submarine.WorldPosition.Y > Level.Loaded.Size.Y) { continue; }
int targetDir = targetPort.IsHorizontal ?
Math.Sign(targetPort.Item.WorldPosition.X - targetPort.Item.Submarine.WorldPosition.X) :
Math.Sign(targetPort.Item.WorldPosition.Y - targetPort.Item.Submarine.WorldPosition.Y);
int targetDir = targetPort.GetDir();
if (sourceDir == targetDir) { continue; }
@@ -1,19 +1,16 @@
using System.Collections.Generic;
using Barotrauma.Sounds;
using System.Collections.Generic;
using System.Xml.Linq;
using Barotrauma.Sounds;
namespace Barotrauma.Items.Components
{
partial class Powered : ItemComponent
{
protected List<RoundSound> sparkSounds;
private RoundSound powerOnSound;
private bool powerOnSoundPlayed;
partial void InitProjectSpecific(XElement element)
{
sparkSounds = new List<RoundSound>();
foreach (XElement subElement in element.Elements())
{
switch (subElement.Name.ToString().ToLowerInvariant())
@@ -21,10 +18,6 @@ namespace Barotrauma.Items.Components
case "poweronsound":
powerOnSound = Submarine.LoadRoundSound(subElement, false);
break;
case "sparksound":
var sparkSound = Submarine.LoadRoundSound(subElement, false);
if (sparkSound != null) { sparkSounds.Add(sparkSound); }
break;
}
}
}
@@ -32,6 +32,8 @@ namespace Barotrauma.Items.Components
private List<ParticleEmitter> ParticleEmitterHitCharacter = new List<ParticleEmitter>();
private List<Pair<RelatedItem, ParticleEmitter>> ParticleEmitterHitItem = new List<Pair<RelatedItem, ParticleEmitter>>();
private float prevProgressBarState;
partial void InitProjSpecific(XElement element)
{
foreach (XElement subElement in element.Elements())
@@ -70,7 +72,7 @@ namespace Barotrauma.Items.Components
float particleAngle = item.body.Rotation + ((item.body.Dir > 0.0f) ? 0.0f : MathHelper.Pi);
ParticleEmitter.Emit(
deltaTime, item.WorldPosition + TransformedBarrelPos,
item.CurrentHull, particleAngle, -particleAngle);
item.CurrentHull, particleAngle, ParticleEmitter.Prefab.CopyEntityAngle ? -particleAngle : 0);
}
}
@@ -110,19 +112,22 @@ namespace Barotrauma.Items.Components
}
}
partial void FixItemProjSpecific(Character user, float deltaTime, Item targetItem, float prevCondition)
partial void FixItemProjSpecific(Character user, float deltaTime, Item targetItem)
{
if (prevCondition != targetItem.Condition)
float progressBarState = targetItem.ConditionPercentage / 100.0f;
if (!MathUtils.NearlyEqual(progressBarState, prevProgressBarState))
{
Vector2 progressBarPos = targetItem.DrawPosition;
var progressBar = user.UpdateHUDProgressBar(
targetItem,
progressBarPos,
targetItem.Condition / item.MaxCondition,
progressBarState,
Color.Red, Color.Green);
if (progressBar != null) { progressBar.Size = new Vector2(60.0f, 20.0f); }
}
prevProgressBarState = progressBarState;
Vector2 particlePos = ConvertUnits.ToDisplayUnits(pickedPosition);
if (targetItem.Submarine != null) particlePos += targetItem.Submarine.DrawPosition;
foreach (var emitter in ParticleEmitterHitItem)
@@ -74,10 +74,16 @@ namespace Barotrauma.Items.Components
//dropped or dragged from the panel to the players inventory
if (draggingConnected != null)
{
int linkIndex = c.FindWireIndex(draggingConnected.Item);
if (linkIndex > -1)
//the wire can only be dragged out if it's not connected to anything at the other end
if (Screen.Selected == GameMain.SubEditorScreen ||
(draggingConnected.Connections[0] == null && draggingConnected.Connections[1] == null) ||
(draggingConnected.Connections.Contains(c) && draggingConnected.Connections.Contains(null)))
{
Inventory.draggingItem = c.wires[linkIndex].Item;
int linkIndex = c.FindWireIndex(draggingConnected.Item);
if (linkIndex > -1 || panel.DisconnectedWires.Contains(draggingConnected))
{
Inventory.draggingItem = draggingConnected.Item;
}
}
}
@@ -109,59 +115,79 @@ namespace Barotrauma.Items.Components
if (draggingConnected != null)
{
DrawWire(spriteBatch, draggingConnected, draggingConnected.Item, PlayerInput.MousePosition, new Vector2(x + width / 2, y + height - 10), mouseInRect, null, panel, "");
if (mouseInRect)
{
DrawWire(spriteBatch, draggingConnected, PlayerInput.MousePosition, new Vector2(x + width / 2, y + height - 10), null, panel, "");
}
if (!PlayerInput.LeftButtonHeld())
{
if (GameMain.Client != null)
if (draggingConnected.Connections[0]?.ConnectionPanel == panel ||
draggingConnected.Connections[1]?.ConnectionPanel == panel)
{
panel.Item.CreateClientEvent(panel);
draggingConnected.RemoveConnection(panel.Item);
panel.DisconnectedWires.Add(draggingConnected);
}
if (GameMain.Client != null) { panel.Item.CreateClientEvent(panel); }
draggingConnected = null;
}
}
//if the Character using the panel has a wire item equipped
//and the wire hasn't been connected yet, draw it on the panel
if (equippedWire != null)
if (equippedWire != null && (draggingConnected != equippedWire || !mouseInRect))
{
if (panel.Connections.Find(c => c.Wires.Contains(equippedWire)) == null)
{
DrawWire(spriteBatch, equippedWire, equippedWire.Item,
new Vector2(x + width / 2, y + height - 100),
new Vector2(x + width / 2, y + height), mouseInRect, null, panel, "");
DrawWire(spriteBatch, equippedWire, new Vector2(x + width / 2, y + height - 150 * GUI.Scale),
new Vector2(x + width / 2, y + height),
null, panel, "");
if (draggingConnected == equippedWire) Inventory.draggingItem = equippedWire.Item;
if (draggingConnected == equippedWire) { Inventory.draggingItem = equippedWire.Item; }
}
}
float step = (width * 0.75f) / panel.DisconnectedWires.Count();
x = (int)(x + width / 2 - step * (panel.DisconnectedWires.Count() - 1) / 2);
foreach (Wire wire in panel.DisconnectedWires)
{
if (wire == draggingConnected && mouseInRect) { continue; }
Connection recipient = wire.OtherConnection(null);
string label = recipient == null ? "" : recipient.item.Name + $" ({recipient.DisplayName})";
if (wire.Locked) { label += "\n" + TextManager.Get("ConnectionLocked"); }
DrawWire(spriteBatch, wire, new Vector2(x, y + height - 100 * GUI.Scale),
new Vector2(x, y + height),
null, panel, label);
x += (int)step;
}
//stop dragging a wire item if the cursor is within any connection panel
//(so we don't drop the item when dropping the wire on a connection)
if (mouseInRect || GUI.MouseOn?.UserData is ConnectionPanel) Inventory.draggingItem = null;
if (mouseInRect || GUI.MouseOn?.UserData is ConnectionPanel) { Inventory.draggingItem = null; }
}
private void Draw(SpriteBatch spriteBatch, ConnectionPanel panel, Vector2 position, Vector2 labelPos, Vector2 wirePosition, bool mouseIn, Wire equippedWire, float wireInterval)
{
//spriteBatch.DrawString(GUI.SmallFont, Name, new Vector2(labelPos.X, labelPos.Y-10), Color.White);
GUI.DrawString(spriteBatch, labelPos, DisplayName, IsPower ? Color.Red : Color.White, Color.Black, 0, GUI.SmallFont);
connectionSprite.Draw(spriteBatch, position);
for (int i = 0; i < MaxLinked; i++)
{
if (wires[i] == null || wires[i].Hidden || draggingConnected == wires[i]) continue;
if (wires[i] == null || wires[i].Hidden || (draggingConnected == wires[i] && (mouseIn || Screen.Selected == GameMain.SubEditorScreen))) { continue; }
Connection recipient = wires[i].OtherConnection(this);
string label = recipient == null ? "" :
wires[i].Locked ? recipient.item.Name + "\n" + TextManager.Get("ConnectionLocked") : recipient.item.Name;
DrawWire(spriteBatch, wires[i], (recipient == null) ? wires[i].Item : recipient.item, position, wirePosition, mouseIn, equippedWire, panel, label);
string label = recipient == null ? "" : recipient.item.Name + $" ({recipient.DisplayName})";
if (wires[i].Locked) { label += "\n" + TextManager.Get("ConnectionLocked"); }
DrawWire(spriteBatch, wires[i], position, wirePosition, equippedWire, panel, label);
wirePosition.Y += wireInterval;
}
if (draggingConnected != null && Vector2.Distance(position, PlayerInput.MousePosition) < 13.0f)
if (draggingConnected != null && Vector2.Distance(position, PlayerInput.MousePosition) < (20.0f * GUI.Scale))
{
connectionSpriteHighlight.Draw(spriteBatch, position);
@@ -172,15 +198,15 @@ namespace Barotrauma.Items.Components
if (index > -1 && !Wires.Contains(draggingConnected))
{
bool alreadyConnected = draggingConnected.IsConnectedTo(panel.Item);
draggingConnected.RemoveConnection(panel.Item);
if (draggingConnected.Connect(this, !alreadyConnected, true))
{
var otherConnection = draggingConnected.OtherConnection(this);
SetWire(index, draggingConnected);
}
}
if (GameMain.Client != null) { panel.Item.CreateClientEvent(panel); }
draggingConnected = null;
}
}
@@ -215,15 +241,8 @@ namespace Barotrauma.Items.Components
flashTimer -= deltaTime;
}
private static void DrawWire(SpriteBatch spriteBatch, Wire wire, Item item, Vector2 end, Vector2 start, bool mouseIn, Wire equippedWire, ConnectionPanel panel, string label)
private static void DrawWire(SpriteBatch spriteBatch, Wire wire, Vector2 end, Vector2 start, Wire equippedWire, ConnectionPanel panel, string label)
{
if (draggingConnected == wire)
{
if (!mouseIn) return;
end = PlayerInput.MousePosition;
start.X = (start.X + end.X) / 2.0f;
}
int textX = (int)start.X;
if (start.X < end.X)
textX -= 10;
@@ -244,11 +263,19 @@ namespace Barotrauma.Items.Components
if (!string.IsNullOrEmpty(label))
{
GUI.DrawString(spriteBatch,
new Vector2(start.X < end.X ? textX - GUI.SmallFont.MeasureString(label).X : textX, start.Y - 5.0f),
label,
(mouseOn ? Color.Gold : Color.White) * (wire.Locked ? 0.6f : 1.0f), Color.Black * 0.8f,
3, GUI.SmallFont);
if (start.Y > panel.GuiFrame.Rect.Bottom - 1.0f)
{
//wire at the bottom of the panel -> draw the text below the panel, tilted 45 degrees
GUI.SmallFont.DrawString(spriteBatch, label, start + Vector2.UnitY * 20 * GUI.Scale, Color.White, 45.0f, Vector2.Zero, 1.0f, SpriteEffects.None, 0.0f);
}
else
{
GUI.DrawString(spriteBatch,
new Vector2(start.X < end.X ? textX - GUI.SmallFont.MeasureString(label).X : textX, start.Y - 5.0f),
label,
(mouseOn ? Color.Gold : Color.White) * (wire.Locked ? 0.6f : 1.0f), Color.Black * 0.8f,
3, GUI.SmallFont);
}
}
var wireEnd = end + Vector2.Normalize(start - end) * 30.0f;
@@ -259,14 +286,14 @@ namespace Barotrauma.Items.Components
{
spriteBatch.Draw(wireVertical.Texture, new Rectangle(wireEnd.ToPoint(), new Point(18, (int)dist)), wireVertical.SourceRect,
Color.Gold,
MathUtils.VectorToAngle(end - start) + MathHelper.PiOver2, //angle of line (calulated above)
MathUtils.VectorToAngle(end - start) + MathHelper.PiOver2,
new Vector2(6, 0), // point in line about which to rotate
SpriteEffects.None,
0.0f);
}
spriteBatch.Draw(wireVertical.Texture, new Rectangle(wireEnd.ToPoint(), new Point(12, (int)dist)), wireVertical.SourceRect,
wire.Item.Color * alpha,
MathUtils.VectorToAngle(end - start) + MathHelper.PiOver2, //angle of line (calulated above)
MathUtils.VectorToAngle(end - start) + MathHelper.PiOver2,
new Vector2(6, 0), // point in line about which to rotate
SpriteEffects.None,
0.0f);
@@ -283,7 +310,7 @@ namespace Barotrauma.Items.Components
if (allowRewiring && !wire.Locked && (!panel.Locked || Screen.Selected == GameMain.SubEditorScreen))
{
//start dragging the wire
if (PlayerInput.LeftButtonHeld()) draggingConnected = wire;
if (PlayerInput.LeftButtonHeld()) { draggingConnected = wire; }
}
}
}
@@ -52,7 +52,7 @@ namespace Barotrauma.Items.Components
private void DrawConnections(SpriteBatch spriteBatch, GUICustomComponent container)
{
if (user != Character.Controlled || user == null) return;
if (user != Character.Controlled || user == null) { return; }
HighlightedWire = null;
Connection.DrawConnections(spriteBatch, this, user);
@@ -70,8 +70,22 @@ namespace Barotrauma.Items.Components
{
//delay reading the state until midround syncing is done
//because some of the wires connected to the panel may not exist yet
int bitsToRead = Connections.Count * Connection.MaxLinked * 16;
StartDelayedCorrection(type, msg.ExtractBits(bitsToRead), sendingTime, waitForMidRoundSync: true);
long msgStartPos = msg.Position;
foreach (Connection connection in Connections)
{
for (int i = 0; i < Connection.MaxLinked; i++)
{
msg.ReadUInt16();
}
}
ushort disconnectedWireCount = msg.ReadUInt16();
for (int i = 0; i < disconnectedWireCount; i++)
{
msg.ReadUInt16();
}
int msgLength = (int)(msg.Position - msgStartPos);
msg.Position = msgStartPos;
StartDelayedCorrection(type, msg.ExtractBits(msgLength), sendingTime, waitForMidRoundSync: true);
}
else
{
@@ -95,11 +109,9 @@ namespace Barotrauma.Items.Components
{
ushort wireId = msg.ReadUInt16();
Item wireItem = Entity.FindEntityByID(wireId) as Item;
if (wireItem == null) continue;
if (!(Entity.FindEntityByID(wireId) is Item wireItem)) { continue; }
Wire wireComponent = wireItem.GetComponent<Wire>();
if (wireComponent == null) continue;
if (wireComponent == null) { continue; }
newWires.Add(wireComponent);
@@ -108,18 +120,46 @@ namespace Barotrauma.Items.Components
}
}
List<Wire> previousDisconnectedWires = new List<Wire>(DisconnectedWires);
DisconnectedWires.Clear();
ushort disconnectedWireCount = msg.ReadUInt16();
for (int i = 0; i < disconnectedWireCount; i++)
{
ushort wireId = msg.ReadUInt16();
if (!(Entity.FindEntityByID(wireId) is Item wireItem)) { continue; }
Wire wireComponent = wireItem.GetComponent<Wire>();
if (wireComponent == null) { continue; }
DisconnectedWires.Add(wireComponent);
}
foreach (Wire wire in prevWires)
{
if (wire.Connections[0] == null && wire.Connections[1] == null)
bool connected = wire.Connections[0] != null || wire.Connections[1] != null;
if (!connected)
{
foreach (Item item in Item.ItemList)
{
var connectionPanel = item.GetComponent<ConnectionPanel>();
if (connectionPanel != null && connectionPanel.DisconnectedWires.Contains(wire))
{
connected = true;
break;
}
}
}
if (wire.Item.ParentInventory == null && !connected)
{
wire.Item.Drop(null);
}
//wires that are not in anyone's inventory (i.e. not currently being rewired) can never be connected to only one connection
// -> someone must have dropped the wire from the connection panel
else if (wire.Item.ParentInventory == null &&
(wire.Connections[0] != null ^ wire.Connections[1] != null))
}
foreach (Wire disconnectedWire in previousDisconnectedWires)
{
if (disconnectedWire.Connections[0] == null &&
disconnectedWire.Connections[1] == null &&
!DisconnectedWires.Contains(disconnectedWire))
{
wire.Item.Drop(null);
disconnectedWire.Item.Drop(dropper: null);
}
}
}
@@ -2,6 +2,7 @@
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using System;
using System.Collections.Generic;
using System.Linq;
@@ -90,18 +91,26 @@ namespace Barotrauma.Items.Components
section.Draw(spriteBatch, item.Color, drawOffset, depth, 0.3f);
}
if (IsActive && nodes.Count > 0 && Vector2.Distance(newNodePos, nodes[nodes.Count - 1]) > nodeDistance)
if (nodes.Count > 0)
{
WireSection.Draw(
spriteBatch,
new Vector2(nodes[nodes.Count - 1].X, nodes[nodes.Count - 1].Y) + drawOffset,
new Vector2(newNodePos.X, newNodePos.Y) + drawOffset,
item.Color * 0.5f,
depth,
0.3f);
if (!IsActive)
{
if (connections[0] == null) { DrawHangingWire(spriteBatch, nodes[0] + drawOffset, depth); }
if (connections[1] == null) { DrawHangingWire(spriteBatch, nodes.Last() + drawOffset, depth); }
}
if (IsActive && Vector2.Distance(newNodePos, nodes[nodes.Count - 1]) > nodeDistance)
{
WireSection.Draw(
spriteBatch,
new Vector2(nodes[nodes.Count - 1].X, nodes[nodes.Count - 1].Y) + drawOffset,
new Vector2(newNodePos.X, newNodePos.Y) + drawOffset,
item.Color * 0.5f,
depth,
0.3f);
}
}
if (!editing || !GameMain.SubEditorScreen.WiringMode) return;
if (!editing || !GameMain.SubEditorScreen.WiringMode) { return; }
for (int i = 0; i < nodes.Count; i++)
{
@@ -126,6 +135,23 @@ namespace Barotrauma.Items.Components
}
}
private void DrawHangingWire(SpriteBatch spriteBatch, Vector2 start, float depth)
{
float angle = (float)Math.Sin(GameMain.GameScreen.GameTime * 2.0f + item.ID) * 0.2f;
Vector2 endPos = start + new Vector2((float)Math.Sin(angle), -(float)Math.Cos(angle)) * 50.0f;
WireSection.Draw(
spriteBatch,
start, endPos,
Color.Orange, depth + 0.00001f, 0.2f);
WireSection.Draw(
spriteBatch,
start, start + (endPos - start) * 0.7f,
item.Color, depth, 0.3f);
}
public static void UpdateEditing(List<Wire> wires)
{
//dragging a node of some wire
@@ -25,6 +25,9 @@ namespace Barotrauma.Items.Components
private SoundChannel moveSoundChannel;
private Vector2 crosshairPos, crosshairPointerPos;
private Dictionary<string, Widget> widgets = new Dictionary<string, Widget>();
private float prevAngle;
private bool flashLowPower;
private bool flashNoAmmo;
@@ -117,6 +120,25 @@ namespace Barotrauma.Items.Components
barSize: 0.0f);
}
private void InitializeRotationLimitWidget(Widget widget)
{
widget.Hovered += () =>
{
widget.secondaryColor = Color.Green;
};
widget.Selected += () =>
{
widget.color = Color.Green;
};
widget.MouseHeld += (deltaTime) =>
{
widget.DrawPos = PlayerInput.MousePosition;
};
widget.Deselected += () =>
{
widget.color = Color.Red;
};
}
partial void LaunchProjSpecific()
{
@@ -246,24 +268,153 @@ namespace Barotrauma.Items.Components
item.SpriteColor,
rotation + MathHelper.PiOver2, item.Scale,
SpriteEffects.None, item.SpriteDepth + (barrelSprite.Depth - item.Sprite.Depth));
if (!editing) return;
if (!editing) { return; }
float widgetRadius = 60.0f;
GUI.DrawLine(spriteBatch,
drawPos,
drawPos + new Vector2((float)Math.Cos(minRotation), (float)Math.Sin(minRotation)) * 60.0f,
drawPos + new Vector2((float)Math.Cos(minRotation), (float)Math.Sin(minRotation)) * widgetRadius,
Color.Green);
GUI.DrawLine(spriteBatch,
drawPos,
drawPos + new Vector2((float)Math.Cos(maxRotation), (float)Math.Sin(maxRotation)) * 60.0f,
drawPos + new Vector2((float)Math.Cos(maxRotation), (float)Math.Sin(maxRotation)) * widgetRadius,
Color.Green);
GUI.DrawLine(spriteBatch,
drawPos,
drawPos + new Vector2((float)Math.Cos((maxRotation + minRotation) / 2), (float)Math.Sin((maxRotation + minRotation) / 2)) * 60.0f,
drawPos + new Vector2((float)Math.Cos((maxRotation + minRotation) / 2), (float)Math.Sin((maxRotation + minRotation) / 2)) * widgetRadius,
Color.LightGreen);
if (!item.IsSelected) { return; }
Widget minRotationWidget = GetWidget("minrotation", spriteBatch, size: 10, initMethod: (widget) =>
{
widget.MouseDown += () =>
{
widget.color = Color.Green;
prevAngle = minRotation;
};
widget.Deselected += () =>
{
widget.color = Color.Yellow;
item.CreateEditingHUD();
};
widget.MouseHeld += (deltaTime) =>
{
minRotation = GetRotationAngle(drawPos);
if (minRotation > maxRotation)
{
float temp = minRotation;
minRotation = maxRotation;
maxRotation = temp;
}
MapEntity.DisableSelect = true;
};
widget.PreUpdate += (deltaTime) =>
{
widget.DrawPos = new Vector2(widget.DrawPos.X, -widget.DrawPos.Y);
widget.DrawPos = Screen.Selected.Cam.WorldToScreen(widget.DrawPos);
};
widget.PostUpdate += (deltaTime) =>
{
widget.DrawPos = Screen.Selected.Cam.ScreenToWorld(widget.DrawPos);
widget.DrawPos = new Vector2(widget.DrawPos.X, -widget.DrawPos.Y);
};
widget.PreDraw += (sprtBtch, deltaTime) =>
{
widget.tooltip = "Min: " + (int)MathHelper.ToDegrees(minRotation);
widget.DrawPos = drawPos + new Vector2((float)Math.Cos(minRotation), (float)Math.Sin(minRotation)) * widgetRadius;
widget.Update(deltaTime);
};
});
Widget maxRotationWidget = GetWidget("maxrotation", spriteBatch, size: 10, initMethod: (widget) =>
{
widget.MouseDown += () =>
{
widget.color = Color.Green;
prevAngle = minRotation;
};
widget.Deselected += () =>
{
widget.color = Color.Yellow;
item.CreateEditingHUD();
};
widget.MouseHeld += (deltaTime) =>
{
maxRotation = GetRotationAngle(drawPos);
if (minRotation > maxRotation)
{
float temp = minRotation;
minRotation = maxRotation;
maxRotation = temp;
}
MapEntity.DisableSelect = true;
};
widget.PreUpdate += (deltaTime) =>
{
widget.DrawPos = new Vector2(widget.DrawPos.X, -widget.DrawPos.Y);
widget.DrawPos = Screen.Selected.Cam.WorldToScreen(widget.DrawPos);
};
widget.PostUpdate += (deltaTime) =>
{
widget.DrawPos = Screen.Selected.Cam.ScreenToWorld(widget.DrawPos);
widget.DrawPos = new Vector2(widget.DrawPos.X, -widget.DrawPos.Y);
};
widget.PreDraw += (sprtBtch, deltaTime) =>
{
widget.tooltip = "Max: " + (int)MathHelper.ToDegrees(maxRotation);
widget.DrawPos = drawPos + new Vector2((float)Math.Cos(maxRotation), (float)Math.Sin(maxRotation)) * widgetRadius;
widget.Update(deltaTime);
};
});
minRotationWidget.Draw(spriteBatch, (float)Timing.Step);
maxRotationWidget.Draw(spriteBatch, (float)Timing.Step);
}
private Widget GetWidget(string id, SpriteBatch spriteBatch, int size = 5, Action<Widget> initMethod = null)
{
if (!widgets.TryGetValue(id, out Widget widget))
{
widget = new Widget(id, size, Widget.Shape.Rectangle)
{
color = Color.Yellow,
tooltipOffset = new Vector2(size / 2 + 5, -10),
inputAreaMargin = 20,
RequireMouseOn = false
};
widgets.Add(id, widget);
initMethod?.Invoke(widget);
}
return widget;
}
/// <summary>
/// Returns correct angle between -2PI and +2PI
/// </summary>
/// <param name="drawPosition"></param>
/// <returns></returns>
private float GetRotationAngle(Vector2 drawPosition)
{
Vector2 mouseVector = Screen.Selected.Cam.ScreenToWorld(PlayerInput.MousePosition);
mouseVector.Y = -mouseVector.Y;
Vector2 rotationVector = mouseVector - drawPosition;
rotationVector.Normalize();
double angle = Math.Atan2(MathHelper.ToRadians(rotationVector.Y), MathHelper.ToRadians(rotationVector.X));
if (angle < 0)
{// calculates which coterminal angle is closer to previous angle
angle = Math.Abs(angle - prevAngle) < Math.Abs((angle + Math.PI * 2) - prevAngle) ? angle : angle + Math.PI * 2;
}
else if (angle > 0)
{
angle = Math.Abs(angle - prevAngle) < Math.Abs((angle - Math.PI * 2) - prevAngle) ? angle : angle - Math.PI * 2;
}
angle = MathHelper.Clamp((float)angle, -((float)Math.PI * 2), (float)Math.PI * 2);
prevAngle = (float)angle;
return (float)angle;
}
public override void DrawHUD(SpriteBatch spriteBatch, Character character)
@@ -329,6 +329,10 @@ namespace Barotrauma
item.AiTarget?.Draw(spriteBatch);
}
}
if (body != null)
{
body.DebugDraw(spriteBatch, Color.White);
}
}
if (!editing || (body != null && !body.Enabled))
@@ -880,7 +884,6 @@ namespace Barotrauma
}
}
break;
case NetEntityEvent.Type.InventoryState:
{
int containerIndex = msg.ReadRangedInteger(0, components.Count - 1);
@@ -969,6 +972,10 @@ namespace Barotrauma
case NetEntityEvent.Type.ChangeProperty:
WritePropertyChange(msg, extraData, true);
break;
case NetEntityEvent.Type.Combine:
UInt16 combineTargetID = (UInt16)extraData[1];
msg.Write(combineTargetID);
break;
}
msg.WritePadBits();
}
@@ -90,6 +90,15 @@ namespace Barotrauma
}
}
private Vector2 ClampParticlePos(Vector2 particlePos, Hull hull)
{
if (hull == null) return particlePos;
return new Vector2(
MathHelper.Clamp(particlePos.X, hull.WorldRect.X, hull.WorldRect.Right),
MathHelper.Clamp(particlePos.Y, hull.WorldRect.Y - hull.WorldRect.Height, hull.WorldRect.Y));
}
private IEnumerable<object> DimLight(LightSource light)
{
float currBrightness = 1.0f;
@@ -260,20 +260,19 @@ namespace Barotrauma.Lights
(int)(GameMain.GraphicsWidth * currLightMapScale), (int)(GameMain.GraphicsHeight * currLightMapScale)), Color.Black);
spriteBatch.End();
}
else
visibleHulls = GetVisibleHulls(cam);
spriteBatch.Begin(SpriteSortMode.Deferred, BlendState.Opaque, transformMatrix: spriteBatchTransform);
foreach (Rectangle drawRect in visibleHulls.Values)
{
visibleHulls = GetVisibleHulls(cam);
spriteBatch.Begin(SpriteSortMode.Deferred, BlendState.Opaque, transformMatrix: spriteBatchTransform);
foreach (Rectangle drawRect in visibleHulls.Values)
{
//TODO: draw some sort of smoothed rectangle
GUI.DrawRectangle(spriteBatch,
new Vector2(drawRect.X, -drawRect.Y),
new Vector2(drawRect.Width, drawRect.Height),
Color.Black, true);
}
spriteBatch.End();
}
//TODO: draw some sort of smoothed rectangle
GUI.DrawRectangle(spriteBatch,
new Vector2(drawRect.X, -drawRect.Y),
new Vector2(drawRect.Width, drawRect.Height),
Color.Black, true);
}
spriteBatch.End();
graphics.BlendState = BlendState.Additive;
}
@@ -382,8 +382,28 @@ namespace Barotrauma
}
else
{
selectedList.Clear();
newSelection.ForEach(e => AddSelection(e));
selectedList = newSelection;
//selectedList.Clear();
//newSelection.ForEach(e => AddSelection(e));
foreach (var entity in newSelection)
{
HandleDoorGapLinks(entity,
onGapFound: (door, gap) =>
{
door.RefreshLinkedGap();
if (!selectedList.Contains(gap))
{
selectedList.Add(gap);
}
},
onDoorFound: (door, gap) =>
{
if (!selectedList.Contains(door.Item))
{
selectedList.Add(door.Item);
}
});
}
}
//select wire if both items it's connected to are selected
@@ -12,11 +12,6 @@ using System.Collections.Generic;
namespace Barotrauma
{
partial class WallSection
{
public ConvexHull hull;
}
partial class Structure : MapEntity, IDamageable, IServerSerializable
{
public static bool ShowWalls = true, ShowStructures = true;
@@ -204,8 +204,7 @@ namespace Barotrauma.Networking
ulong fileSize = inc.ReadUInt64();
string fileName = inc.ReadString();
string errorMsg;
if (!ValidateInitialData(fileType, fileName, fileSize, out errorMsg))
if (!ValidateInitialData(fileType, fileName, fileSize, out string errorMsg))
{
GameMain.Client.CancelFileTransfer(inc.SequenceChannel);
DebugConsole.ThrowError("File transfer failed (" + errorMsg + ")");
@@ -32,6 +32,8 @@ namespace Barotrauma.Networking
protected GUITickBox cameraFollowsSub;
public RoundEndCinematic EndCinematic;
private ClientPermissions permissions = ClientPermissions.None;
private List<string> permittedConsoleCommands = new List<string>();
@@ -209,7 +211,7 @@ namespace Barotrauma.Networking
otherClients = new List<Client>();
serverSettings = new ServerSettings("Server", 0, 0, 0, false, false);
serverSettings = new ServerSettings(this, "Server", 0, 0, 0, false, false);
ConnectToServer(ip, serverName);
@@ -800,7 +802,7 @@ namespace Barotrauma.Networking
GameMain.GameSession.WinningTeam = winningTeam;
GameMain.GameSession.Mission.Completed = true;
}
CoroutineManager.StartCoroutine(EndGame(endMessage));
CoroutineManager.StartCoroutine(EndGame(endMessage), "EndGame");
break;
case ServerPacketHeader.CAMPAIGN_SETUP_INFO:
UInt16 saveCount = inc.ReadUInt16();
@@ -1059,6 +1061,12 @@ namespace Barotrauma.Networking
if (Character != null) Character.Remove();
HasSpawned = false;
while (CoroutineManager.IsCoroutineRunning("EndGame"))
{
if (EndCinematic != null) { EndCinematic.Stop(); }
yield return CoroutineStatus.Running;
}
GameMain.LightManager.LightingEnabled = true;
//enable spectate button in case we fail to start the round now
@@ -1192,6 +1200,15 @@ namespace Barotrauma.Networking
if (GameMain.GameSession != null) { GameMain.GameSession.GameMode.End(endMessage); }
// Enable characters near the main sub for the endCinematic
foreach (Character c in Character.CharacterList)
{
if (Vector2.DistanceSquared(Submarine.MainSub.WorldPosition, c.WorldPosition) < NetConfig.EnableCharacterDistSqr)
{
c.Enabled = true;
}
}
ServerSettings.ServerDetailsChanged = true;
gameStarted = false;
@@ -1199,17 +1216,15 @@ namespace Barotrauma.Networking
GameMain.GameScreen.Cam.TargetPos = Vector2.Zero;
GameMain.LightManager.LosEnabled = false;
respawnManager = null;
float endPreviewLength = 10.0f;
if (Screen.Selected == GameMain.GameScreen)
{
new RoundEndCinematic(Submarine.MainSub, GameMain.GameScreen.Cam, endPreviewLength);
float secondsLeft = endPreviewLength;
do
EndCinematic = new RoundEndCinematic(Submarine.MainSub, GameMain.GameScreen.Cam);
while (EndCinematic.Running && Screen.Selected == GameMain.GameScreen)
{
secondsLeft -= CoroutineManager.UnscaledDeltaTime;
yield return CoroutineStatus.Running;
} while (secondsLeft > 0.0f && Screen.Selected == GameMain.GameScreen);
}
EndCinematic = null;
}
Submarine.Unload();
@@ -1628,6 +1643,7 @@ namespace Barotrauma.Networking
outmsg.Write(LastClientListUpdateID);
Character.Controlled?.ClientWrite(outmsg);
GameMain.GameScreen.Cam?.ClientWrite(outmsg);
entityEventManager.Write(outmsg, client.ServerConnection);
@@ -1829,9 +1845,10 @@ namespace Barotrauma.Networking
steamAuthTicket?.Cancel();
steamAuthTicket = null;
foreach (var fileTransfer in FileReceiver.ActiveTransfers)
List<FileReceiver.FileTransferIn> activeTransfers = new List<FileReceiver.FileTransferIn>(FileReceiver.ActiveTransfers);
foreach (var fileTransfer in activeTransfers)
{
fileTransfer.Dispose();
FileReceiver.StopTransfer(fileTransfer, deleteFile: true);
}
if (HasPermission(ClientPermissions.ServerLog))
@@ -1842,7 +1859,8 @@ namespace Barotrauma.Networking
if (GameMain.ServerChildProcess != null)
{
int checks = 0;
while (!GameMain.ServerChildProcess.HasExited) {
while (!GameMain.ServerChildProcess.HasExited)
{
if (checks > 10)
{
GameMain.ServerChildProcess.Kill();
@@ -2329,24 +2347,34 @@ namespace Barotrauma.Networking
if (respawnManager != null)
{
string respawnInfo = "";
string respawnText = "";
float textScale = 1.0f;
Color textColor = Color.White;
if (respawnManager.CurrentState == RespawnManager.State.Waiting &&
respawnManager.CountdownStarted)
respawnManager.RespawnCountdownStarted)
{
respawnInfo = TextManager.GetWithVariable(respawnManager.UsingShuttle ? "RespawnShuttleDispatching" : "RespawningIn", "[time]", ToolBox.SecondsToReadableTime(respawnManager.RespawnTimer));
float timeLeft = (float)(respawnManager.RespawnTime - DateTime.Now).TotalSeconds;
respawnText = TextManager.GetWithVariable(respawnManager.UsingShuttle ? "RespawnShuttleDispatching" : "RespawningIn", "[time]", ToolBox.SecondsToReadableTime(timeLeft));
}
else if (respawnManager.CurrentState == RespawnManager.State.Transporting)
else if (respawnManager.CurrentState == RespawnManager.State.Transporting &&
respawnManager.ReturnCountdownStarted)
{
respawnInfo = respawnManager.TransportTimer <= 0.0f ?
float timeLeft = (float)(respawnManager.ReturnTime - DateTime.Now).TotalSeconds;
respawnText = timeLeft <= 0.0f ?
"" :
TextManager.GetWithVariable("RespawnShuttleLeavingIn", "[time]", ToolBox.SecondsToReadableTime(respawnManager.TransportTimer));
TextManager.GetWithVariable("RespawnShuttleLeavingIn", "[time]", ToolBox.SecondsToReadableTime(timeLeft));
if (timeLeft < 20.0f)
{
//oscillate between 0-1
float phase = (float)(Math.Sin(timeLeft * MathHelper.Pi) + 1.0f) * 0.5f;
textScale = 1.0f + phase * 0.5f;
textColor = Color.Lerp(Color.Red, Color.White, 1.0f - phase);
}
}
if (respawnManager != null)
if (!string.IsNullOrEmpty(respawnText))
{
GUI.DrawString(spriteBatch,
new Vector2(120.0f, 10),
respawnInfo, Color.White, null, 0, GUI.SmallFont);
GUI.SmallFont.DrawString(spriteBatch, respawnText, new Vector2(120.0f, 10), textColor, 0.0f, Vector2.Zero, textScale, Microsoft.Xna.Framework.Graphics.SpriteEffects.None, 0.0f);
}
}
@@ -0,0 +1,78 @@
using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.Xna.Framework;
namespace Barotrauma
{
partial class KarmaManager : ISerializableEntity
{
public void CreateSettingsFrame(GUIComponent parent)
{
CreateLabeledSlider(parent, 0.0f, 40.0f, 1.0f, "KickBanThreshold");
CreateLabeledSlider(parent, 0.0f, 50.0f, 1.0f, "HerpesThreshold");
CreateLabeledSlider(parent, 0.0f, 0.5f, 0.01f, "KarmaDecay");
CreateLabeledSlider(parent, 50.0f, 100.0f, 1.0f, "KarmaDecayThreshold");
CreateLabeledSlider(parent, 0.0f, 0.5f, 0.01f, "KarmaIncrease");
CreateLabeledSlider(parent, 0.0f, 50.0f, 1.0f, "KarmaIncreaseThreshold");
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.12f), parent.RectTransform), TextManager.Get("Karma.PositiveActions"), textAlignment: Alignment.Center)
{
CanBeFocused = false
};
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "StructureRepairKarmaIncrease");
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "HealFriendlyKarmaIncrease");
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "DamageEnemyKarmaIncrease");
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "ItemRepairKarmaIncrease");
CreateLabeledSlider(parent, 0.0f, 10.0f, 0.05f, "ExtinguishFireKarmaIncrease");
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.12f), parent.RectTransform), TextManager.Get("Karma.NegativeActions"), textAlignment: Alignment.Center)
{
CanBeFocused = false
};
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "StructureDamageKarmaDecrease");
CreateLabeledSlider(parent, 0.0f, 1.0f, 0.01f, "DamageFriendlyKarmaDecrease");
CreateLabeledSlider(parent, 0.0f, 100.0f, 1.0f, "ReactorMeltdownKarmaDecrease");
CreateLabeledSlider(parent, 0.0f, 10.0f, 0.05f, "ReactorOverheatKarmaDecrease");
CreateLabeledSlider(parent, 0.0f, 20.0f, 1f, "AllowedWireDisconnectionsPerMinute");
CreateLabeledSlider(parent, 0.0f, 20.0f, 0.5f, "WireDisconnectionKarmaDecrease");
CreateLabeledSlider(parent, 0.0f, 30.0f, 1.0f, "SpamFilterKarmaDecrease");
}
private void CreateLabeledSlider(GUIComponent parent, float min, float max, float step, string propertyName)
{
var container = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.1f), parent.RectTransform), isHorizontal: true)
{
Stretch = true,
RelativeSpacing = 0.05f,
ToolTip = TextManager.Get("Karma." + propertyName + "ToolTip")
};
string labelText = TextManager.Get("Karma." + propertyName);
var label = new GUITextBlock(new RectTransform(new Vector2(0.7f, 0.8f), container.RectTransform),
labelText, font: GUI.SmallFont)
{
ToolTip = TextManager.Get("Karma." + propertyName + "ToolTip")
};
var slider = new GUIScrollBar(new RectTransform(new Vector2(0.3f, 0.8f), container.RectTransform), barSize: 0.1f)
{
Step = step <= 0.0f ? 0.0f : step / (max - min),
Range = new Vector2(min, max),
OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
string formattedValueStr = step >= 1.0f ?
((int)scrollBar.BarScrollValue).ToString() :
scrollBar.BarScrollValue.Format(decimalCount: step <= 0.1f ? 2 : 1);
label.Text = TextManager.AddPunctuation(':', labelText, formattedValueStr);
return true;
}
};
GameMain.NetworkMember.ServerSettings.AssignGUIComponent(propertyName, slider);
slider.OnMoved(slider, slider.BarScroll);
}
}
}
@@ -1,25 +1,59 @@
using System;
using Lidgren.Network;
using Microsoft.Xna.Framework;
using System;
namespace Barotrauma.Networking
{
partial class RespawnManager
{
partial void UpdateWaiting(float deltaTime)
{
if (CountdownStarted)
{
respawnTimer = Math.Max(0.0f, respawnTimer - deltaTime);
}
}
private DateTime lastShuttleLeavingWarningTime;
partial void UpdateTransportingProjSpecific(float deltaTime)
{
if (shuttleTransportTimer + deltaTime > 15.0f && shuttleTransportTimer <= 15.0f &&
GameMain.Client?.Character != null &&
GameMain.Client.Character.Submarine == respawnShuttle)
if (GameMain.Client?.Character == null || GameMain.Client.Character.Submarine != RespawnShuttle) { return; }
if (!ReturnCountdownStarted) { return; }
//show a warning when there's 20 seconds until the shuttle leaves
if ((ReturnTime - DateTime.Now).TotalSeconds < 20.0f &&
(DateTime.Now - lastShuttleLeavingWarningTime).TotalSeconds > 30.0f)
{
lastShuttleLeavingWarningTime = DateTime.Now;
GameMain.Client.AddChatMessage("ServerMessage.ShuttleLeaving", ChatMessageType.Server);
}
}
public void ClientRead(ServerNetObject type, NetBuffer msg, float sendingTime)
{
var newState = (State)msg.ReadRangedInteger(0, Enum.GetNames(typeof(State)).Length);
switch (newState)
{
case State.Transporting:
ReturnCountdownStarted = msg.ReadBoolean();
maxTransportTime = msg.ReadSingle();
float transportTimeLeft = msg.ReadSingle();
ReturnTime = DateTime.Now + new TimeSpan(0, 0, 0, 0, milliseconds: (int)(transportTimeLeft * 1000.0f));
RespawnCountdownStarted = false;
if (CurrentState != newState)
{
CoroutineManager.StopCoroutines("forcepos");
//CoroutineManager.StartCoroutine(ForceShuttleToPos(Level.Loaded.StartPosition - Vector2.UnitY * Level.ShaftHeight, 100.0f), "forcepos");
}
break;
case State.Waiting:
RespawnCountdownStarted = msg.ReadBoolean();
ResetShuttle();
float newRespawnTime = msg.ReadSingle();
RespawnTime = DateTime.Now + new TimeSpan(0, 0, 0, 0, milliseconds: (int)(newRespawnTime * 1000.0f));
break;
case State.Returning:
RespawnCountdownStarted = false;
break;
}
CurrentState = newState;
msg.ReadPadBits();
}
}
}
@@ -51,7 +51,22 @@ namespace Barotrauma.Networking
public bool ContentPackagesMatch(IEnumerable<ContentPackage> myContentPackages)
{
return ContentPackagesMatch(myContentPackages.Select(cp => cp.MD5hash.Hash));
//make sure we have all the packages the server requires
foreach (string hash in ContentPackageHashes)
{
if (!myContentPackages.Any(myPackage => myPackage.MD5hash.Hash == hash)) { return false; }
}
//make sure the server isn't missing any of our packages that cause multiplayer incompatibility
foreach (ContentPackage myPackage in myContentPackages)
{
if (myPackage.HasMultiplayerIncompatibleContent)
{
if (!ContentPackageHashes.Any(hash => hash == myPackage.MD5hash.Hash)) { return false; }
}
}
return true;
}
public bool ContentPackagesMatch(IEnumerable<string> myContentPackageHashes)
@@ -17,7 +17,7 @@ namespace Barotrauma.Networking
public void AssignGUIComponent(GUIComponent component)
{
GUIComponent = component;
GUIComponentValue = property.GetValue(serverSettings);
GUIComponentValue = property.GetValue(parentObject);
TempValue = GUIComponentValue;
}
@@ -30,6 +30,7 @@ namespace Barotrauma.Networking
else if (GUIComponent is GUITextBox textBox) return textBox.Text;
else if (GUIComponent is GUIScrollBar scrollBar) return scrollBar.BarScrollValue;
else if (GUIComponent is GUIRadioButtonGroup radioButtonGroup) return radioButtonGroup.Selected;
else if (GUIComponent is GUIDropDown dropdown) return dropdown.SelectedData;
return null;
}
set
@@ -39,6 +40,7 @@ namespace Barotrauma.Networking
else if (GUIComponent is GUITextBox textBox) textBox.Text = (string)value;
else if (GUIComponent is GUIScrollBar scrollBar) scrollBar.BarScrollValue = (float)value;
else if (GUIComponent is GUIRadioButtonGroup radioButtonGroup) radioButtonGroup.Selected = (Enum)value;
else if (GUIComponent is GUIDropDown dropdown) dropdown.SelectItem(value);
}
}
@@ -50,31 +52,6 @@ namespace Barotrauma.Networking
return !PropEquals(TempValue, GUIComponentValue);
}
}
public bool PropEquals(object a,object b)
{
switch (typeString)
{
case "float":
if (!(a is float?)) return false;
if (!(b is float?)) return false;
return (float)a == (float)b;
case "int":
if (!(a is int?)) return false;
if (!(b is int?)) return false;
return (int)a == (int)b;
case "bool":
if (!(a is bool?)) return false;
if (!(b is bool?)) return false;
return (bool)a == (bool)b;
case "Enum":
if (!(a is Enum)) return false;
if (!(b is Enum)) return false;
return ((Enum)a).Equals((Enum)b);
default:
return a.ToString().Equals(b.ToString(),StringComparison.InvariantCulture);
}
}
}
private Dictionary<string, bool> tempMonsterEnabled;
@@ -222,11 +199,15 @@ namespace Barotrauma.Networking
private GUIFrame[] settingsTabs;
private GUIButton[] tabButtons;
private int settingsTabIndex;
private GUIDropDown karmaPresetDD;
private GUIComponent karmaSettingsBlocker;
enum SettingsTab
{
General,
Rounds,
Server,
Antigriefing,
Banlist,
Whitelist
}
@@ -236,6 +217,11 @@ namespace Barotrauma.Networking
return netProperties.First(p => p.Value.Name == name).Value;
}
public void AssignGUIComponent(string propertyName, GUIComponent component)
{
GetPropertyData(propertyName).AssignGUIComponent(component);
}
public void AddToGUIUpdateList()
{
if (GUI.DisableHUD) return;
@@ -264,7 +250,7 @@ namespace Barotrauma.Networking
};
//center frames
GUIFrame innerFrame = new GUIFrame(new RectTransform(new Vector2(0.3f, 0.7f), settingsFrame.RectTransform, Anchor.Center) { MinSize = new Point(400, 430) });
GUIFrame innerFrame = new GUIFrame(new RectTransform(new Vector2(0.4f, 0.75f), settingsFrame.RectTransform, Anchor.Center) { MinSize = new Point(400, 430) });
GUIFrame paddedFrame = new GUIFrame(new RectTransform(new Vector2(0.9f, 0.9f), innerFrame.RectTransform, Anchor.Center), style: null);
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), paddedFrame.RectTransform), TextManager.Get("Settings"), font: GUI.LargeFont);
@@ -304,18 +290,21 @@ namespace Barotrauma.Networking
OnClicked = ToggleSettingsFrame
};
//--------------------------------------------------------------------------------
// game settings
// server settings
//--------------------------------------------------------------------------------
var roundsTab = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), settingsTabs[(int)SettingsTab.Rounds].RectTransform, Anchor.Center))
var serverTab = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), settingsTabs[(int)SettingsTab.General].RectTransform, Anchor.Center))
{
Stretch = true,
RelativeSpacing = 0.02f
};
//***********************************************
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), TextManager.Get("ServerSettingsSubSelection"));
var selectionFrame = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), isHorizontal: true)
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsSubSelection"));
var selectionFrame = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), isHorizontal: true)
{
Stretch = true,
RelativeSpacing = 0.05f
@@ -327,11 +316,11 @@ namespace Barotrauma.Networking
var selectionTick = new GUITickBox(new RectTransform(new Vector2(0.3f, 1.0f), selectionFrame.RectTransform), TextManager.Get(((SelectionMode)i).ToString()), font: GUI.SmallFont);
selectionMode.AddRadioButton((SelectionMode)i, selectionTick);
}
DebugConsole.NewMessage(SubSelectionMode.ToString(),Color.White);
DebugConsole.NewMessage(SubSelectionMode.ToString(), Color.White);
GetPropertyData("SubSelectionMode").AssignGUIComponent(selectionMode);
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), TextManager.Get("ServerSettingsModeSelection"));
selectionFrame = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), isHorizontal: true)
new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsModeSelection"));
selectionFrame = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), isHorizontal: true)
{
Stretch = true,
RelativeSpacing = 0.05f
@@ -345,6 +334,84 @@ namespace Barotrauma.Networking
}
GetPropertyData("ModeSelectionMode").AssignGUIComponent(selectionMode);
//***********************************************
var voiceChatEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform),
TextManager.Get("ServerSettingsVoiceChatEnabled"));
GetPropertyData("VoiceChatEnabled").AssignGUIComponent(voiceChatEnabled);
//***********************************************
string autoRestartDelayLabel = TextManager.Get("ServerSettingsAutoRestartDelay") + " ";
var startIntervalText = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), autoRestartDelayLabel);
var startIntervalSlider = new GUIScrollBar(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), barSize: 0.1f)
{
UserData = startIntervalText,
Step = 0.05f,
OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
GUITextBlock text = scrollBar.UserData as GUITextBlock;
text.Text = autoRestartDelayLabel + ToolBox.SecondsToReadableTime(scrollBar.BarScrollValue);
return true;
}
};
startIntervalSlider.Range = new Vector2(10.0f, 300.0f);
GetPropertyData("AutoRestartInterval").AssignGUIComponent(startIntervalSlider);
startIntervalSlider.OnMoved(startIntervalSlider, startIntervalSlider.BarScroll);
//***********************************************
var startWhenClientsReady = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform),
TextManager.Get("ServerSettingsStartWhenClientsReady"));
GetPropertyData("StartWhenClientsReady").AssignGUIComponent(startWhenClientsReady);
CreateLabeledSlider(serverTab, "ServerSettingsStartWhenClientsReadyRatio", out GUIScrollBar slider, out GUITextBlock sliderLabel);
string clientsReadyRequiredLabel = sliderLabel.Text;
slider.Step = 0.2f;
slider.Range = new Vector2(0.5f, 1.0f);
slider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
((GUITextBlock)scrollBar.UserData).Text = clientsReadyRequiredLabel.Replace("[percentage]", ((int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 10.0f)).ToString());
return true;
};
GetPropertyData("StartWhenClientsReadyRatio").AssignGUIComponent(slider);
slider.OnMoved(slider, slider.BarScroll);
//***********************************************
var allowSpecBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsAllowSpectating"));
GetPropertyData("AllowSpectating").AssignGUIComponent(allowSpecBox);
var shareSubsBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsShareSubFiles"));
GetPropertyData("AllowFileTransfers").AssignGUIComponent(shareSubsBox);
var randomizeLevelBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsRandomizeSeed"));
GetPropertyData("RandomizeSeed").AssignGUIComponent(randomizeLevelBox);
var saveLogsBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsSaveLogs"))
{
OnSelected = (GUITickBox) =>
{
//TODO: fix?
//showLogButton.Visible = SaveServerLogs;
return true;
}
};
GetPropertyData("SaveServerLogs").AssignGUIComponent(saveLogsBox);
//--------------------------------------------------------------------------------
// game settings
//--------------------------------------------------------------------------------
var roundsTab = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), settingsTabs[(int)SettingsTab.Rounds].RectTransform, Anchor.Center))
{
Stretch = true,
RelativeSpacing = 0.02f
};
var endBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform),
TextManager.Get("ServerSettingsEndRoundWhenDestReached"));
GetPropertyData("EndRoundAtLevelEnd").AssignGUIComponent(endBox);
@@ -353,7 +420,7 @@ namespace Barotrauma.Networking
TextManager.Get("ServerSettingsEndRoundVoting"));
GetPropertyData("AllowEndVoting").AssignGUIComponent(endVoteBox);
CreateLabeledSlider(roundsTab, "ServerSettingsEndRoundVotesRequired", out GUIScrollBar slider, out GUITextBlock sliderLabel);
CreateLabeledSlider(roundsTab, "ServerSettingsEndRoundVotesRequired", out slider, out sliderLabel);
string endRoundLabel = sliderLabel.Text;
slider.Step = 0.2f;
@@ -361,7 +428,7 @@ namespace Barotrauma.Networking
GetPropertyData("EndVoteRequiredRatio").AssignGUIComponent(slider);
slider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
((GUITextBlock)scrollBar.UserData).Text = endRoundLabel + (int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 10.0f) + " %";
((GUITextBlock)scrollBar.UserData).Text = endRoundLabel + " " + (int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 10.0f) + " %";
return true;
};
slider.OnMoved(slider, slider.BarScroll);
@@ -378,7 +445,7 @@ namespace Barotrauma.Networking
slider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
GUITextBlock text = scrollBar.UserData as GUITextBlock;
text.Text = intervalLabel + ToolBox.SecondsToReadableTime(scrollBar.BarScrollValue);
text.Text = intervalLabel + " " + ToolBox.SecondsToReadableTime(scrollBar.BarScrollValue);
return true;
};
slider.OnMoved(slider, slider.BarScroll);
@@ -437,6 +504,57 @@ namespace Barotrauma.Networking
};
slider.OnMoved(slider, slider.BarScroll);
var ragdollButtonBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), TextManager.Get("ServerSettingsAllowRagdollButton"));
GetPropertyData("AllowRagdollButton").AssignGUIComponent(ragdollButtonBox);
var traitorRatioBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), roundsTab.RectTransform), TextManager.Get("ServerSettingsUseTraitorRatio"));
CreateLabeledSlider(roundsTab, "", out slider, out sliderLabel);
var traitorRatioSlider = slider;
traitorRatioBox.OnSelected = (GUITickBox) =>
{
traitorRatioSlider.OnMoved(traitorRatioSlider, traitorRatioSlider.BarScroll);
return true;
};
if (TraitorUseRatio)
{
traitorRatioSlider.Range = new Vector2(0.1f, 1.0f);
}
else
{
traitorRatioSlider.Range = new Vector2(1.0f, maxPlayers);
}
string traitorRatioLabel = TextManager.Get("ServerSettingsTraitorRatio") + " ";
string traitorCountLabel = TextManager.Get("ServerSettingsTraitorCount") + " ";
traitorRatioSlider.Range = new Vector2(0.1f, 1.0f);
traitorRatioSlider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
GUITextBlock traitorText = scrollBar.UserData as GUITextBlock;
if (traitorRatioBox.Selected)
{
scrollBar.Step = 0.01f;
scrollBar.Range = new Vector2(0.1f, 1.0f);
traitorText.Text = traitorRatioLabel + (int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 1.0f) + " %";
}
else
{
scrollBar.Step = 1f / (maxPlayers - 1);
scrollBar.Range = new Vector2(1.0f, maxPlayers);
traitorText.Text = traitorCountLabel + scrollBar.BarScrollValue;
}
return true;
};
GetPropertyData("TraitorUseRatio").AssignGUIComponent(traitorRatioBox);
GetPropertyData("TraitorRatio").AssignGUIComponent(traitorRatioSlider);
traitorRatioSlider.OnMoved(traitorRatioSlider, traitorRatioSlider.BarScroll);
traitorRatioBox.OnSelected(traitorRatioBox);
var buttonHolder = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.07f), roundsTab.RectTransform), isHorizontal: true)
{
Stretch = true,
@@ -558,68 +676,21 @@ namespace Barotrauma.Networking
};
}
//--------------------------------------------------------------------------------
// server settings
// antigriefing
//--------------------------------------------------------------------------------
var serverTab = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), settingsTabs[(int)SettingsTab.Server].RectTransform, Anchor.Center))
var antigriefingTab = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), settingsTabs[(int)SettingsTab.Antigriefing].RectTransform, Anchor.Center))
{
Stretch = true,
RelativeSpacing = 0.02f
};
//***********************************************
var voiceChatEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform),
TextManager.Get("ServerSettingsVoiceChatEnabled"));
GetPropertyData("VoiceChatEnabled").AssignGUIComponent(voiceChatEnabled);
//***********************************************
string autoRestartDelayLabel = TextManager.Get("ServerSettingsAutoRestartDelay") + " ";
var startIntervalText = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), autoRestartDelayLabel);
var startIntervalSlider = new GUIScrollBar(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), barSize: 0.1f)
{
UserData = startIntervalText,
Step = 0.05f,
OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
GUITextBlock text = scrollBar.UserData as GUITextBlock;
text.Text = autoRestartDelayLabel + ToolBox.SecondsToReadableTime(scrollBar.BarScrollValue);
return true;
}
};
startIntervalSlider.Range = new Vector2(10.0f, 300.0f);
GetPropertyData("AutoRestartInterval").AssignGUIComponent(startIntervalSlider);
startIntervalSlider.OnMoved(startIntervalSlider, startIntervalSlider.BarScroll);
//***********************************************
var startWhenClientsReady = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform),
TextManager.Get("ServerSettingsStartWhenClientsReady"));
GetPropertyData("StartWhenClientsReady").AssignGUIComponent(startWhenClientsReady);
CreateLabeledSlider(serverTab, "ServerSettingsStartWhenClientsReadyRatio", out slider, out sliderLabel);
string clientsReadyRequiredLabel = sliderLabel.Text;
slider.Step = 0.2f;
slider.Range = new Vector2(0.5f, 1.0f);
slider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
((GUITextBlock)scrollBar.UserData).Text = clientsReadyRequiredLabel.Replace("[percentage]", ((int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 10.0f)).ToString());
return true;
};
GetPropertyData("StartWhenClientsReadyRatio").AssignGUIComponent(slider);
slider.OnMoved(slider, slider.BarScroll);
//***********************************************
var allowSpecBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsAllowSpectating"));
GetPropertyData("AllowSpectating").AssignGUIComponent(allowSpecBox);
var voteKickBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsAllowVoteKick"));
var voteKickBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), antigriefingTab.RectTransform), TextManager.Get("ServerSettingsAllowVoteKick"));
GetPropertyData("AllowVoteKick").AssignGUIComponent(voteKickBox);
CreateLabeledSlider(serverTab, "ServerSettingsKickVotesRequired", out slider, out sliderLabel);
CreateLabeledSlider(antigriefingTab, "ServerSettingsKickVotesRequired", out slider, out sliderLabel);
string votesRequiredLabel = sliderLabel.Text + " ";
slider.Step = 0.2f;
slider.Range = new Vector2(0.5f, 1.0f);
@@ -631,9 +702,9 @@ namespace Barotrauma.Networking
GetPropertyData("KickVoteRequiredRatio").AssignGUIComponent(slider);
slider.OnMoved(slider, slider.BarScroll);
CreateLabeledSlider(serverTab, "ServerSettingsAutobanTime", out slider, out sliderLabel);
CreateLabeledSlider(antigriefingTab, "ServerSettingsAutobanTime", out slider, out sliderLabel);
string autobanLabel = sliderLabel.Text + " ";
slider.Step = 0.05f;
slider.Step = 0.01f;
slider.Range = new Vector2(0.0f, MaxAutoBanTime);
slider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
@@ -643,91 +714,66 @@ namespace Barotrauma.Networking
GetPropertyData("AutoBanTime").AssignGUIComponent(slider);
slider.OnMoved(slider, slider.BarScroll);
var shareSubsBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsShareSubFiles"));
GetPropertyData("AllowFileTransfers").AssignGUIComponent(shareSubsBox);
// karma --------------------------------------------------------------------------
var randomizeLevelBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsRandomizeSeed"));
GetPropertyData("RandomizeSeed").AssignGUIComponent(randomizeLevelBox);
var saveLogsBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsSaveLogs"))
{
OnSelected = (GUITickBox) =>
{
//TODO: fix?
//showLogButton.Visible = SaveServerLogs;
return true;
}
};
GetPropertyData("SaveServerLogs").AssignGUIComponent(saveLogsBox);
var ragdollButtonBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsAllowRagdollButton"));
GetPropertyData("AllowRagdollButton").AssignGUIComponent(ragdollButtonBox);
var traitorRatioBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsUseTraitorRatio"));
CreateLabeledSlider(serverTab, "", out slider, out sliderLabel);
/*var traitorRatioText = new GUITextBlock(new Rectangle(20, y + 20, 20, 20), "Traitor ratio: 20 %", "", settingsTabs[1], GUI.SmallFont);
var traitorRatioSlider = new GUIScrollBar(new Rectangle(150, y + 22, 100, 15), "", 0.1f, settingsTabs[1]);*/
var traitorRatioSlider = slider;
traitorRatioBox.OnSelected = (GUITickBox) =>
{
traitorRatioSlider.OnMoved(traitorRatioSlider, traitorRatioSlider.BarScroll);
return true;
};
if (TraitorUseRatio)
{
traitorRatioSlider.Range = new Vector2(0.1f, 1.0f);
}
else
{
traitorRatioSlider.Range = new Vector2(1.0f, maxPlayers);
}
string traitorRatioLabel = TextManager.Get("ServerSettingsTraitorRatio") + " ";
string traitorCountLabel = TextManager.Get("ServerSettingsTraitorCount") + " ";
traitorRatioSlider.Range = new Vector2(0.1f, 1.0f);
traitorRatioSlider.OnMoved = (GUIScrollBar scrollBar, float barScroll) =>
{
GUITextBlock traitorText = scrollBar.UserData as GUITextBlock;
if (traitorRatioBox.Selected)
{
scrollBar.Step = 0.01f;
scrollBar.Range = new Vector2(0.1f, 1.0f);
traitorText.Text = traitorRatioLabel + (int)MathUtils.Round(scrollBar.BarScrollValue * 100.0f, 1.0f) + " %";
}
else
{
scrollBar.Step = 1f / (maxPlayers - 1);
scrollBar.Range = new Vector2(1.0f, maxPlayers);
traitorText.Text = traitorCountLabel + scrollBar.BarScrollValue;
}
return true;
};
GetPropertyData("TraitorUseRatio").AssignGUIComponent(traitorRatioBox);
GetPropertyData("TraitorRatio").AssignGUIComponent(traitorRatioSlider);
traitorRatioSlider.OnMoved(traitorRatioSlider, traitorRatioSlider.BarScroll);
traitorRatioBox.OnSelected(traitorRatioBox);
var karmaBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), serverTab.RectTransform), TextManager.Get("ServerSettingsUseKarma"));
var karmaBox = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.05f), antigriefingTab.RectTransform), TextManager.Get("ServerSettingsUseKarma"));
GetPropertyData("KarmaEnabled").AssignGUIComponent(karmaBox);
karmaPresetDD = new GUIDropDown(new RectTransform(new Vector2(1.0f, 0.05f), antigriefingTab.RectTransform));
foreach (string karmaPreset in GameMain.NetworkMember.KarmaManager.Presets.Keys)
{
karmaPresetDD.AddItem(TextManager.Get("KarmaPreset." + karmaPreset), karmaPreset);
}
var karmaSettingsContainer = new GUIFrame(new RectTransform(new Vector2(1.0f, 0.5f), antigriefingTab.RectTransform), style: null);
var karmaSettingsList = new GUIListBox(new RectTransform(Vector2.One, karmaSettingsContainer.RectTransform));
karmaSettingsBlocker = new GUIFrame(new RectTransform(Vector2.One, karmaSettingsContainer.RectTransform, Anchor.CenterLeft) { MaxSize = new Point(karmaSettingsList.Content.Rect.Width, int.MaxValue) },
style: "InnerFrame");
karmaPresetDD.OnSelected = (selected, obj) =>
{
List<NetPropertyData> properties = netProperties.Values.ToList();
List<object> prevValues = new List<object>();
foreach (NetPropertyData prop in netProperties.Values)
{
prevValues.Add(prop.TempValue);
if (prop.GUIComponent != null) { prop.Value = prop.GUIComponentValue; }
}
if (KarmaPreset == "custom")
{
GameMain.NetworkMember?.KarmaManager?.SaveCustomPreset();
GameMain.NetworkMember?.KarmaManager?.Save();
}
KarmaPreset = obj as string;
GameMain.NetworkMember.KarmaManager.SelectPreset(KarmaPreset);
karmaSettingsList.Content.ClearChildren();
karmaSettingsBlocker.Visible = !karmaBox.Selected || KarmaPreset != "custom";
GameMain.NetworkMember.KarmaManager.CreateSettingsFrame(karmaSettingsList.Content);
for (int i = 0; i < netProperties.Count; i++)
{
properties[i].TempValue = prevValues[i];
}
return true;
};
karmaPresetDD.SelectItem(KarmaPreset);
AssignGUIComponent("KarmaPreset", karmaPresetDD);
karmaBox.OnSelected = (tb) =>
{
karmaSettingsBlocker.Visible = !tb.Selected || KarmaPreset != "custom";
return true;
};
//--------------------------------------------------------------------------------
// banlist
//--------------------------------------------------------------------------------
BanList.CreateBanFrame(settingsTabs[2]);
BanList.CreateBanFrame(settingsTabs[(int)SettingsTab.Banlist]);
//--------------------------------------------------------------------------------
// whitelist
//--------------------------------------------------------------------------------
Whitelist.CreateWhiteListFrame(settingsTabs[3]);
Whitelist.CreateWhiteListFrame(settingsTabs[(int)SettingsTab.Whitelist]);
}
private void CreateLabeledSlider(GUIComponent parent, string labelTag, out GUIScrollBar slider, out GUITextBlock label)
@@ -763,6 +809,11 @@ namespace Barotrauma.Networking
{
if (settingsFrame == null)
{
if (KarmaPreset == "custom")
{
GameMain.NetworkMember?.KarmaManager?.SaveCustomPreset();
GameMain.NetworkMember?.KarmaManager?.Save();
}
CreateSettingsFrame();
}
else
@@ -777,44 +828,5 @@ namespace Barotrauma.Networking
return false;
}
public void ManagePlayersFrame(GUIFrame infoFrame)
{
GUIListBox cList = new GUIListBox(new RectTransform(Vector2.One, infoFrame.RectTransform));
/*foreach (Client c in ConnectedClients)
{
var frame = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.15f), cList.Content.RectTransform),
c.Name + " (" + c.Connection.RemoteEndPoint.Address.ToString() + ")", style: "ListBoxElement")
{
Color = (c.InGame && c.Character != null && !c.Character.IsDead) ? Color.Gold * 0.2f : Color.Transparent,
HoverColor = Color.LightGray * 0.5f,
SelectedColor = Color.Gold * 0.5f
};
var buttonArea = new GUILayoutGroup(new RectTransform(new Vector2(0.45f, 0.85f), frame.RectTransform, Anchor.CenterRight) { RelativeOffset = new Vector2(0.05f, 0.0f) },
isHorizontal: true);
var kickButton = new GUIButton(new RectTransform(new Vector2(0.25f, 1.0f), buttonArea.RectTransform),
TextManager.Get("Kick"))
{
UserData = c.Name,
OnClicked = GameMain.NetLobbyScreen.KickPlayer
};
var banButton = new GUIButton(new RectTransform(new Vector2(0.25f, 1.0f), buttonArea.RectTransform),
TextManager.Get("Ban"))
{
UserData = c.Name,
OnClicked = GameMain.NetLobbyScreen.BanPlayer
};
var rangebanButton = new GUIButton(new RectTransform(new Vector2(0.25f, 1.0f), buttonArea.RectTransform),
TextManager.Get("BanRange"))
{
UserData = c.Name,
OnClicked = GameMain.NetLobbyScreen.BanPlayerRange
};
}*/ //TODO: reimplement
}
}
}
@@ -597,6 +597,8 @@ namespace Barotrauma.Steam
if (string.IsNullOrEmpty(item.Error))
{
DebugConsole.NewMessage("Published workshop item " + item.Title + " successfully.", Microsoft.Xna.Framework.Color.LightGreen);
var newItem = instance.client.Workshop.GetItem(item.Id);
newItem?.Subscribe();
}
else
{
@@ -56,6 +56,8 @@ namespace Barotrauma.Particles
private int animFrame;
private float collisionUpdateTimer;
public bool HighQualityCollisionDetection;
public ParticlePrefab.DrawTargetType DrawTarget
{
@@ -133,6 +135,8 @@ namespace Barotrauma.Particles
velocityChange = prefab.VelocityChangeDisplay;
velocityChangeWater = prefab.VelocityChangeWaterDisplay;
HighQualityCollisionDetection = false;
OnChangeHull = null;
subEmitters.Clear();
@@ -224,7 +228,7 @@ namespace Barotrauma.Particles
}
lifeTime -= deltaTime;
if (lifeTime <= 0.0f || color.A <= 0 || size.X <= 0.0f || size.Y <= 0.0f) return false;
if (lifeTime <= 0.0f || color.A <= 0 || size.X <= 0.0f || size.Y <= 0.0f) { return false; }
if (hasSubEmitters)
{
@@ -234,16 +238,23 @@ namespace Barotrauma.Particles
}
}
if (!prefab.UseCollision) return true;
if (!prefab.UseCollision) { return true; }
collisionUpdateTimer -= deltaTime;
if (collisionUpdateTimer <= 0.0f)
if (HighQualityCollisionDetection)
{
//more frequent collision updates if the particle is moving fast
collisionUpdateTimer = 0.5f - Math.Min((Math.Abs(velocity.X) + Math.Abs(velocity.Y)) * 0.001f, 0.4f);
return CollisionUpdate();
}
else
{
collisionUpdateTimer -= deltaTime;
if (collisionUpdateTimer <= 0.0f)
{
//more frequent collision updates if the particle is moving fast
collisionUpdateTimer = 0.5f - Math.Min((Math.Abs(velocity.X) + Math.Abs(velocity.Y)) * 0.01f, 0.45f);
return CollisionUpdate();
}
}
return true;
}
@@ -288,7 +299,7 @@ namespace Barotrauma.Particles
bool gapFound = false;
foreach (Gap gap in hullGaps)
{
if (gap.Open <= 0.0f || gap.IsHorizontal != (collisionNormal.X != 0.0f)) continue;
if (gap.Open <= 0.9f || gap.IsHorizontal != (collisionNormal.X != 0.0f)) continue;
if (gap.IsHorizontal)
{
@@ -56,6 +56,7 @@ namespace Barotrauma.Particles
if (particle != null)
{
particle.Size *= Rand.Range(Prefab.ScaleMin, Prefab.ScaleMax);
particle.HighQualityCollisionDetection = Prefab.HighQualityCollisionDetection;
}
}
@@ -98,6 +99,8 @@ namespace Barotrauma.Particles
public readonly float ParticlesPerSecond;
public readonly bool HighQualityCollisionDetection;
public readonly bool CopyEntityAngle;
public ParticleEmitterPrefab(XElement element)
@@ -145,7 +148,7 @@ namespace Barotrauma.Particles
EmitInterval = element.GetAttributeFloat("emitinterval", 0.0f);
ParticlesPerSecond = element.GetAttributeInt("particlespersecond", 0);
ParticleAmount = element.GetAttributeInt("particleamount", 0);
HighQualityCollisionDetection = element.GetAttributeBool("highqualitycollisiondetection", false);
CopyEntityAngle = element.GetAttributeBool("copyentityangle", false);
}
}
@@ -45,7 +45,7 @@ namespace Barotrauma
{
if (!body.Enabled)
{
color = Color.Gray;
color = Color.Black;
}
else if (!body.Awake)
{
@@ -267,6 +267,17 @@ namespace Barotrauma
sb.AppendLine(exception.StackTrace);
sb.AppendLine("\n");
if (exception.InnerException != null)
{
sb.AppendLine("InnerException: " + exception.InnerException.Message);
if (exception.InnerException.TargetSite != null)
{
sb.AppendLine("Target site: " + exception.InnerException.TargetSite.ToString());
}
sb.AppendLine("Stack trace: ");
sb.AppendLine(exception.InnerException.StackTrace);
}
sb.AppendLine("Last debug messages:");
for (int i = DebugConsole.Messages.Count - 1; i >= 0; i--)
{
@@ -2788,6 +2788,7 @@ namespace Barotrauma
if (editRagdoll || !editLimbs && !editJoints)
{
RagdollParams.AddToEditor(ParamsEditor.Instance, alsoChildren: false);
RagdollParams.ColliderParams.ForEach(c => c.AddToEditor(ParamsEditor.Instance));
}
if (editJoints)
{
@@ -3041,14 +3042,16 @@ namespace Barotrauma
private void CalculateSpritesheetZoom()
{
float width = textures.OrderByDescending(t => t.Width).First().Width;
var texture = textures.OrderByDescending(t => t.Width).FirstOrDefault();
if (texture == null)
{
spriteSheetZoom = 1;
return;
}
float width = texture.Width;
float height = textures.Sum(t => t.Height);
float margin = 20;
if (textures == null || textures.None())
{
spriteSheetMaxZoom = 1;
}
else if (height > width)
if (height > width)
{
spriteSheetMaxZoom = (centerArea.Rect.Bottom - spriteSheetOffsetY - margin) / height;
}
@@ -415,9 +415,22 @@ namespace Barotrauma
ServerInfo s1 = c1.GUIComponent.UserData as ServerInfo;
ServerInfo s2 = c2.GUIComponent.UserData as ServerInfo;
if (s1 == null && s2 == null)
{
return 0;
}
else if (s1 == null)
{
return ascending ? 1 : -1;
}
else if (s2 == null)
{
return ascending ? -1 : 1;
}
switch (sortBy)
{
case "ServerListCompatible":
case "ServerListCompatible":
bool? s1Compatible = NetworkMember.IsCompatible(GameMain.Version.ToString(), s1.GameVersion);
if (!s1.ContentPackageHashes.Any()) { s1Compatible = null; }
if (s1Compatible.HasValue) { s1Compatible = s1Compatible.Value && s1.ContentPackagesMatch(GameMain.SelectedPackages); };
@@ -441,7 +454,7 @@ namespace Barotrauma
if (s1.HasPassword == s2.HasPassword) { return 0; }
return (s1.HasPassword ? 1 : -1) * (ascending ? 1 : -1);
case "ServerListName":
return s1.ServerName.CompareTo(s2.ServerName) * (ascending ? 1 : -1);
return string.Compare(s1.ServerName, s2.ServerName) * (ascending ? 1 : -1);
case "ServerListRoundStarted":
if (s1.GameStarted == s2.GameStarted) { return 0; }
return (s1.GameStarted ? 1 : -1) * (ascending ? 1 : -1);
@@ -20,6 +20,8 @@ namespace Barotrauma
private GUIFrame bottomPanel;
private GUIFrame backgroundColorPanel;
private bool drawGrid, snapToGrid;
private GUIFrame topPanelContents;
private GUITextBlock texturePathText;
private GUITextBlock xmlPathText;
@@ -137,7 +139,7 @@ namespace Barotrauma
return true;
}
};
new GUIButton(new RectTransform(new Vector2(0.05f, 0.35f), topPanelContents.RectTransform, Anchor.TopCenter, Pivot.CenterLeft) { RelativeOffset = new Vector2(0.055f, 0.3f) }, "Reset Zoom")
var resetBtn = new GUIButton(new RectTransform(new Vector2(0.05f, 0.35f), topPanelContents.RectTransform, Anchor.TopCenter, Pivot.CenterLeft) { RelativeOffset = new Vector2(0.055f, 0.3f) }, "Reset Zoom")
{
OnClicked = (box, data) =>
{
@@ -145,6 +147,26 @@ namespace Barotrauma
return true;
}
};
resetBtn.TextBlock.AutoScale = true;
new GUITickBox(new RectTransform(new Vector2(0.2f, 0.2f), topPanelContents.RectTransform, Anchor.BottomCenter, Pivot.CenterRight) { RelativeOffset = new Vector2(0, 0.3f) }, "Show grid")
{
Selected = drawGrid,
OnSelected = (tickBox) =>
{
drawGrid = tickBox.Selected;
return true;
}
};
new GUITickBox(new RectTransform(new Vector2(0.2f, 0.2f), topPanelContents.RectTransform, Anchor.BottomCenter, Pivot.CenterRight) { RelativeOffset = new Vector2(0.17f, 0.3f) }, "Snap to grid")
{
Selected = snapToGrid,
OnSelected = (tickBox) =>
{
snapToGrid = tickBox.Selected;
return true;
}
};
texturePathText = new GUITextBlock(new RectTransform(new Vector2(0.5f, 0.4f), topPanelContents.RectTransform, Anchor.Center, Pivot.BottomCenter) { RelativeOffset = new Vector2(0.4f, 0) }, "", Color.LightGray);
xmlPathText = new GUITextBlock(new RectTransform(new Vector2(0.5f, 0.4f), topPanelContents.RectTransform, Anchor.Center, Pivot.TopCenter) { RelativeOffset = new Vector2(0.4f, 0) }, "", Color.LightGray);
@@ -230,8 +252,7 @@ namespace Barotrauma
}, style: null, color: Color.Black * 0.6f);
var colorLabel = new GUITextBlock(new RectTransform(new Vector2(0.3f, 1), element.RectTransform, Anchor.CenterLeft), colorComponentLabels[i],
font: GUI.SmallFont, textAlignment: Alignment.CenterLeft);
GUINumberInput numberInput = new GUINumberInput(new RectTransform(new Vector2(0.7f, 1), element.RectTransform, Anchor.CenterRight),
GUINumberInput.NumberType.Int)
var numberInput = new GUINumberInput(new RectTransform(new Vector2(0.7f, 1), element.RectTransform, Anchor.CenterRight), GUINumberInput.NumberType.Int)
{
Font = GUI.SmallFont
};
@@ -259,26 +280,32 @@ namespace Barotrauma
}
}
private HashSet<Sprite> loadedSprites = new HashSet<Sprite>();
private readonly HashSet<Sprite> loadedSprites = new HashSet<Sprite>();
private void LoadSprites()
{
loadedSprites.ForEach(s => s.Remove());
loadedSprites.Clear();
//foreach (string filePath in ContentPackage.GetAllContentFiles(GameMain.SelectedPackages))
//{
// XDocument doc = XMLExtensions.TryLoadXml(filePath);
// if (doc != null && doc.Root != null)
// {
// LoadSprites(doc.Root);
// }
//}
var contentPackages = GameMain.Config.SelectedContentPackages.ToList();
foreach (string filePath in Directory.GetFiles("Content/", "*.xml", SearchOption.AllDirectories))
#if !DEBUG
var vanilla = GameMain.VanillaContent;
if (vanilla != null)
{
XDocument doc = XMLExtensions.TryLoadXml(filePath);
if (doc != null && doc.Root != null)
contentPackages.Remove(vanilla);
}
#endif
foreach (var contentPackage in contentPackages)
{
foreach (var file in contentPackage.Files)
{
LoadSprites(doc.Root);
if (file.Path.EndsWith(".xml"))
{
XDocument doc = XMLExtensions.TryLoadXml(file.Path);
if (doc != null && doc.Root != null)
{
LoadSprites(doc.Root);
}
}
}
}
@@ -304,11 +331,12 @@ namespace Barotrauma
{
string spriteFolder = "";
string textureElement = element.GetAttributeString("texture", "");
// TODO: parse and create
// TODO: parse and create?
if (textureElement.Contains("[GENDER]") || textureElement.Contains("[HEADID]") || textureElement.Contains("[RACE]")) { return; }
if (!textureElement.Contains("/"))
{
spriteFolder = Path.GetDirectoryName(element.ParseContentPathFromUri());
var parsedPath = element.ParseContentPathFromUri();
spriteFolder = Path.GetDirectoryName(parsedPath);
}
// Uncomment if we do multiple passes -> there can be duplicates
//string identifier = Sprite.GetID(element);
@@ -344,7 +372,7 @@ namespace Barotrauma
xmlPathText.TextColor = Color.LightGreen;
return true;
}
#endregion
#endregion
#region Public methods
public override void AddToGUIUpdateList()
@@ -466,6 +494,11 @@ namespace Barotrauma
//GUI.DrawRectangle(spriteBatch, viewArea, Color.Green, isFilled: false);
GUI.DrawRectangle(spriteBatch, textureRect, Color.Gray, isFilled: false);
if (drawGrid)
{
DrawGrid(spriteBatch, textureRect, zoom, Submarine.GridSize);
}
foreach (GUIComponent element in spriteList.Content.Children)
{
Sprite sprite = element.UserData as Sprite;
@@ -507,8 +540,11 @@ namespace Barotrauma
w.tooltip = $"Position: {sprite.SourceRect.Location}";
w.MouseHeld += dTime =>
{
w.DrawPos = PlayerInput.MousePosition;
sprite.SourceRect = new Rectangle(((w.DrawPos + new Vector2(w.size / 2) - textureRect.Location.ToVector2()) / zoom).ToPoint(), sprite.SourceRect.Size);
w.DrawPos = (drawGrid && snapToGrid) ?
SnapToGrid(PlayerInput.MousePosition, textureRect, zoom, Submarine.GridSize, Submarine.GridSize.X / 4.0f * zoom) :
PlayerInput.MousePosition;
w.DrawPos = new Vector2((float)Math.Ceiling(w.DrawPos.X), (float)Math.Ceiling(w.DrawPos.Y));
sprite.SourceRect = new Rectangle(((w.DrawPos - textureRect.Location.ToVector2()) / zoom).ToPoint(), sprite.SourceRect.Size);
if (spriteList.SelectedComponent is GUITextBlock textBox)
{
// TODO: cache the sprite name?
@@ -516,15 +552,18 @@ namespace Barotrauma
}
w.tooltip = $"Position: {sprite.SourceRect.Location}";
};
w.refresh = () => w.DrawPos = textureRect.Location.ToVector2() + sprite.SourceRect.Location.ToVector2() * zoom - new Vector2(w.size / 2);
w.refresh = () => w.DrawPos = textureRect.Location.ToVector2() + sprite.SourceRect.Location.ToVector2() * zoom;
});
var sizeWidget = GetWidget($"{id}_size", sprite, widgetSize, Widget.Shape.Rectangle, initMethod: w =>
{
w.tooltip = $"Size: {sprite.SourceRect.Size}";
w.MouseHeld += dTime =>
{
w.DrawPos = PlayerInput.MousePosition;
sprite.SourceRect = new Rectangle(sprite.SourceRect.Location, ((w.DrawPos - new Vector2(w.size) - positionWidget.DrawPos) / zoom).ToPoint());
w.DrawPos = (drawGrid && snapToGrid) ?
SnapToGrid(PlayerInput.MousePosition, textureRect, zoom, Submarine.GridSize, Submarine.GridSize.X / 4.0f * zoom) :
PlayerInput.MousePosition;
w.DrawPos = new Vector2((float)Math.Ceiling(w.DrawPos.X), (float)Math.Ceiling(w.DrawPos.Y));
sprite.SourceRect = new Rectangle(sprite.SourceRect.Location, ((w.DrawPos - positionWidget.DrawPos) / zoom).ToPoint());
// TODO: allow to lock the origin
sprite.RelativeOrigin = sprite.RelativeOrigin;
if (spriteList.SelectedComponent is GUITextBlock textBox)
@@ -534,7 +573,7 @@ namespace Barotrauma
}
w.tooltip = $"Size: {sprite.SourceRect.Size}";
};
w.refresh = () => w.DrawPos = textureRect.Location.ToVector2() + new Vector2(sprite.SourceRect.Right, sprite.SourceRect.Bottom) * zoom + new Vector2(w.size / 2);
w.refresh = () => w.DrawPos = textureRect.Location.ToVector2() + new Vector2(sprite.SourceRect.Right, sprite.SourceRect.Bottom) * zoom;
});
if (isSelected)
{
@@ -553,6 +592,58 @@ namespace Barotrauma
spriteBatch.End();
}
private void DrawGrid(SpriteBatch spriteBatch, Rectangle gridArea, float zoom, Vector2 gridSize)
{
gridSize *= zoom;
if (gridSize.X < 1.0f) { return; }
if (gridSize.Y < 1.0f) { return; }
int xLines = (int)(gridArea.Width / gridSize.X);
int yLines = (int)(gridArea.Height / gridSize.Y);
for (int x = 0; x <= xLines; x++)
{
GUI.DrawLine(spriteBatch,
new Vector2(gridArea.X + x * gridSize.X, gridArea.Y),
new Vector2(gridArea.X + x * gridSize.X, gridArea.Bottom),
Color.White * 0.25f);
}
for (int y = 0; y <= yLines; y++)
{
GUI.DrawLine(spriteBatch,
new Vector2(gridArea.X, gridArea.Y + y * gridSize.Y),
new Vector2(gridArea.Right, gridArea.Y + y * gridSize.Y),
Color.White * 0.25f);
}
}
private Vector2 SnapToGrid(Vector2 position, Rectangle gridArea, float zoom, Vector2 gridSize, float tolerance)
{
gridSize *= zoom;
if (gridSize.X < 1.0f) { return position; }
if (gridSize.Y < 1.0f) { return position; }
Vector2 snappedPos = position;
snappedPos.X -= gridArea.X;
snappedPos.Y -= gridArea.Y;
Vector2 gridPos = new Vector2(
MathUtils.RoundTowardsClosest(snappedPos.X, gridSize.X),
MathUtils.RoundTowardsClosest(snappedPos.Y, gridSize.Y));
if (Math.Abs(gridPos.X - snappedPos.X) < tolerance)
{
snappedPos.X = gridPos.X;
}
if (Math.Abs(gridPos.Y - snappedPos.Y) < tolerance)
{
snappedPos.Y = gridPos.Y;
}
snappedPos.X += gridArea.X;
snappedPos.Y += gridArea.Y;
return snappedPos;
}
public override void Select()
{
base.Select();
@@ -706,7 +797,7 @@ namespace Barotrauma
zoomBar.BarScroll = GetBarScrollValue();
viewAreaOffset = Point.Zero;
}
#endregion
#endregion
#region Helpers
private Point viewAreaOffset;
@@ -750,7 +841,7 @@ namespace Barotrauma
// Keeps the relative origin unchanged. The absolute origin will be recalculated.
sprite.RelativeOrigin = sprite.RelativeOrigin;
}
#endregion
#endregion
#region Widgets
private Dictionary<string, Widget> widgets = new Dictionary<string, Widget>();
@@ -792,6 +883,6 @@ namespace Barotrauma
widgets.Clear();
Widget.selectedWidgets.Clear();
}
#endregion
#endregion
}
}
@@ -51,7 +51,7 @@ namespace Barotrauma
tabs = new GUIFrame[Enum.GetValues(typeof(Tab)).Length];
menu = new GUIFrame(new RectTransform(new Vector2(0.85f, 0.8f), GUI.Canvas, Anchor.Center) { MinSize = new Point(GameMain.GraphicsHeight, 0) });
menu = new GUIFrame(new RectTransform(new Vector2(0.85f, 0.85f), GUI.Canvas, Anchor.Center) { MinSize = new Point(GameMain.GraphicsHeight, 0) });
var container = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.85f), menu.RectTransform, Anchor.Center) { RelativeOffset = new Vector2(0.0f, 0.05f) }) { Stretch = true };
@@ -111,6 +111,7 @@ namespace Barotrauma
var listContainer = new GUILayoutGroup(new RectTransform(new Vector2(0.5f, 1.0f), tabs[(int)Tab.Browse].RectTransform))
{
RelativeSpacing = 0.01f,
Stretch = true
};
@@ -125,7 +126,7 @@ namespace Barotrauma
};
var findModsButtonContainer = new GUIFrame(new RectTransform(new Vector2(1.0f, 0.02f), listContainer.RectTransform), style: null);
new GUIButton(new RectTransform(new Vector2(1.0f, 1.0f), findModsButtonContainer.RectTransform, Anchor.Center), TextManager.Get("FindModsButton"), style: null)
new GUIButton(new RectTransform(new Vector2(1.0f, 0.9f), findModsButtonContainer.RectTransform, Anchor.Center), TextManager.Get("FindModsButton"), style: null)
{
Color = new Color(38, 86, 38, 75),
HoverColor = new Color(85, 203, 99, 50),
@@ -260,7 +261,12 @@ namespace Barotrauma
private void RefreshItemLists()
{
SteamManager.GetSubscribedWorkshopItems((items) => { OnItemsReceived(items, subscribedItemList); });
SteamManager.GetSubscribedWorkshopItems((items) =>
{
//filter out the items published by the player (they're shown in the publish tab)
var mySteamID = SteamManager.GetSteamID();
OnItemsReceived(items.Where(it => it.OwnerId != mySteamID).ToList(), subscribedItemList);
});
SteamManager.GetPopularWorkshopItems((items) => { OnItemsReceived(items, topItemList); }, 20);
SteamManager.GetPublishedWorkshopItems((items) => { OnItemsReceived(items, publishedItemList); });
@@ -704,19 +710,17 @@ namespace Barotrauma
}
};
var headerAreaBackground = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.5f), content.RectTransform, maxSize: new Point(int.MaxValue, 235))) { Color = Color.Black };
var headerArea = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 1.0f), headerAreaBackground.RectTransform), childAnchor: Anchor.Center);
var headerArea = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.5f), content.RectTransform)) { Color = Color.Black };
if (itemPreviewSprites.ContainsKey(item.PreviewImageUrl))
{
new GUIImage(new RectTransform(new Point(headerArea.Rect.Width, headerArea.Rect.Height), headerArea.RectTransform), itemPreviewSprites[item.PreviewImageUrl], scaleToFit: true);
new GUIImage(new RectTransform(Vector2.One, headerArea.RectTransform), itemPreviewSprites[item.PreviewImageUrl], scaleToFit: true);
}
else
{
new GUIImage(new RectTransform(new Point(headerArea.Rect.Width, headerArea.Rect.Height), headerArea.RectTransform), SteamManager.Instance.DefaultPreviewImage, scaleToFit: true);
new GUIImage(new RectTransform(Vector2.One, headerArea.RectTransform), SteamManager.Instance.DefaultPreviewImage, scaleToFit: true);
}
var descriptionContainer = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.2f), content.RectTransform)) { ScrollBarVisible = true };
//spacing
@@ -944,21 +948,25 @@ namespace Barotrauma
tagBtn.TextBlock.AutoScale = true;
tagBtn.Color *= 0.5f;
tagBtn.SelectedColor = Color.LightGreen;
tagBtn.HoverColor = Color.Lerp(tagBtn.HoverColor, Color.LightGreen, 0.5f);
tagBtn.Selected = itemEditor.Tags.Any(t => t.ToLowerInvariant() == tag);
Color defaultTextColor = tagBtn.TextColor;
tagBtn.TextColor = tagBtn.Selected ? Color.LightGreen : defaultTextColor;
tagBtn.OnClicked = (btn, userdata) =>
{
if (!tagBtn.Selected)
{
if (!itemEditor.Tags.Any(t => t.ToLowerInvariant() == tag)) { itemEditor.Tags.Add(tagBtn.Text); }
tagBtn.Selected = true;
tagBtn.TextBlock.TextColor = Color.LightGreen;
tagBtn.TextColor = Color.LightGreen;
}
else
{
itemEditor.Tags.RemoveAll(t => t.ToLowerInvariant() == tagBtn.Text.ToLowerInvariant());
tagBtn.Selected = false;
tagBtn.TextBlock.TextColor = tagBtn.TextColor;
tagBtn.TextColor = defaultTextColor;
}
return true;
};
@@ -71,6 +71,12 @@ namespace Barotrauma
private Color primaryColor = new Color(12, 14, 15, 190);
private Color secondaryColor = new Color(12, 14, 15, 215);
private const int submarineNameLimit = 30;
private GUITextBlock submarineNameCharacterCount;
private const int submarineDescriptionLimit = 500;
private GUITextBlock submarineDescriptionCharacterCount;
public override Camera Cam
{
get { return cam; }
@@ -346,7 +352,6 @@ namespace Barotrauma
UseGridLayout = true,
CheckSelected = MapEntityPrefab.GetSelected
};
UpdateEntityList();
//empty guiframe as a separator
new GUIFrame(new RectTransform(new Vector2(1.0f, 0.02f), paddedLeftPanel.RectTransform), style: null);
@@ -603,14 +608,16 @@ namespace Barotrauma
}
entityList.Content.RectTransform.SortChildren((i1, i2) =>
entityList.Content.RectTransform.SortChildren((i1, i2) =>
(i1.GUIComponent.UserData as MapEntityPrefab).Name.CompareTo((i2.GUIComponent.UserData as MapEntityPrefab).Name));
}
public override void Select()
{
base.Select();
UpdateEntityList();
foreach (MapEntityPrefab prefab in MapEntityPrefab.List)
{
prefab.sprite?.EnsureLazyLoaded();
@@ -950,32 +957,60 @@ namespace Barotrauma
OnClicked = (btn, userdata) => { if (GUI.MouseOn == btn || GUI.MouseOn == btn.TextBlock) saveFrame = null; return true; }
};
var innerFrame = new GUIFrame(new RectTransform(new Vector2(0.4f, 0.45f), saveFrame.RectTransform, Anchor.Center) { MinSize = new Point(750, 400) });
var innerFrame = new GUIFrame(new RectTransform(new Vector2(0.4f, 0.5f), saveFrame.RectTransform, Anchor.Center) { MinSize = new Point(750, 400) });
var paddedSaveFrame = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.9f), innerFrame.RectTransform, Anchor.Center)) { Stretch = true, RelativeSpacing = 0.02f };
//var header = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.0f), paddedSaveFrame.RectTransform), TextManager.Get("SaveSubDialogHeader"), font: GUI.LargeFont);
var columnArea = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.9f), paddedSaveFrame.RectTransform), isHorizontal: true) { Stretch = true };
var leftColumn = new GUILayoutGroup(new RectTransform(new Vector2(0.55f, 1.0f), columnArea.RectTransform)) { RelativeSpacing = 0.02f, Stretch = true };
var leftColumn = new GUILayoutGroup(new RectTransform(new Vector2(0.55f, 1.0f), columnArea.RectTransform)) { RelativeSpacing = 0.01f, Stretch = true };
var rightColumn = new GUILayoutGroup(new RectTransform(new Vector2(0.42f, 1.0f), columnArea.RectTransform)) { RelativeSpacing = 0.02f, Stretch = true };
// left column -----------------------------------------------------------------------
var saveSubLabel = new GUITextBlock(new RectTransform(new Vector2(0.4f, 0.03f), leftColumn.RectTransform),
var nameHeaderGroup = new GUILayoutGroup(new RectTransform(new Vector2(.975f, 0.03f), leftColumn.RectTransform), true);
var saveSubLabel = new GUITextBlock(new RectTransform(new Vector2(.5f, 1f), nameHeaderGroup.RectTransform),
TextManager.Get("SaveSubDialogName"));
nameBox = new GUITextBox(new RectTransform(new Vector2(0.65f, 0.05f), leftColumn.RectTransform))
submarineNameCharacterCount = new GUITextBlock(new RectTransform(new Vector2(.5f, 1f), nameHeaderGroup.RectTransform), string.Empty, textAlignment: Alignment.TopRight);
nameBox = new GUITextBox(new RectTransform(new Vector2(.95f, 0.05f), leftColumn.RectTransform))
{
OnEnterPressed = ChangeSubName,
Text = GetSubName()
};
nameBox.OnTextChanged += (textBox, text) =>
{
if (text.Length > submarineNameLimit)
{
nameBox.Text = text.Substring(0, submarineNameLimit);
nameBox.Flash(Color.Red);
return true;
}
new GUITextBlock(new RectTransform(new Vector2(0.5f, 0.03f), leftColumn.RectTransform), TextManager.Get("SaveSubDialogDescription"));
submarineNameCharacterCount.Text = text.Length + " / " + submarineNameLimit;
return true;
};
submarineNameCharacterCount.Text = nameBox.Text.Length + " / " + submarineNameLimit;
var descriptionHeaderGroup = new GUILayoutGroup(new RectTransform(new Vector2(.975f, 0.03f), leftColumn.RectTransform), true);
new GUITextBlock(new RectTransform(new Vector2(0.5f, 1f), descriptionHeaderGroup.RectTransform), TextManager.Get("SaveSubDialogDescription"));
submarineDescriptionCharacterCount = new GUITextBlock(new RectTransform(new Vector2(.5f, 1f), descriptionHeaderGroup.RectTransform), string.Empty, textAlignment: Alignment.TopRight);
var descriptionContainer = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.25f), leftColumn.RectTransform));
descriptionBox = new GUITextBox(new RectTransform(Vector2.One, descriptionContainer.Content.RectTransform), font: GUI.SmallFont, wrap: true);
descriptionBox = new GUITextBox(new RectTransform(Vector2.One, descriptionContainer.Content.RectTransform, Anchor.Center), font: GUI.SmallFont, wrap: true);
descriptionBox.OnTextChanged += (textBox, text) =>
{
if (text.Length > submarineDescriptionLimit)
{
descriptionBox.Text = text.Substring(0, submarineDescriptionLimit);
descriptionBox.Flash(Color.Red);
return true;
}
Vector2 textSize = textBox.Font.MeasureString(descriptionBox.WrappedText);
textBox.RectTransform.NonScaledSize = new Point(textBox.RectTransform.NonScaledSize.X, Math.Max(descriptionContainer.Rect.Height, (int)textSize.Y + 10));
descriptionContainer.UpdateScrollBarSize();
@@ -984,6 +1019,7 @@ namespace Barotrauma
return true;
};
descriptionBox.Text = Submarine.MainSub == null ? "" : Submarine.MainSub.Description;
submarineDescriptionCharacterCount.Text = descriptionBox.Text.Length + " / " + submarineDescriptionLimit;
var crewSizeArea = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.03f), leftColumn.RectTransform), isHorizontal: true) { AbsoluteSpacing = 5 };
@@ -1493,8 +1529,21 @@ namespace Barotrauma
private void TryDeleteSub(Submarine sub)
{
if (sub == null) return;
if (sub == null) { return; }
//if the sub is included in a content package that only defines that one sub,
//delete the content package as well
ContentPackage subPackage = null;
foreach (ContentPackage cp in ContentPackage.List)
{
if (cp.Files.Count == 1 && Path.GetFullPath(cp.Files[0].Path) == Path.GetFullPath(sub.FilePath))
{
subPackage = cp;
break;
}
}
subPackage?.Delete();
var msgBox = new GUIMessageBox(
TextManager.Get("DeleteDialogLabel"),
TextManager.GetWithVariable("DeleteDialogQuestion", "[file]", sub.Name),
@@ -1524,7 +1573,6 @@ namespace Barotrauma
if (CharacterMode) SetCharacterMode(false);
if (WiringMode) SetWiringMode(false);
saveFrame = null;
loadFrame = null;
@@ -1754,7 +1802,9 @@ namespace Barotrauma
{
textBox.UserData = text;
}
submarineDescriptionCharacterCount.Text = text.Length + " / " + submarineDescriptionLimit;
return true;
}
@@ -2131,6 +2181,10 @@ namespace Barotrauma
{
dummyCharacter.SelectedConstruction.AddToGUIUpdateList();
}
else if (WiringMode && MapEntity.SelectedList.Count == 1 && MapEntity.SelectedList[0] is Item item && item.GetComponent<Wire>() != null)
{
MapEntity.SelectedList[0].AddToGUIUpdateList();
}
}
else
{
@@ -2290,9 +2344,9 @@ namespace Barotrauma
dummyCharacter.SelectedConstruction = null;
}*/
}
else if (MapEntity.FilteredSelectedList.Count == 1)
else if (MapEntity.SelectedList.Count == 1)
{
(MapEntity.FilteredSelectedList[0] as Item)?.UpdateHUD(cam, dummyCharacter, (float)deltaTime);
(MapEntity.SelectedList[0] as Item)?.UpdateHUD(cam, dummyCharacter, (float)deltaTime);
}
CharacterHUD.Update((float)deltaTime, dummyCharacter, cam);
@@ -203,6 +203,8 @@ namespace Barotrauma
public static void Update(float deltaTime)
{
if (!Initialized) { return; }
UpdateMusic(deltaTime);
if (startUpSound != null && !GameMain.SoundManager.IsPlaying(startUpSound))
@@ -629,7 +631,7 @@ namespace Barotrauma
{
if (OverrideMusicType != null) return OverrideMusicType;
if (Screen.Selected != GameMain.GameScreen)
if (Screen.Selected == null || Screen.Selected != GameMain.GameScreen)
{
return "menu";
}
@@ -644,7 +646,7 @@ namespace Barotrauma
Submarine targetSubmarine = Character.Controlled?.Submarine;
if ((targetSubmarine != null && targetSubmarine.AtDamageDepth) ||
(Screen.Selected == GameMain.GameScreen && GameMain.GameScreen.Cam.Position.Y < SubmarineBody.DamageDepth))
(GameMain.GameScreen != null && Screen.Selected == GameMain.GameScreen && GameMain.GameScreen.Cam.Position.Y < SubmarineBody.DamageDepth))
{
return "deep";
}
@@ -54,7 +54,9 @@ namespace Barotrauma
partial void ApplyProjSpecific(float deltaTime, Entity entity, List<ISerializableEntity> targets, Hull hull)
{
if (entity != null && sounds.Count > 0)
if (entity == null) { return; }
if (sounds.Count > 0)
{
if (soundChannel == null || !soundChannel.IsPlaying)
{
@@ -95,22 +97,20 @@ namespace Barotrauma
}
}
if (entity != null)
foreach (ParticleEmitter emitter in particleEmitters)
{
foreach (ParticleEmitter emitter in particleEmitters)
float angle = 0.0f;
if (emitter.Prefab.CopyEntityAngle)
{
float angle = 0.0f;
if (emitter.Prefab.CopyEntityAngle)
if (entity is Item item && item.body != null)
{
if (entity is Item it)
{
angle = it.body == null ? 0.0f : it.body.Rotation;
}
angle = item.body.Rotation + ((item.body.Dir > 0.0f) ? 0.0f : MathHelper.Pi);
}
emitter.Emit(deltaTime, entity.WorldPosition, hull, angle);
}
emitter.Emit(deltaTime, entity.WorldPosition, hull, angle);
}
}
static partial void UpdateAllProjSpecific(float deltaTime)