diff --git a/src/ClassicUO.Client/ClassicUO.Client.csproj b/src/ClassicUO.Client/ClassicUO.Client.csproj index 3535ca65e2..ca119cc38d 100644 --- a/src/ClassicUO.Client/ClassicUO.Client.csproj +++ b/src/ClassicUO.Client/ClassicUO.Client.csproj @@ -5,8 +5,8 @@ cuoicon.ico ClassicUO ClassicUO - 3.12.0 - 3.12.0 + 3.13.0 + 3.13.0 diff --git a/src/ClassicUO.Client/Configuration/Profile.cs b/src/ClassicUO.Client/Configuration/Profile.cs index a8c88d92d1..3963b4da82 100644 --- a/src/ClassicUO.Client/Configuration/Profile.cs +++ b/src/ClassicUO.Client/Configuration/Profile.cs @@ -561,7 +561,8 @@ public int CoolDownConditionCount } }; - public bool UseLastMovedCooldownPosition { get; set; } = false; + public bool UseLastMovedCooldownPosition { get; set; } = false; + public bool CloseHealthBarIfAnchored { get; set; } = false; @@ -744,6 +745,11 @@ public List ReadGumps(string path) int y = int.Parse(xml.GetAttribute(nameof(y))); uint serial = uint.Parse(xml.GetAttribute(nameof(serial))); + if(uint.TryParse(xml.GetAttribute("serverSerial"), out uint serverSerial)) + { + UIManager.SavePosition(serverSerial, new Point(x, y)); + } + Gump gump = null; switch (type) diff --git a/src/ClassicUO.Client/Game/Managers/SpellVisualRangeManager.cs b/src/ClassicUO.Client/Game/Managers/SpellVisualRangeManager.cs index b9fcd2871f..d4352c50bf 100644 --- a/src/ClassicUO.Client/Game/Managers/SpellVisualRangeManager.cs +++ b/src/ClassicUO.Client/Game/Managers/SpellVisualRangeManager.cs @@ -83,6 +83,10 @@ private void SetCasting(SpellRangeInfo spell) LastSpellTime = DateTime.Now; currentSpell = spell; isCasting = true; + if(currentSpell != null && currentSpell.FreezeCharacterWhileCasting) + { + World.Player.Flags |= Flags.Frozen; + } } public void ClearCasting() @@ -90,6 +94,7 @@ public void ClearCasting() isCasting = false; currentSpell = null; LastSpellTime = DateTime.MinValue; + World.Player.Flags &= ~Flags.Frozen; } public SpellRangeInfo GetCurrentSpell() @@ -422,6 +427,7 @@ public class SpellRangeInfo public bool IsLinear { get; set; } = false; public double CastTime { get; set; } = 0.0; public bool ShowCastRangeDuringCasting { get; set; } = false; + public bool FreezeCharacterWhileCasting { get; set; } = false; public static SpellRangeInfo FromSpellDef(SpellDefinition spell) { diff --git a/src/ClassicUO.Client/Game/Managers/UIManager.cs b/src/ClassicUO.Client/Game/Managers/UIManager.cs index 8cff3df7da..cb7fe90808 100644 --- a/src/ClassicUO.Client/Game/Managers/UIManager.cs +++ b/src/ClassicUO.Client/Game/Managers/UIManager.cs @@ -127,9 +127,9 @@ public static void ShowGamePopup(PopupMenuGump popup) public static bool IsModalControlOpen() { - foreach (Gump control in Gumps) + for (LinkedListNode last = Gumps.Last; last != null; last = last.Previous) { - if (control.IsModal) + if (last.Value.IsModal) { return true; } diff --git a/src/ClassicUO.Client/Game/UI/Gumps/GridContainer.cs b/src/ClassicUO.Client/Game/UI/Gumps/GridContainer.cs index f1b328d17a..0f2727f0b3 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/GridContainer.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/GridContainer.cs @@ -917,8 +917,9 @@ private void _hit_MouseUp(object sender, MouseEventArgs e) } else { + Rectangle containerBounds = ContainerManager.Get(container.Graphic).Bounds; gridContainer.gridSlotManager.AddLockedItemSlot(Client.Game.GameCursor.ItemHold.Serial, slot); - GameActions.DropItem(Client.Game.GameCursor.ItemHold.Serial, 0xFFFF, 0xFFFF, 0, container.Serial); + GameActions.DropItem(Client.Game.GameCursor.ItemHold.Serial, containerBounds.Width / 2, containerBounds.Height / 2, 0, container.Serial); Mouse.CancelDoubleClick = true; } } diff --git a/src/ClassicUO.Client/Game/UI/Gumps/Gump.cs b/src/ClassicUO.Client/Game/UI/Gumps/Gump.cs index fffc3f0c68..de8b4906b6 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/Gump.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/Gump.cs @@ -55,7 +55,7 @@ public Gump(uint local, uint server) AcceptKeyboardInput = false; } - public bool CanBeSaved => GumpType != Gumps.GumpType.None; + public bool CanBeSaved => GumpType != Gumps.GumpType.None || ServerSerial != 0; public virtual GumpType GumpType { get; } @@ -155,6 +155,7 @@ public virtual void Save(XmlTextWriter writer) writer.WriteAttributeString("x", X.ToString()); writer.WriteAttributeString("y", Y.ToString()); writer.WriteAttributeString("serial", LocalSerial.ToString()); + writer.WriteAttributeString("serverSerial", ServerSerial.ToString()); writer.WriteAttributeString("isLocked", isLocked.ToString()); writer.WriteAttributeString("alphaOffset", AlphaOffset.ToString()); } diff --git a/src/ClassicUO.Client/Game/UI/Gumps/HealthBarGump.cs b/src/ClassicUO.Client/Game/UI/Gumps/HealthBarGump.cs index 7e5c6268ae..f0f05a5c6a 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/HealthBarGump.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/HealthBarGump.cs @@ -407,7 +407,11 @@ public override bool Draw(UltimaBatcher2D batcher, int x, int y) protected bool CheckIfAnchoredElseDispose() { - if (UIManager.AnchorManager[this] == null && LocalSerial != World.Player) + if (IsLocked) + { + return false; + } + if ((UIManager.AnchorManager[this] == null || ProfileManager.CurrentProfile.CloseHealthBarIfAnchored) && LocalSerial != World.Player) { Dispose(); diff --git a/src/ClassicUO.Client/Game/UI/Gumps/OptionsGump.cs b/src/ClassicUO.Client/Game/UI/Gumps/OptionsGump.cs index db5f53b87a..6d38771d57 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/OptionsGump.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/OptionsGump.cs @@ -189,7 +189,7 @@ internal class OptionsGump : Gump private HSliderBar _showSkillsMessageDelta; private Checkbox _leftAlignToolTips, _namePlateHealthOnlyWarmode, _enableHealthIndicator, _spellIconDisplayHotkey, _enableAlphaScrollWheel, _useModernShop, _forceCenterAlignMobileTooltips, _openHealthBarForLastAttack; - private Checkbox _hideJournalBorder, _hideJournalTimestamp, _gridHideBorder, _skillProgressBarOnChange, _displaySpellIndicators, _uselastCooldownPosition; + private Checkbox _hideJournalBorder, _hideJournalTimestamp, _gridHideBorder, _skillProgressBarOnChange, _displaySpellIndicators, _uselastCooldownPosition, _closeHPBarWhenAnchored; private InputField _healthIndicatorPercentage, _healthIndicatorWidth, _tooltipHeaderFormat, _skillProgressBarFormat; private ModernColorPicker.HueDisplay _mainWindowHuePicker, _spellIconHotkeyHue, _tooltipBGHue; private HSliderBar _spellIconScale, _journalFontSize, _tooltipFontSize, _gameWindowSideChatFontSize, _overheadFontSize, _overheadTextWidth, _textStrokeSize, _gridHightlightLineSize, _maxJournalEntries; @@ -4389,6 +4389,10 @@ private void BuildTazUO() }; + section.Add(AddLabel(null, "Close anchored healthbars when automatically closing healthbars", 0, 0)); + section.AddRight(_closeHPBarWhenAnchored = AddCheckBox(null, "", _currentProfile.CloseHealthBarIfAnchored, 0, 0)); + + NiceButton autoLoot; section.Add(autoLoot = new NiceButton(0, 0, 150, TEXTBOX_HEIGHT, ButtonAction.Activate, "Open auto loot options") { IsSelectable = false, DisplayBorder = true }); autoLoot.MouseUp += (s, e) => { @@ -5095,6 +5099,7 @@ private void Apply() UIManager.Add(new ResizableJournal()); } } + _currentProfile.CloseHealthBarIfAnchored = _closeHPBarWhenAnchored.IsChecked; _currentProfile.UseLastMovedCooldownPosition = _uselastCooldownPosition.IsChecked; _currentProfile.InfoBarFont = TrueTypeLoader.Instance.Fonts[_infoBarFont.SelectedIndex]; diff --git a/src/ClassicUO.Client/Game/UI/Gumps/PaperdollGump.cs b/src/ClassicUO.Client/Game/UI/Gumps/PaperdollGump.cs index 0723e742f9..8c98bf8538 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/PaperdollGump.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/PaperdollGump.cs @@ -63,6 +63,7 @@ internal class PaperDollGump : TextContainerGump private GumpPic _picBase; private GumpPic _profilePic; private readonly EquipmentSlot[] _slots = new EquipmentSlot[6]; + private readonly EquipmentSlot[] _slots_right = new EquipmentSlot[6]; private Label _titleLabel; private GumpPic _virtueMenuPic; private Button _warModeBtn; @@ -314,6 +315,19 @@ private void BuildGump() Add(_slots[5] = new EquipmentSlot(0, 2, 75 + 21 * 5, Layer.Tunic, this)); + // Right side equip slots + Add(_slots_right[0] = new EquipmentSlot(0, 166, 75, Layer.Torso, this)); + + Add(_slots_right[1] = new EquipmentSlot(0, 166, 75 + 21, Layer.Arms, this)); + + Add(_slots_right[2] = new EquipmentSlot(0, 166, 75 + 21 * 2, Layer.Shirt, this)); + + Add(_slots_right[3] = new EquipmentSlot(0, 166, 75 + 21 * 3, Layer.Pants, this)); + + Add(_slots_right[4] = new EquipmentSlot(0, 166, 75 + 21 * 4, Layer.Skirt, this)); + + Add(_slots_right[5] = new EquipmentSlot(0, 166, 75 + 21 * 5, Layer.Shoes, this)); + // Paperdoll control! _paperDollInteractable = new PaperDollInteractable(8, 19, LocalSerial, this); Add(_paperDollInteractable); @@ -613,6 +627,13 @@ protected override void UpdateContents() _slots[i].LocalSerial = mobile.FindItemByLayer((Layer)idx)?.Serial ?? 0; } + + for (int i = 0; i < _slots_right.Length; i++) + { + int idx = (int)_slots_right[i].Layer; + + _slots_right[i].LocalSerial = mobile.FindItemByLayer((Layer)idx)?.Serial ?? 0; + } } } @@ -790,7 +811,7 @@ public override void Update() { Item it_at_layer = mobile.FindItemByLayer(Layer); - if (item != it_at_layer || _itemGump == null) + if ((it_at_layer != null && _itemGump != null && _itemGump.Graphic != it_at_layer.DisplayedGraphic) || _itemGump == null) { if (_itemGump != null) { diff --git a/src/ClassicUO.Client/Game/UI/Gumps/VersionHistory.cs b/src/ClassicUO.Client/Game/UI/Gumps/VersionHistory.cs index a00b34217d..e7bd93d590 100644 --- a/src/ClassicUO.Client/Game/UI/Gumps/VersionHistory.cs +++ b/src/ClassicUO.Client/Game/UI/Gumps/VersionHistory.cs @@ -7,6 +7,14 @@ namespace ClassicUO.Game.UI.Gumps internal class VersionHistory : Gump { private static string[] updateTexts = { + "/c[white][3.13.0]/cd\n" + + "- Fix item unintentional stacking\n" + + "- Potential small bug fix\n" + + "- Option to close anchored healthbars automatically\n" + + "- Added optional freeze on cast to spell indicator system\n" + + "- Save server side gump positions\n" + + "- Added addition equipment slots to the original paperdoll gump", + "/c[white][3.12.0]/cd\n" + "- Added Exclude self to advanced nameplate options\n" + "- Bug fix for spell indicator loading\n" + diff --git a/src/ClassicUO.Client/Network/PacketHandlers.cs b/src/ClassicUO.Client/Network/PacketHandlers.cs index 81a79f82a5..f2e8d18838 100644 --- a/src/ClassicUO.Client/Network/PacketHandlers.cs +++ b/src/ClassicUO.Client/Network/PacketHandlers.cs @@ -2145,9 +2145,9 @@ private static void UpdateSkills(ref StackDataReader p) { if (lastBase != skill.BaseFixed) Skill.InvokeSkillBaseChanged(id); - if(lastValue != skill.ValueFixed) + if (lastValue != skill.ValueFixed) Skill.InvokeSkillValueChanged(id); - if(lastCap != skill.CapFixed) + if (lastCap != skill.CapFixed) Skill.InvokeSkillCapChanged(id); } @@ -3732,47 +3732,47 @@ private static void UnicodeTalk(ref StackDataReader p) { Span buffer = stackalloc byte[] { - 0x03, - 0x00, - 0x28, - 0x20, - 0x00, - 0x34, - 0x00, - 0x03, - 0xdb, - 0x13, - 0x14, - 0x3f, - 0x45, - 0x2c, - 0x58, - 0x0f, - 0x5d, - 0x44, - 0x2e, - 0x50, - 0x11, - 0xdf, - 0x75, - 0x5c, - 0xe0, - 0x3e, - 0x71, - 0x4f, - 0x31, - 0x34, - 0x05, - 0x4e, - 0x18, - 0x1e, - 0x72, - 0x0f, - 0x59, - 0xad, - 0xf5, - 0x00 - }; + 0x03, + 0x00, + 0x28, + 0x20, + 0x00, + 0x34, + 0x00, + 0x03, + 0xdb, + 0x13, + 0x14, + 0x3f, + 0x45, + 0x2c, + 0x58, + 0x0f, + 0x5d, + 0x44, + 0x2e, + 0x50, + 0x11, + 0xdf, + 0x75, + 0x5c, + 0xe0, + 0x3e, + 0x71, + 0x4f, + 0x31, + 0x34, + 0x05, + 0x4e, + 0x18, + 0x1e, + 0x72, + 0x0f, + 0x59, + 0xad, + 0xf5, + 0x00 + }; NetClient.Socket.Send(buffer); @@ -7235,7 +7235,8 @@ string[] lines GameActions.Print($"If I am on the correct facet I think these coords should be somewhere near.. {location.X} and {location.Y}.."); MenuButton menu = new MenuButton(25, Color.Black.PackedValue, 0.75f, "Menu") { X = gump.Width - 46, Y = 6 }; - menu.MouseUp += (s, e) => { + menu.MouseUp += (s, e) => + { menu.ContextMenu?.Show(); }; diff --git a/tazuoversioninfo.txt b/tazuoversioninfo.txt index 87dbaa157f..77fdc6bb0a 100644 --- a/tazuoversioninfo.txt +++ b/tazuoversioninfo.txt @@ -1 +1 @@ -3.12.0 \ No newline at end of file +3.13.0 \ No newline at end of file