Resource icon

Ultima Odyssey 2019-03-12

No permission to download

Djeryv

Well-Known Member
Oct 2, 2014
287
34
No worries. Before I added that, there were a few times I shut down my server and forgot to save...losing a bunch of progress. It still isn't fool-proof, as you have to log out in an instant-logout region to kick it off otherwise you have to wait for your character to time out before it kicks off that save function...but I am generally good about logging out in the tavern.
 

Joshua

Well-Known Member
Sep 13, 2014
562
64
34
Bountiful, Utah
Shard Name
My Own Shard
If it was truly a goal to save if the client ever left the server, could just use ' DisconnectedEventHandler ' instead. Regardless of logging out in tavern or in the wild, it would invoke the save request.
 

13440130

Well-Known Member
Jan 25, 2015
123
6
Server Crash Report
===================

RunUO Version 2.1, Build 4272.35047
Operating System: Microsoft Windows NT 5.2.3790 Service Pack 2
.NET Framework: 2.0.50727.3655
Time: 2019-3-17 23:13:54
Mobiles: 47307
Items: 205057
Exception:
System.ArgumentException: 已添加了具有相同键的项。
在 System.ThrowHelper.ThrowArgumentException(ExceptionResource resource)
在 System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add)
在 System.Collections.Generic.Dictionary`2.Add(TKey key, TValue value)
在 Server.Items.SoulOrb.OnSummoned(Mobile from, SoulOrb orb)
在 Server.Spells.Eighth.ResurrectionSpell.Target(Mobile m)
在 Server.Targeting.Target.Invoke(Mobile from, Object targeted)
在 Server.Network.PacketHandlers.TargetResponse(NetState state, PacketReader pvSrc)
在 Server.Network.MessagePump.HandleReceive(NetState ns)
在 Server.Network.MessagePump.Slice()
在 Server.Core.Main(String[] args)
 

Violet Joy

Member
Sep 29, 2018
8
3
Well, we could ensure a save only when there are no aggressors...
in "Broadcast.cs" replace line 81 with...
C#:
if ( Server.Misc.DifficultyLevel.SaveOnCharacterLogout() ){
    if (args.Mobile.Aggressors.Count == 0)
        World.Save( true, false );
}
Post automatically merged:

Server crash report...
"SoulOrb.cs"
C#:
public static void OnSummoned( Mobile from, SoulOrb orb )
{
    if(m_ResList == null)
        m_ResList = new Dictionary<Mobile, SoulOrb>();

    if(!m_ResList.ContainsValue(orb))
    {
        m_ResList.Add(from, orb);
    }
}
Mobile and orb are not checked for null.
The exception is thrown when adding to the dictionary, Dictionary<Mobile, SoulOrb>.
Null keys always throw an exception.
Null values will -not- throw an exception, however, I assume a value, SoulOrb, is eventually needed. Thus I suggest checking for null.

C#:
public static void OnSummoned( Mobile from, SoulOrb orb )
{
    if(m_ResList == null)
        m_ResList = new Dictionary<Mobile, SoulOrb>();
    
    // Added null key and value checks.
    if(from != null && orb != null && !m_ResList.ContainsValue(orb))
    {
        m_ResList.Add(from, orb);
    }
}
 
Last edited:

Djeryv

Well-Known Member
Oct 2, 2014
287
34
I decided to go the "disconnect" route so if I close my client I want the world to save (assuming I set it to "true") no matter what region I am in. If I have to suddenly stop playing, to give my daughter a ride to her friend's house, I want to be able to shut down stuff quickly and get saved.

I also took Violet Joy's fix and applied it to my Soul Orb. Soul Orbs are just an item that allows people to cast resurrect on themselves to resurrect a minute or so after dying to make the spell useful in a single player environment.

Soul Orbs were based on an Auto Res Potion script I found somewhere once upon a time. So I added Violet Joy's tweaks to that script as well because maybe it would also cause the crash shown.

Attached here are my files that were affected with these changes.

I only tested these where I drank the potion, was killed, and I was resurrected as normal. The other I cast the spell, got my soul orb, died, and resurrected shortly after.
 

Attachments

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
Got a weird crash the other day. Happened when a player tried to choose a Heavy Xbow from the Legendary Book.

C#:
RunUO Version 2.1, Build 4272.35047
Operating System: Microsoft Windows NT 6.2.9200.0
.NET Framework: 2.0.50727.8937
Time: 3/20/2019 4:55:55 PM
Mobiles: 44948
Items: 157772
Exception:
System.InvalidCastException: Unable to cast object of type 'Server.Items.GiftHeavyCrossbow' to type 'Server.Items.BaseArmor'.
   at Server.Mobiles.EpicCharacter.GiveGiftBonus(Item item, Int32 val1, Int32 val2, Int32 val3, Int32 val4, Int32 val5, Double sk1, Double sk2, Double sk3, Double sk4, Double sk5, Int32 slay1, Int32 slay2)
   at Server.Mobiles.EpicCharacter.AddToItem(Item item, Mobile from)
   at Server.Mobiles.EpicCharacter.EpicBookGump.OnResponse(NetState state, RelayInfo info)
   at Server.Network.PacketHandlers.DisplayGumpResponse(NetState state, PacketReader pvSrc)
   at Server.Network.MessagePump.HandleReceive(NetState ns)
   at Server.Network.MessagePump.Slice()
   at Server.Core.Main(String[] args)

Clients:
- Count: 1
 

PyrO

Well-Known Member
Jan 27, 2015
1,074
75
Line 1366 in the EpicCharacter class, change
C#:
                else if ( val1 == 100 && item is BaseRanged ){ ((BaseArmor)item).SkillBonuses.SetValues(0, MorphingItem.GetMorphSkill( 5 ), sk1); }
to
C#:
                else if ( val1 == 100 && item is BaseRanged ){ ((BaseWeapon)item).SkillBonuses.SetValues(0, MorphingItem.GetMorphSkill( 5 ), sk1); }
 

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
Line 1366 in the EpicCharacter class, change
C#:
                else if ( val1 == 100 && item is BaseRanged ){ ((BaseArmor)item).SkillBonuses.SetValues(0, MorphingItem.GetMorphSkill( 5 ), sk1); }
to
C#:
                else if ( val1 == 100 && item is BaseRanged ){ ((BaseWeapon)item).SkillBonuses.SetValues(0, MorphingItem.GetMorphSkill( 5 ), sk1); }
Great! I'll edit that in. And it was for the tribute book and not the Legendary Book like I previously stated. (For those who see this later.)

Thanks PyrO!
 

Djeryv

Well-Known Member
Oct 2, 2014
287
34
I am not home right now to look...but wouldnt both share this problem?
 

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
I hadn't checked the LegendBook file vs. the EpicCharacter file to see how they worked. I don't know how similar they are, or if Legendary equipment and the Epic equipment are generated in the same way. I'll look at both.

*Edit* These files work completely different. LegendsBook just gives the reward items, while the EpicCharacter is what's generating the tribute versions. The Heavy Xbow had the wrong base class attached to it, but I'm not sure if the Legendary items are generated the same way. I haven't had to look at that before.

*Edit2* Also, what controls when people go grey/red? I've noticed that some transformations cause characters to go grey, and cannot interact with NPC's for some time until it wears off. Necromancers tend to go in and out of these forms quite a bit, and it's a little thing I'd like to change if I new where to look.
 
Last edited:

Djeryv

Well-Known Member
Oct 2, 2014
287
34
I noticed that since I added the spaceship level, and there are functions to morph the loot to a sci-fi theme, that I think I caused a rare effect of having items like scrolls, potions, and wands "double dip" a bit on the "unidentified" attribute. Meaning I would find an unidentified "item"...I would identify it...then get an unidentified "liquid"...then I could identify that. So I tried to fix it with the changes below and I tested it and it seems to work fine...but more time will tell if it sticks:

LootPack.cs

Around line 159...

replace

cont.DropItem( itemID );

with

if ( cont != null && ( itemID.VendorCanID == "" || itemID.VendorCanID == null ) )
{
cont.DropItem( item );
itemID.Delete();
}
else if ( cont != null )
{
cont.DropItem( itemID );
}


ContainerFunctions.cs

Around line 1807

replace

if ( box != null )
box.DropItem( itemID );


with

if ( box != null && ( itemID.VendorCanID == "" || itemID.VendorCanID == null ) )
{
box.DropItem( item );
itemID.Delete();
}
else if ( box != null )
{
box.DropItem( itemID );
}


Also, for your lich form type issues with vendors, that is probably caused by my changes to remove exploits from disguise kits and incognito spells. I wanted them useful so a murderer can disguise themselves and go into town...but I wanted that to be the really only advantage for a murderer and not something to take advantage of and avoid the whole murder penalty system by just disguising all of the time. So in DifficultyLevel.cs, there is this around line 242:

if ( DisguiseTimers.IsDisguised( m ) && checkDisguise )
enemy = false;


...so this area of code allows for anyone to deal with vendors in public spaces (necro guild, thief guild, etc), but if you are in the regular town region a lich form would be under the IsDisguised category and stop them from dealing with vendors. Now I like that people in lich form can't deal with a human provisioner in Britain. It would be cosmetically weird to me that a provisioner would say "hey mister lich...can I sell you something today". But if you want to change it you would have to start there and add extra checks or simply remove it altogether and let disguised murderers deal with vendors. Also, I don't think it makes you "grey" but your name may appear grey because you are not in human form and RunUO has something in there that changes certain body values to have that color name.
 

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
I agree with you about speaking while transformed. It would be odd. I would think maybe the black magic guild area wouldn't care about it as much, as they have a demon chilling in the back room. Maybe I can add a region check.

The only real area of frustration is the amount of time you are "grey" after a transformation. I'll go into wraith form to recall to a black magic guild, and have to wait 15 minutes to do any business in there. The character isn't a murder, but does have negative karma (don't think a bunch of necromancers who are chopping up golems in the back would care). I'd just like to reduce the time someone goes grey after a necromancer transformation.

I'd think adding a regional check for the black magic guild would be the easiest way to go around all of the other checks before they happen. Is there an example in the code that I can look at that shows how your region checks for those areas work? I know one is happening for magic as it's not allowed in the guild or the bank. I just haven't found where in the code that is happening.
 

Djeryv

Well-Known Member
Oct 2, 2014
287
34
black magic guild is a public region so that shouldn't be an issue...meaning they should be able to interract with vendors. Now I am going to test it to be sure. I'll do lich form. Be right back.

I just turned into a lich and a wraith and could buy stuff in Britain.

Can you explain your issue again?

Also...are you asking about letting people cast spells in public regions?
 
Last edited:

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
No, not casting spells.

Hrm... maybe it's something else that's happening. I noticed the issues shortly after running dungeons. Maybe I'm doing something in dungeons that's making me grey. I just changed forms and stayed blue.

Maybe it's looting? Where do I check for looting and going grey? The only one's on my shard are my friends, and looting anything on the ground shouldn't really matter. Maybe that's what's happening?
 

Djeryv

Well-Known Member
Oct 2, 2014
287
34
Are you playing with friends and not grouped? Maybe looted their kills?

Are you grave digging?
 

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
That's probably what's happening. I'm looting something my friends killed earlier. There are only three of us that play, and I think that sometimes the bodies on the ground aren't the "random" ones, and are actually just the ones that they killed.

Where do I look to disable going grey in looting?
 

Djeryv

Well-Known Member
Oct 2, 2014
287
34
Look at line 847 in Corpse.cs. I think that is what you want. You can probably just set the entire function to FALSE if you don't mind anyone looting whatever they want...even another player's corpse.

I also asked about grave digging because sometimes when you do it you will get a message stating that "someone has saw you and fled" which means you are a criminal for a short time.

Lastly, those corpse containers could cause one to pause about potential criminal actions (thinking it is a real game corpse object) but I wanted to simulate an environment of other adventurers that died and you get to find their stuff so I made these containers to dress up the world a bit.
 
Last edited:

FaceMelter

Well-Known Member
May 31, 2014
79
5
38
Shard Name
Altima
Ah! That's what that means. Makes sense.

Perfect. I changed the lines in Corpse.cs and returned false for the IsCriminalAction function. I'll do some testing. Thank you!

Also, I'm looking at expanding the spells in the rune magic system beyond magery.

I've looked at the system, and so long as I hook a rune combination to an "m_spell_ID" that's registered in the Spell Registry, I can make it cast any spell.

Is there a way to look at the spell registry ID's?