Thread: Adding new slots to the equipment tab

Results 1 to 10 of 10
  1. #1 Adding new slots to the equipment tab 
    Mikan Fanboy



    Omar's Avatar
    Join Date
    Dec 2007
    Posts
    222
    Thanks given
    434
    Thanks received
    608
    Discord
    View profile
    Rep Power
    4799
    This tutorial is part of a series on 317 interfaces. For some of the other entries, see the list below:

    • [Only registered and activated users can see links. ]
    • [Only registered and activated users can see links. ]
    • [Only registered and activated users can see links. ]


    We'll be covering the creation of new equipment slots as well as a rudimentary understanding of inventory sprites, spacing, etc.

    Let's take a look at [Only registered and activated users can see links. ], the inventory type. The things of note for us are the following lines:

    Code:
        w.inventoryMarginX = b.getUByte();
        w.inventoryMarginY = b.getUByte();
        w.inventoryOffsetX = new int[20];
        w.inventoryOffsetY = new int[20];
    The "marginX" and "marginY" properties determine how many pixels of space should exist between inventory items. The "OffsetX" and "OffsetY" arrays allow you to offset a specific inventory slot by a given number of pixels.

    In addition to the inventory specific properties, "height" and "width", found at the top of the decoder, are also very important to us as they behave a little bit differently for inventories.

    Code:
        w.width = b.getUShort();
        w.height = b.getUShort();
    For inventory interfaces, rather than determining the size of the interface in pixels, as would the fields would normally do, these actually determine the number of inventory rows and columns (height and width, respectively).

    So, given an inventory with a width of 3, height of 3, offsets and margins of 0, our inventory would look a little something like this when full (X, Y), with the total size being 96x96 (64 being the end position [Only registered and activated users can see links. ]).

    0, 0 32, 0 64, 0
    0, 32 32, 32 64, 32
    0, 64 32, 64 64, 64

    Spoiler for Code:

    Code:
        override fun buildView() {
            val container = interfaceBuilder().id(parentId).asTabInterface()
            val rect = interfaceBuilder(container).color(GREY).size(96, 96).position(200, 125).filled().asRectangle()
            interfaceBuilder(rect).size(3, 3).items(Array(9) {
                Item(CHAOS_RUNE, 1)
            }).asInventory()
        }


    Spoiler for Image example:




    Should we add a marginX of 8, we'd end up with the following, with a total size of 112x96 (96 + 16 from the two items with a margin of 8).

    0, 0 40, 0 80, 0
    0, 32 40, 32 80, 32
    0, 64 40, 64 80, 64

    Spoiler for Code:

    Code:
        override fun buildView() {
            val container = interfaceBuilder().id(parentId).asTabInterface()
            val rect = interfaceBuilder(container).color(GREY).size(112, 96).position(200, 125).filled().asRectangle()
            interfaceBuilder(rect).size(3, 3).items(Array(9) {
                Item(CHAOS_RUNE, 1)
            }).inventorySpritePadding(8, 0).asInventory()
        }


    Spoiler for Image example:




    Similarly, modifying the marginY to be 8 produces the following, with a total size of 112x112.

    0, 0 40, 0 80, 0
    0, 40 40, 40 80, 40
    0, 80 40, 80 80, 80

    Spoiler for Code:

    Code:
        override fun buildView() {
            val container = interfaceBuilder().id(parentId).asTabInterface()
            val rect = interfaceBuilder(container).color(GREY).size(112, 112).position(200, 125).filled().asRectangle()
            interfaceBuilder(rect).size(3, 3).items(Array(9) {
                Item(CHAOS_RUNE, 1)
            }).inventorySpritePadding(8, 8).asInventory()
        }


    Spoiler for Image example:




    Next, the last bit we need to know how to play around with in order to add new slots is the offsets since these allow you to more precisely position things in the equipment tab. Let's demonstrate by moving the 8th Chaos rune a little bit. We'll give it an offset of 16 on the X and -16 on the Y. This'll push it over to the right and pull it upwards.

    0, 0 40, 0 80, 0
    0, 40 40, 40 80, 40
    0, 80 56, 64 80, 80

    Spoiler for Code:

    Code:
        override fun buildView() {
            val container = interfaceBuilder().id(parentId).asTabInterface()
            val rect = interfaceBuilder(container).color(GREY).size(112, 112).position(200, 125).filled().asRectangle()
            val inventory = interfaceBuilder(rect).size(3, 3).items(Array(9) {
                Item(CHAOS_RUNE, 1)
            }).inventorySpritePadding(8, 8).asInventory()
            inventory.inventoryOffsetX[7] = 8
            inventory.inventoryOffsetY[7] = -16
        }


    Spoiler for Image example:




    Using the information we've learned, we can go ahead and start repositioning the slots for new items. Let's go ahead and change slot 14. The equipment inventory has a size of 3x5, so we'll need to take the row and column into account when doing the offsets.

    Code:
        public static void buildEquipmentTab() {
            final RSInterface inventory = instances[1688];
            inventory.inventoryOffsetX[14] = -97;
            inventory.inventoryOffsetY[14] = -198;
        }


    Next, let's go ahead and add a tab sprite behind it. However, we need to be careful doing this as we can't simply add a new child to the equipment tab (1644) as that'll cause the sprite to draw above the item due to the fact that the inventory (1688) will no longer be the final child interface in the array.

    Let's start by adding a method to determine the next free ID in the interface array:

    Code:
        private static int getFreeIndex() {
            for (int i = 0; i < instances.length; i++) {
                if (instances[i] == null) {
                    return i;
                }
            }
            return -1;
        }
    Let's add a couple of methods to create a new sprite interface:

    Code:
        // Add these to your sprite class or replace their usages in the createSprite code
        public static Sprite fetchSprite(final String name, final FileArchive graphics) {
            final int index = name.lastIndexOf(",");
            return RSInterface.getSprite(Integer.parseInt(name.substring(index + 1)), graphics, name.substring(0, index));
        }
    
        public static Sprite fetchSprite(final String name) {
            return fetchSprite(name, RSInterface.graphics);
        }
    
        // Add these to your interface class
        public static RSInterface createSprite(final int parentIndex, final int index, final String disabled, final String enabled) {
            final Sprite disabledSprite = Sprite.fetchSprite(disabled);
            final Sprite enabledSprite = Sprite.fetchSprite(enabled);
            final RSInterface sprite = instances[index] = new RSInterface();
            sprite.id = index;
            sprite.parent = parentIndex;
            sprite.type = 5;
            sprite.width = disabledSprite.width;
            sprite.height = disabledSprite.height;
            sprite.disabledSprite = disabledSprite;
            sprite.enabledSprite = enabledSprite;
            return sprite;
        }
    
        public static RSInterface createSprite(final int parentIndex, final String disabled, final String enabled) {
            final int index = getFreeIndex();
            if (index < 0) {
                throw new IllegalStateException("Interface cache full; expand the size of the array before attempting to create a component!");
            }
            return createSprite(parentIndex, index, disabled, enabled);
        }
    Next, we need a method to fetch the index of an interface in the child array:

    Code:
        public static int getIndexOfChild(final int parent, final int child) {
            final RSInterface rsi = instances[parent];
            for (int i = 0; i < rsi.children.length; i++) {
                if (rsi.children[i] == child) {
                    return i;
                }
            }
            return -1;
        }
    Finally, we need a method to parent an interface to a given parent interface:

    Code:
        public static void addChild(final int parentIndex, final int childIndex, final int x, final int y, final int index) {
            final RSInterface parent = instances[parentIndex];
            final int[] childX = new int[parent.childX.length + 1];
            final int[] childY = new int[parent.childY.length + 1];
            final int[] children = new int[parent.children.length + 1];
            System.arraycopy(parent.childX, 0, childX, 0, index);
            System.arraycopy(parent.childX, index, childX, index + 1, parent.childX.length - index);
            System.arraycopy(parent.childY, 0, childY, 0, parent.childY.length);
            System.arraycopy(parent.childY, index, childY, index + 1, parent.childY.length - index);
            System.arraycopy(parent.children, 0, children, 0, index);
            System.arraycopy(parent.children, index, children, index + 1, parent.children.length - index);
            childX[index] = x;
            childY[index] = y;
            children[index] = childIndex;
            parent.childX = childX;
            parent.childY = childY;
            parent.children = children;
        }
    Now, we can use the methods we created earlier to add the tab sprite and splice it into the array above where the inventory sits:

    Code:
        public static void buildEquipmentTab() {
            final RSInterface parent = instances[1644];
            final RSInterface newTab = createSprite(parent.id, "miscgraphics,0", "miscgraphics,0");
            final RSInterface inventory = instances[1688];
            inventory.inventoryOffsetX[14] = -97;
            inventory.inventoryOffsetY[14] = -198;
            addChild(parent.id, newTab.id, 37, 4, getIndexOfChild(parent.id, inventory.id));
        }


    Finally, the last thing we need to do is add a placeholder sprite for when the slot is empty so that it isn't just blank. Let's quickly look at [Only registered and activated users can see links. ] again:

    Code:
        String s = b.getString();
        if (media != null && s.length() > 0) {
            int j = s.lastIndexOf(",");
            w.inventorySprite[n] = getSprite(s.substring(0, j), media, (Integer.parseInt(s.substring(j + 1))));
        }
    When iterating over the slots in an inventory, in addition to decoding the offsets, it also decodes and sets sprites, if available, to those slots. These inventory sprites only show if the slot is empty. Otherwise, they are disabled. We can go ahead and hardcode these, like so:

    Code:
        public static void buildEquipmentTab() {
            final RSInterface parent = instances[1644];
            final RSInterface newTab = createSprite(parent.id, "miscgraphics,0", "miscgraphics,0");
            final RSInterface inventory = instances[1688];
            inventory.inventoryOffsetX[14] = -97;
            inventory.inventoryOffsetY[14] = -198;
            inventory.inventorySprite[14] = fetchSprite("wornicons,12");
            addChild(parent.id, newTab.id, 37, 4, getIndexOfChild(parent.id, inventory.id));
        }


    That's it. You're done!

    Special thanks:

    • @[Only registered and activated users can see links. ] - refactoring
    • @[Only registered and activated users can see links. ] - moral
    Last edited by Omar; 04-21-2021 at 11:19 AM.
    [Only registered and activated users can see links. ]

    Spoiler for aaaa:




    [Only registered and activated users can see links. ]
    Reply With Quote  
     


  2. #2  
    SEXY LYNCH

    Lynch's Avatar
    Join Date
    Feb 2016
    Age
    22
    Posts
    130
    Thanks given
    15
    Thanks received
    90
    Discord
    View profile
    Rep Power
    403
    thanks yet again for a great tutorial. Keep them coming OMAAAR
    Reply With Quote  
     

  3. Thankful users:


  4. #3  
    OS-Scape - coming soon...
    Raw Envy's Avatar
    Join Date
    Dec 2010
    Posts
    2,986
    Thanks given
    829
    Thanks received
    1,138
    Rep Power
    2891
    Nice work, I'm sure some people will appreciate this being shared.
    [Only registered and activated users can see links. ]

    [Only registered and activated users can see links. ]

    Join OSS Discord for weekly 100m OSRS GP giveaways until release.
    Reply With Quote  
     

  5. Thankful user:


  6. #4  
    Royal-PS Management


    Join Date
    Nov 2015
    Posts
    174
    Thanks given
    111
    Thanks received
    80
    Discord
    View profile
    Rep Power
    431
    Love it Omar
    Quote Originally Posted by Corey View Post
    Vouch for Benneh

    Worked with him for a month. He's professional and always on time with posts, always interested in how the server is doing and how he can can improve and help in any way.
    Reply With Quote  
     

  7. Thankful user:


  8. #5  
    ✥Augury RSPS - Soon✥

    TeJay's Avatar
    Join Date
    Jul 2017
    Posts
    613
    Thanks given
    199
    Thanks received
    263
    Discord
    View profile
    Rep Power
    1450
    Good job mate
    [Only registered and activated users can see links. ]
    Spoiler for Services:
    [Only registered and activated users can see links. ]

    [Only registered and activated users can see links. ]
    Reply With Quote  
     

  9. Thankful user:


  10. #6  
    Registered Member

    Join Date
    Feb 2010
    Posts
    3,192
    Thanks given
    1,125
    Thanks received
    840
    Discord
    View profile
    Rep Power
    1525
    nice tutorial really detailed
    Reply With Quote  
     

  11. Thankful user:


  12. #7  
    nice


    Join Date
    Jul 2014
    Posts
    667
    Thanks given
    293
    Thanks received
    344
    Discord
    View profile
    Rep Power
    2952
    good tutorial
    Reply With Quote  
     

  13. Thankful user:


  14. #8  
    08-13, SpawnScape Owner

    jet kai's Avatar
    Join Date
    Dec 2009
    Age
    25
    Posts
    757
    Thanks given
    405
    Thanks received
    403
    Discord
    View profile
    Rep Power
    2160
    Appreciate the detailed and free content coming from this one.
    [Only registered and activated users can see links. ]

    [Only registered and activated users can see links. ]

    [Only registered and activated users can see links. ]

    [Only registered and activated users can see links. ]
    Reply With Quote  
     

  15. Thankful user:


  16. #9  
    WVWVWVWVWVWVWVW

    _jordan's Avatar
    Join Date
    Nov 2012
    Age
    23
    Posts
    2,869
    Thanks given
    63
    Thanks received
    1,531
    Discord
    View profile
    Rep Power
    5000
    very nice

    Spoiler for signature:
    When your vision is crystal clear, they say it's razor-sharp
    A focused mind is said to be like a knife, but the scalpel is wisdom
    All one can do is accept that life is a double-edged sword
    Stay on the edge

    -



    Reply With Quote  
     

  17. Thankful user:


  18. #10  
    Extreme Donator


    Rythe's Avatar
    Join Date
    Dec 2019
    Age
    28
    Posts
    361
    Thanks given
    303
    Thanks received
    172
    Discord
    View profile
    Rep Power
    590
    Awesome omar, good job! keep it up.

    good tut.
    Reply With Quote  
     

  19. Thankful user:



Thread Information
Users Browsing this Thread

There are currently 1 users browsing this thread. (0 members and 1 guests)


User Tag List

Similar Threads

  1. IPB Adding new groups to the online list
    By Grey59 in forum Application Development
    Replies: 13
    Last Post: 07-20-2016, 09:29 AM
  2. Adding teleports on to the quest tab?
    By Haashim in forum Help
    Replies: 1
    Last Post: 05-04-2013, 11:48 AM
  3. Adding new maps to the clipping system?
    By RebornHonor in forum Help
    Replies: 3
    Last Post: 08-20-2012, 07:24 PM
  4. Adding new chars to the server (hard)
    By Shoes in forum Help
    Replies: 6
    Last Post: 05-30-2010, 09:00 PM
  5. Adding new maps to the Worldmap!
    By SWAT in forum Tutorials
    Replies: 27
    Last Post: 02-03-2010, 07:46 PM
Tags for this Thread

View Tag Cloud

Posting Permissions
  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •