Hello There, Guest! (LoginRegister)

Skinning Tutorials


  Willz Skinning Guide

      Part 1   -   Introduction

      Part 2   -   Your First Plus Skin

      Part 3   -   Dealing with RLE's

      Part 4   -   WLM 8.5 Resource Bible
Warning: may take a while to load

The Essential Skinners Guide – By Willz

Part 3   -   Getting Around MSNRLE

Getting around MSNRLE

The MSNRLE format is something that has caused skinners much grief since it was first introduced in Windows Live Messenger 8.0 beta. Before this format came, MSN Messenger mainly relied on PNG images for its resources which made skinning a breeze. But why was MSNRLE such a pain for skinners?

The main reason is because it is an undocumented format that only Microsoft can reproduce which left skinners in the dark. During the early stages of Windows Live Messenger most energy was spent into finding a way around the MSNRLE problem and to be able to convert it to PNG.

Thankfully workarounds were found, but it proved that these were found out a bit too late as most skinners had already given up. The MSNRLE format is really interesting since it can come in a variety of forms and if skinners could actually reproduce it, well things would be a lot easier.

MSNRLE can come in single layer or multi-layer form (much like a PSD), but what makes the format special is that it also defines if the image is colorized and how it is drawn without the need of 4006 group data.

The single layer MSNRLE images are the easy part, the majority of those can be replaced no problems (except for a couple resources that need some extra attention). The problem comes when you are trying to replace a Multi-layer MSNRLE. Because PNG images do not have layers, the only way to replace a Multi-layer MSNRLE with a PNG is with some custom code. The following is a tutorial that will cover two examples on how to replace Multi-Layer MSNRLE images. These two examples are all you will have to deal with in terms of Multi-layer MSNRLE replacements.

Before we start!

While Messenger Plus! already offers MSNRLE to PNG conversion in the resource extraction process I should point out that this process is still not perfect and there are several images that it can't convert as of yet. For these resources I highly recommend you download a tool known as MSNRLE2PNG.

MSNRLE2PNG is a tool developed by TheSteve and TheBlasphemer and has been around for quite some time now. These guys led the charge into finding ways around the MSNRLE format back in the 8.0 days and without their efforts I too would have just given up skinning altogether.

MSNRLE2PNG is available from http://memskin.fanatic.net.nz/?page_id=6



Initial preparations

Now for these tutorials you will need to prepare a few images.

For the first tutorial we will be replacing the close button with our own custom one. For this tutorial you will need to prepare 4 separate images:

Close Button Normal state

Close Button Mouse Over state

Close Button Pressed state

Close Button disabled state



In the second tutorial we will be replacing the contact list buddy images with our own custom ones. For this tutorial you will need to prepare 8 separate images:

Online Buddy

Busy / Phone Buddy (both use the same image and this can't be changed)

Away / BRB / Out to Lunch / Idle Buddy (all these use the same image and can't be changed)

Offline Buddy

Mobile Contact

Blocked Offline Contact

Blocked Online Contact

Contact Book



For the purpose of these tutorials I will be using simple Hue adjusted images. I should also point out that these tutorials will be done on Windows Live Messenger 8.5. This doesn't stop you from doing it in 9.0 beta, but I do not recommend making a skin in beta software so take this any way you want.



Replacing the Close Button

Now let's dive into the first tutorial. The first thing that we are going to do is start a new SkinInfo.xml file and start by creating all the necessary elements to structure our skin. I won't be covering how to start a SkinInfo.xml file as that was done in the previous part of this guide. If you are unsure of how to lay out a SkinInfo.xml file then I highly recommend you go back and complete the previous tutorial.

Your SkinInfo.xml should look something along these lines:

<SkinInfo>


<Information>

<Name>Close and Buddy</Name>

<Description>Fear My Uber Awesome Skills</Description>

<Version>1.0</Version>

<Compatibility>

<MsgVersion Major="8" Minor="5"/>

</Compatibility>

</Information>

<MessengerSkin>


<ResGroup>


<Restrictions>

<MsgVersions>

<Version Major="8" Minor="5"/>

</MsgVersions>

</Restrictions>


<Resources>

</Resources>

</ResGroup>


</MessengerSkin>


</SkinInfo>



The region we will be working in will be the <Resources> section, so from this point forward I will be only showing code from this area since the rest will no longer touched. In the previous part of this guide the <Replace> method was covered, however because we are dealing with Multi-Layer MSNRLE we will have to use the <New> method to add our images.





<New> is the element that contains all the instructions that adds new custom images that you can call upon in UIFile code. In order to avoid confusion and have a clear separation between replaced and new resources, Messenger Plus! only allows resources in the <New> section to have Id's between 59000 and 59999.

So now onto the code:

<Resources>

<New>

<Pictures>

<Picture Id="59000">

<File>Images/59000.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

</Pictures>

</New>

</Resources>

As mentioned before, the <New> element contains the instructions to add new resources that can be called upon in UIFile code. Within this element you can either declare new <Pictures> (image resources) or <Colors> (rgb color values for foreground and background properties). Because we are only interested in adding new images we will be using the <Pictures> element.

Within the <Pictures> element we can create a series of <Picture> elements which define a new image resource. Within each <Picture> element, there are instructions on how to treat the file. The <File> element points to where the image resource is and the <Metadata> element contains a list of drawing properties that are applied to the image.

In this case I have applied the <Colorize> element which simply tells Messenger whether or not the image should be colorized. Another important part of the <Metadata> section is the one that defines UMMargins, these tell Messenger how to stretch an image if it is a background. UMMargins will be covered in a tutorial further on so do not worry about them just yet.

Now that we have that covered we can now declare the other 3 images. Your code should look something along the lines of this:

<Resources>

<New>

<Pictures>

<Picture Id="59000">

<File>Images/59000.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59001">

<File>Images/59001.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59002">

<File>Images/59002.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59003">

<File>Images/59003.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

</Pictures>

</New>

</Resources>



All that is left to do in terms of SkinInfo.xml editing is to declare the replacement of the UIFile we will be working with. For the purpose of this tutorial we will be working in the 947 (Sign In Window) UIFile as we can see that changes we make immediately. Replacing a UIFile really easy and is quite similar to replacing an image. Copy over the 947 style and we will cover how to replace it.



IMPORTANT NOTE

Do NOT use the style files from the consolidated windows resource section. These UIFiles have been edited so that you can read them easier. Using these files will your skin will replace the default language in a users messenger and it will frustrate your users.

<Resources>

<Replace>

<Windows>

<Styles>

<Style Id="947">

<File>UIFiles/Styles/947.txt</File>

</Style>

</Styles>

</Windows>

</Replace>

<New>

<Pictures>

<Picture Id="59000">

<File>Images/59000.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59001">

<File>Images/59001.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59002">

<File>Images/59002.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59003">

<File>Images/59003.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

</Pictures>

</New>

</Resources>





Now to break up what we just added:

<Replace>

<Windows>

<Styles>

<Style Id="947">

<File>UIFiles/Styles/947.txt</File>

</Style>

</Styles>

</Windows>

</Replace>

Like in the previous part of this skinning guide, a <Replace> element has been added to declare the resources that we want replace in Windows Live Messenger. Since this time around we are editing the source images of buttons all we need to replace is the Style information. Styles and Definitions fall under the <Windows> element so we create that element to declare that we want to edit the window structure.

Then we open up a <Styles> element to declare the list of styles we wanted to replace. Since we are only interested in the 947 style this is the only one we are going to replace. So much like replacing a picture we simply just declare the style and its Id and the point it to the file we want to replace it with.

By now you should be used to replacing resources so in future we will not break down replacements. We now have done all the editing we need to do in SkinInfo.xml so we can leave it for now. It is now time to take a look at the 947 style.

Styles are fairly easy to read as most of the major elements use naming conventions that make it easy to know what each style declaration does. We are looking for the close button so if you look for the word "close" in the style file you will find the following:

button[id=Atom(FLWCloseBtn)]

{

AccName:rcstr(20069);

AccDesc:rcstr(20069);

Content:rcimg(20070);

padding:rcrect(20084);

}

See what I mean by easy to read? As you can see the class is pretty self explanatory with the words FLWCloseBtn. You can probably easily guess what the minimize and maximize buttons use so after you finish this part of the tutorial replacing the other two buttons should be a breeze.

Now to break up the properties used:

AccName – The name of the button, can refer to a string in mslang.dll using rcstr(#####); where ##### is the string number is mslang.dll, or normal text using quotation marks.

AccDesc – The tooltip that appears on mouse over, can refer to a string in mslang.dll using rcstr(#####); where ##### is the string number is mslang.dll, or normal text using quotation marks.

Content – This property defines what the element/button contains within it. This property can set images or text.

Padding – Like the CSS property, this defines spacing around an element / button. Padding can be defined by using rcrect(#####); where ##### is the rectangle resource number in msgsres.dll or by using rect(A,B,C,D); where A=left padding, B=top padding, C=right padding and D=bottom padding.



IMPORTANT NOTE

You will notice when you begin to replace other buttons that not all of them rely on the content property to define the button image. Some use the background property instead of the content property.

Is there a difference?

Yes, the background property fills in the entire space of the element with the image you define while the content property maintains the images original size. You must make a choice of when it is appropriate to use one or the other. As a general rule, just follow the way it is done in the style files and all should be well.

The way the button is currently structured is that it relies on single resource for all 4 button states. What we are going to do now is break this dependency and manually define each state using the [ContentIndex] condition on the button class.

What exactly does [contentindex] do? ContentIndex was put there so that you could call on a layer in a Multi-Layer MSNRLE. It was then discovered that you could set different source images for each instance of ContentIndex.

So how does this all come together?



button[id=Atom(FLWCloseBtn)][ContentIndex=0]

{

AccName:rcstr(20069);

AccDesc:rcstr(20069);

Content:rcimg(59000);

padding:rcrect(20084);

}

button[id=Atom(FLWCloseBtn)][ContentIndex=1]

{

AccName:rcstr(20069);

AccDesc:rcstr(20069);

Content:rcimg(59001);

padding:rcrect(20084);

}

button[id=Atom(FLWCloseBtn)][ContentIndex=2]

{

AccName:rcstr(20069);

AccDesc:rcstr(20069);

Content:rcimg(59002);

padding:rcrect(20084);

}

button[id=Atom(FLWCloseBtn)][ContentIndex=3]

{

AccName:rcstr(20069);

AccDesc:rcstr(20069);

Content:rcimg(59003);

padding:rcrect(20084);

}

All that was done to make this work was to duplicate the class 3 times and then add the [ContentIndex] condition to all four copies and then specify the MSNRLE layer. So how did I know what numbers to use? If you take a look at the image that Plus! converts to PNG you will see that there are 4 images. ContentIndexes start at 0 so using this information we can come to the following conclusion:

[ContentIndex=0] – Close button normal state

[ContentIndex=1] – Close button mouse over state

[ContentIndex=2] – Close button pressed state

[ContentIndex=3] – Close button disabled/inactive state



With that information we can then change the content property of each of these to point to the images we declared in SkinInfo.xml (59000, 59001, 59002 and 59003) using content:rcimg(#####); where ##### is the resource number.

If you save your files and then load up your skin you should now see your new close button in place and in effect:

You can use the same technique to replace other Mult-Layer MSNRLE images so you aren't just restricted to buttons. Try changing the minimize and maximize buttons as well to see if what you have just learn has stuck. Another thing I should mention is that code we changed here only affects the sign in window and that all the other windows will still have the original close button. In order to edit every single button you must make the same changes we did to the 947 style to the following styles:

919, 920, 921, 923, 927, 931, 949, 950, 953, 44101, 45701 and 45710.

Replacing the Contact List Buddy Images

Nearly every single Multi-Layer MSNRLE you come across can be replaced using the method we used in replacing the close button. There are only a few instances where you have to use a slightly different technique to get the job done. One of these instances is the buddy image.

Now while the buddy image appears to be a normal Multi-Layer MSNRLE there is something that sets it apart from the others. The buddy image (for reasons still unknown) has blank layer states in its MSNRLE. Now this doesn't sound bad, but in reality it is since it makes it hard to know what contentindexes to use. What makes things worse is that if you try to replace one of these Blank states (even with blank image) it will cause Messenger to crash.

So in order to save you guys some trouble I have decided to show you how to successfully replace the buddy image in the contact list so that you know what needs to be done. Rather than start a new skin, we will continue on with the current skin we have made.

This tutorial will be a lot shorter than the last one since I will not be bothering to break up code and explain steps much as the first part of it will be repeats of what was done in the Close button replacement part.

The first thing that needs to be done is to declare some new images in SkinInfo.xml. So like the last part of this tutorial we will declare 8 new images under the <Pictures> section of SkinInfo.xml After this you will need to then add in replace statements for styles 1004 and 1009 (detailed and normal contact list).

Your code should look something like this:

<Resources>

<Replace>

<Windows>

<Styles>

<Style Id="947">

<File>UIFiles/Styles/947.txt</File>

</Style>

<Style Id="1004">

<File>UIFiles/Styles/1004.txt</File>

</Style>

<Style Id="1009">

<File>UIFiles/Styles/1009.txt</File>

</Style>

</Styles>

</Windows>

</Replace>

<New>

<Pictures>

<!-- Close Button Images -->

<Picture Id="59000">

<File>images/59000.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59001">

<File>images/59001.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59002">

<File>images/59002.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59003">

<File>images/59003.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<!-- Buddy Replacement Images -->

<Picture Id="59004">

<File>images/59004.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59005">

<File>images/59005.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59006">

<File>images/59006.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59007">

<File>images/59007.png</File>

<Metadata>

<Colorize>false</Colorize>

</Metadata>

</Picture>

<Picture Id="59008">