RunUO Community

This is a sample guest message. Register a free account today to become a member! Once signed in, you'll be able to participate on this site by adding your own topics and posts, as well as connect with other members through your own private inbox!

Addon Container

Erevan

Sorceror
I've been trying to put together the system for Garden Sheds (OSI)..
http://www.uoguide.com/Garden_Shed

I wanted to start simple.. according to UOGuide these sheds have TWO containers, with no weight limit. Doing that part may be a bit more complex, so I figured I'd at least make a basic addon container.

The DefaultGumpID should return a barrel gump.. (one of the actual container gumps on OSI). For whatever reason, it doesn't pop open. The addons places just fine, however.

Code:
using System;
using Server;
using Server.Gumps;
using Server.Network;
 
namespace Server.Items
{
    public class GardenShedAddon : BaseAddonContainer
    {
        public override BaseAddonContainerDeed Deed { get { return new GardenShedDeed(); } }
        public override int LabelNumber { get { return 1153491; } } // garden shed
        public override int DefaultGumpID { get { return 0x3E; } }
        public override int DefaultDropSound { get { return 0x42; } }
 
        [Constructable]
        public GardenShedAddon( bool east ) : base( east ? 0x4BED : 0x4BE9 )
        {
            if ( east ) // East
            {
                AddComponent( new AddonContainerComponent( 0x4BF5 ), -1, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BF4 ), -1, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BF3 ), -1, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BEF ), 0, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BEA ), -1, 2, 0 );
                AddComponent( new AddonContainerComponent( 0x4BEB ), 1, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BEC ), 1, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BED ), 1, -1, 0 ); // Main
                AddComponent( new AddonContainerComponent( 0x4BEE ), 0, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BF0 ), 0, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BF1 ), 0, 2, 0 );
                AddComponent( new AddonContainerComponent( 0x4BEA ), 1, 2, 0 ); // Is this dupe needed?
            }
            else    // South
            {
                AddComponent( new AddonContainerComponent( 0x4BDE ), -1, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE3 ), 1, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BDF ), 0, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE0 ), 1, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE1 ), 2, -1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE4 ), 0, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE2 ), 2, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE5 ), -1, 0, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE6 ), -1, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE7 ), 0, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE8 ), 1, 1, 0 );
                AddComponent( new AddonContainerComponent( 0x4BE9 ), 2, 1, 0 ); // Main
            }
        }
 
        public GardenShedAddon( Serial serial ) : base( serial )
        {
        }
 
        public override void Serialize( GenericWriter writer )
        {
            base.Serialize( writer );
 
            writer.WriteEncodedInt( 0 ); // version
        }
 
        public override void Deserialize( GenericReader reader )
        {
            base.Deserialize( reader );
 
            int version = reader.ReadEncodedInt();
        }
    }
 
    public class GardenShedDeed : BaseAddonContainerDeed
    {
        public override BaseAddonContainer Addon { get { return new GardenShedAddon( m_East ); } }
        public override int LabelNumber { get { return 1153491; } } // garden shed
 
        private bool m_East;
 
        [Constructable]
        public GardenShedDeed() : base()
        {
            LootType = LootType.Blessed;
        }
 
        public GardenShedDeed( Serial serial ) : base( serial )
        {
        }
 
        public override void OnDoubleClick( Mobile from )
        {
            if ( IsChildOf( from.Backpack ) )
            {
                from.CloseGump( typeof( InternalGump ) );
                from.SendGump( new InternalGump( this ) );
            }
            else
                from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used.
        }
       
        public override void GetProperties( ObjectPropertyList list )
        {
            base.GetProperties( list );
           
            list.Add( 1113805 );
        }
 
        private void SendTarget( Mobile m )
        {
            base.OnDoubleClick( m );
        }
 
        public override void Serialize( GenericWriter writer )
        {
            base.Serialize( writer );
 
            writer.WriteEncodedInt( 0 ); // version
        }
 
        public override void Deserialize( GenericReader reader )
        {
            base.Deserialize( reader );
 
            int version = reader.ReadEncodedInt();
        }
 
        private class InternalGump : Gump
        {
            private GardenShedDeed m_Deed;
 
            public InternalGump( GardenShedDeed deed ) : base( 60, 36 )
            {
                m_Deed = deed;
 
                AddPage( 0 );
 
                AddBackground( 0, 0, 273, 324, 0x13BE );
                AddImageTiled( 10, 10, 253, 20, 0xA40 );
                AddImageTiled( 10, 40, 253, 244, 0xA40 );
                AddImageTiled( 10, 294, 253, 20, 0xA40 );
                AddAlphaRegion( 10, 10, 253, 304 );
                AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 );
                AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL
                AddHtmlLocalized( 14, 12, 273, 20, 1071175, 0x7FFF, false, false ); // Please select your vanity position.
 
                AddPage( 1 );
 
                AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 );
                AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South
                AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 );
                AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East
            }
 
            public override void OnResponse( NetState sender, RelayInfo info )
            {
                if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 )
                    return;
 
                m_Deed.m_East = ( info.ButtonID != 1 );
                m_Deed.SendTarget( sender.Mobile );
            }
        }
    }
}


I also updated my data/containers.cfg file.. adjusted the following line to include the base itemIDs for the shed.

Code:
0x3E33 36 109 1120x420xE77,0xE7F,0x4BED,0x4E9,0x44F2

Still no go.. and yes, my BaseAddonContainer is updated correctly. I'm starting to wonder if using more than two components is even possible (for addon containers anyway).
 

Vorspire

Knight
There are client limitations that prevent the shed pieces from acting as containers, I suspect on OSI, they actually have the containers stashed inside the shed and link them to the addon components.
That's how I solved it anyway, but my shed has 8 containers of varying capacity and requires you to upgrade them one by one by completing 'tasks' for each piece.

(8 of 12, because 4 of the pieces can't be seen or targeted very well)



Doing this also involved a lot of re-working of BaseAddon in order to allow components to be 'linked' together.
In the above image, the hover-properties are actually supplied by a hidden Pouch container (1 for each upgradeable section)
 

Erevan

Sorceror
Sounds like a nifty idea.. :) I was going to keep mine much simpler than that. I know it's perfectly possible to have an addon container (i.e. TerMur Dressers), and they work perfectly. It's a little odd that one side of the dresser highlights and the other doesn't, but still. As I said above though, I'm concerned that anything with more than 2 components won't function as a container, unless I do a distro overhaul as you have done.
 

Vorspire

Knight
You're right there, I didn't use the distro AddonContainerComponent for the Shed, I had to write my own special "LinkedContainerComponent" so the container could be hidden and still be linked to a standard component, so basically when the normal component is double-clicked, the double-click is called on the linked container too.

The main issue with the Shed pieces is they aren't flagged as containers in TileData.

There *is* a hack you can do, but it doesn't always work:

When the component is first added, have it's default item ID that of a normal everyday container like a barrel, then use a Timer Delay Call with a zero delay to change the Item ID to that of the Shed part.
The Shed part will now open the barrel container gump as you would expect, the issue is, it doesn't last - you walk off screen and come back, it will not open the container gump any more.
I'm sure there will be a way to fix this by overriding the GetWorldPacketFor method, but I haven't tried it yet.
 
Top