Publishing System Settings Logout Login Register
The Ultimate Windows Media Player Skinning Guide
TutorialCommentsThe AuthorReport Tutorial
Tutorial Avatar
Rating
Add to Favorites
Posted on October 7th, 2006
24610 views
Application Skinning
Hi,

After the Ultimate Slicing Guide by Faken, here's the Windows Media Player Skinning one by NGPixel. This tutorial is a complete guide to make your own Windows Media Player skin with advanced features. Since this tutorial is huge, I've splitted it in different chapters and pages, each on a specific feature. This guide can be used as a walkthrough from start to finish or as a reference for a specific feature.

All over the tutorial, I use a skin example that you can download (with all the files that you need) here:

(.zip)



Chapters

- 1 - Introduction to WMP Skinning
- 2 - Before Making the Design
- 3 - Making the Design
- 4 - Making the Buttons Mask
- 5 - Introduction to the WMP XML
- 6 - Writing the XML - Skin Informations
- 7 - Writing the XML - Basic Elements
- 8 - Writing the XML - Buttons
- 9 - Moving Panels
- 10 - Moving Elements
- 11 - Building an Equalizer
- 12 - Even more Stuff!
- 13 - Making the Final Package
- 14 - Distribution
- 15 - Using Round Skins
- 16 - Notes & Legal Stuff




Let's start!

Chapter 1 - Introduction to WMP Skinning

Windows Media Player lets the user choose from a variety of standard skins, each one providing an additional visual experience that enhances listening and viewing pleasure. Windows Media Player comes with several skins to choose from, but it is relatively easy to create and distribute custom skins.

When you first a download a skin, you download one main file that contains all the informations (scripts, codes, graphics, actions, etc.) that are used to display the complete skin. Maybe you ever tried to open one of these files with notepad, not much success you might had. WMP Skin files (.wmz) are actually zipped files.

You can try to open one with WinZip (change the extension to .zip and extract the contents). You will then find all the components of the skin such as images, scripts, JS files, etc.

Skins are made of 3 main parts (one is optional). Images files, XML file and JS file (javascript). The images files are what you see: the background, the buttons, the EQ panels, etc. The XML file contains all the properties of each object in the skin. All the sizes, positions, actions, properties of each object including the panels and visualizations window are listed in that XML file. Finally, there's the optional JS file which contains all the javascripts you need in your skin. For exemple, to animate a panel that slide to the right, you need to insert some codes in your JS file just like you would do for an HTML page.

The XML file and the JS file can be opened with any text editor. For faster and easier looking, use Macromedia Dreamweaver. You will get highlighted code and colored tags.



Chapter 2 - Before Making the Design

Before starting with the main background design of your skin, you need to know some limitations/notes that you have to keep in mind. First, making a round skin is much harder than making a rectangle skin. WMP is not supporting transparency by default. You will need a mask to tell the player which part of the background the hide (make transparent). This mean you will need to specify a color that is going to be removed from the entire background. The problem with this method is that if you set a color that is totally different than the colors you used in your skin, you will see a 1 px border of that color. For exemple, if your skin is blue and you set the masking color as red, you might see a beautiful red border which looks ugly (unless that's what you want it to look like :-/ ).

See Chapter 15 for more details about round skins.

On the other side, if you use sharp edges with only line style borders (rectangle), you won't have any problems and in most case, you won't even need a mask. If it's your first skin, i recommend using a rectangle skin background.

Another tip: It's always useful to put example texts and visualizations/videos windows on your skin so you know how it looks. But don't forget to remove them before exporting!

On the next page, we'll start with the design...



Chapter 3 - Making the Design

You can make a background design with any design software such as Fireworks, Photoshop, GIMP and even MS Paint if you have awesome design skills :).

In this guide, i will use Macromedia Fireworks MX 2004 but most of the steps can easily be followed in any other design software. I'm not explaining how to make a shape since this guide is to make a WMP skin, not to learn how to use Fireworks. If you have know idea how to use these softwares, then look in tutorials list, there're plently of them.

1) Open your design software.

2) Make a new document with a reasonable size. A skin is not a full screen mode, this is not why we call them "skins", skins are small and must stay small. 400px by 300px is good size. Note that you can always make panels than can be hidden below the current skin and only open them when needed. It's especially the case with Equalizers and Playlists.

3)Now, make the design of your skin. Here's one i made mostly only with rectangles and some circles. I then added some buttons. If you are too lazy to make your own, right-click the image and save it (use the BMP file in the package, recommended). That's the skin background i'll use for this example.

Skin 1 - Background Image

Include all the objects that are not dynamic (dynamic means objects that will change when the player is on, for exemple, the seek & volume bar, file title text, time, etc.). Buttons must be included in the background. But you can also slice them seperatly since you can place them as seperate objects in the XML.

In this exemple, i've set the background color as pink (#FF15E8) which is a color that is not used in the current project. This color will be transparent in the final version.

On the next page, we'll start with the buttons mask...



Chapter 4 - Making the Buttons Mask

In addition to the background itself, there's also a mask needed to display the buttons and to make them clickable. A mask has no design. It's only made of different colors where each color match a button. An example is always useful to understand this:

T_2 Example

As you you can see everything is gone except the buttons that are colored in different colors. This is how the player knows where are located the buttons on the skin. In the xml file, a specified color will be attributed to each button object.

Place a shape of the color of your choice on every buttons in your skin. This is the final version of my mask:

Final Mask Version

Export your mask in the same folder as your background.

Note that Windows Media Player is only supporting BMP, JPG, GIF, (PNG is not always supported). BMP is the best format for the quality, so I recommend this format. Don't worry about the size since a skin is only downloaded once and no need to load it again once it's on your computer so it's not a problem. For this guide, i've set all my example as JPG since BMP would take too much time to load in this guide.

In addition, JPG and GIF formats can leave some mask colored points on the skin as well as making the buttons hard to click on some locations, BMP is REALLY recommended.



Chapter 5 - Introduction to the WMP XML

An XML looks like a CSS file. You will find the same structure for the objects properties as CSS does for a tag. But an XML file does much more than that. You can set the skin information, multiple layers, set actions for each objects and even include some Javascript.

If you opened a prebuilt skin, you might have seen no .xml file but a .wms. The .wms is actually the XML file, try to open that file in your favorite code editor (notepad, dreamweaver). You can see that all the codes are there.

So let's start by making a new one. I really recommend using Dreamweaver or a similar software since its easier to find yourself when you have many objects in your skin.



Chapter 6 - Writing the XML - Skin Informations

Create a new XML file or just start a blank document and remove anything code that is already there if there's any. Any skin start by the Skin Information part. Copy-paste this code in your file and change the infos to your own infos:


<THEME id=\"Example_skin_1\"
title=\"Example Skin 1\"
author=\"NGPixel | www.ngpixel.com\"
copyright=\"&copy; NGPixel.com. All rights reserved.\">


You can also put the end tag right now if you want (don't forget it at the end or it won't works).


</THEME>


Everything else that is in your code will be between the "> and the tags.

Now that we have the informations of the skin, we can start with all the visual aspect of the skin. Copy-Paste this code between the 2 tags I explained about before.


<VIEW
backgroundColor=\"none\"
clippingColor = \"#FF15E8\"
transparencyColor=\"#FF15E8\"
backgroundImage = \"backgd.bmp\"
titleBar = \"false\"
scriptFile = \"scriptfile.js\"
onLoad=\"OnLoad();\">


Once again you can close the tag with a tag.

Explanation of this code:

- backgroundColor: This is the background color of the skin (self-explain). Because we want the background to be transparent, we set "none" but you can put your own HEX color code if you want to put one. (HEX code is a code of 6 characters used in HTML to specify colors)

- clippingColor AND transparencyColor: They are usually the same, the transparencyColor tells which color in the background image file will be transparent. In this code, the color is pink (you can't write "pink", you need once again to specify the HEX color code. You can use a ColorPicker software to find the right code.) The clipping color is also used to set the transparent color if a ClippingImage is used in your skin. This is used to hide any part of an object (even a video window if set to windowless).

- backgroundImage: The background image file name. Note that you must put ALL the files in the same folder. Just type the filename of your background image that you made before. This is not the mask but the complete background with all the design.

- titleBar: If the player shows a titlebar or hide it. In most case, a skin is without titlebar but it's your choice :-/ .

- scriptFile: This is the javascript file that is loaded with the skin if you need to include some javascript actions. For example, the Open File button needs a javascript or to move a panel, you need a javascript as well. Create first a new file and call it Scriptfile.js (in the same folder).

- onLoad: Tells the player to load everything that needs to be loaded on start. For example, the equalizers preset are loaded on start.


From now on, you can test your skin in Windows Media Player. To test it follow these intructions:

1) Save your file as .wms if not already done.
2) Double-Click your .wms file.
3) The skin will load in Windows Media Player.
4) Right-Click + Exit to close the skin.

Note that the skin will not be set as default as long as you are not choosing the skin in the skin list. Only set it as default once its done completly. Each you want to test it again, you might will get a warning message, just accept it to replace with the current version of your skin.


Your complete code should look like that:
<THEME id=\"Example_skin_1\"
title=\"Example Skin 1\"
author=\"NGPixel | www.ngpixel.com\"
copyright=\"&copy; NGPixel.com. All rights reserved.\">

<VIEW
backgroundColor=\"none\"
clippingColor = \"#FF15E8\"
transparencyColor=\"#FF15E8\"
backgroundImage = \"backgd.bmp\"
titleBar = \"false\"
scriptFile = \"scriptfile.js\"
onLoad=\"OnLoad();\">

</VIEW>

</THEME>




Chapter 7 - Writing the XML - Basic Elements

It's now time to add some more elements such as the visualization window, the seek and volume bar, etc. Your skin might look cool but there's nothing you can do with it currently. Let's add some more functionalities.

First, we need to create a SubView. A SubView is a group of elements from a same panel. For example, you need one SubView for the main skin and one SubView for a moving panel that can hide below the main skin.

Copy-Paste this code inside the View tag:
<SUBVIEW

id=\"mainview\"
left = \"0\"
height = \"420\"
clippingColor = \"#FF15E8\"
backgroundImage = \"backgd.bmp\"
zIndex = \"3\">


The ID is the name of the SubView. Left means the position in px from the left, the height is the height in pixel from the top, the 2 others are the same as the View tag (look the previous chapter for more info) and the ZIndex is the order from below to top. If you have multiple panel, this define what is on top of the other. The more is the number, the more it is on top.

Don't forget to close that tag at the end.

From this point, i'll split this chapter into objects, such scroll down to the object you want to insert in your skin or simple follow it in order. Each object code goes in the SubView Tag.

The values are the ones used in the example skin from the pack.

- Visualization Window

The visualization window displays the visualizations when playing a song. Unfortunatly, the visualization window and the video window aren't the same so by default, you can't put the 2 at the same time and let the player decide which one to use. The easiest way to fix this problem is to set a button that will switch between the 2 windows. Even more advanced, you could set the video zIndex on top of the myeffect zIndex so the video window will appear on top of it when a video is played.

The code:
<EFFECTS
id = \"myeffects\"
top = \"66\"
left = \"13\"
width = \"150\"
height = \"113\"
zIndex = \"5\"
/>


Explanation:

- ID = The name of the object
- Top = Position in pixels from the top of the subview
- Left = Position in pixels from the left of the subview
- Width = Width in pixels of the object
- Height = Height in pixels of the object
- zIndex = (Optional) Level Order from below to top


- Video Window

The video window display the movies. (see visualization window object for more details)

The code:
<VIDEO
id = \"hiddenvideo\"
backgroundColor = \"#000000\"
top = \"48\"
left = \"7\"
width = \"360\"
height = \"139\"
zIndex = \"4\"
/>


Explanation:

- ID = The name of the object
- BackgroudColor = The background color of the window in HEX colour code
- Top = Position in pixels from the top of the subview
- Left = Position in pixels from the left of the subview
- Width = Width in pixels of the object
- Height = Height in pixels of the object
- zIndex = (Optional) Level Order from below to top


- Volume Slider

There're many methods to make a volume slider, it can be a block that you move, a fill type, a round button, etc. In this example, its going to be a fill type.

Note that you will need the images from the pack if you want to use the same files. The image fills must be 1px wide.

The code:
<slider toolTip=\"Volume\"
left=\"227\" top=\"126\" width=\"154\" tiled=\"true\"
backgroundImage=\"seek1.bmp\"
foregroundImage=\"seek_fill1.bmp\"
thumbImage=\"seek1.bmp\"
borderSize=\"0\" min=\"0\"
max=\"100\" min=\"0\"
value=\"wmpprop:player.settings.volume\"
onDragEnd=\"player.settings.volume=value;\">
</slider>


Explanation:

- toolTip = The name of the object and the mouse over tooltip text.
- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Width = Width in pixels of the object.
- Tiled = If the fill image is repeated (almost always true value)
- Background Image = The background image of the slider.
- Foreground Image = The image when the volume is over this position. (can be repeated, make it 1 px width)
- ThumbImage = Same as Background Image in most case.
- Bordersize = The size of the border if you need one. (Put it in the background image instead)
- Min = The mininum value of the slider. %
- Max = The maximum value of the slider. %
- Value = This retrieve the actual volume of the player.
- onDragEnd = When the user release the slider, the volume change to the new value.


- Seek Slider

There're many methods to make a seek slider, it can be a block that you move, a fill type, a round button, etc. In this example, its going to be a fill type.

Note that you will need the images from the pack if you want to use the same files. The image fills must be 1px wide.

The code:
<slider toolTip=\"Seek\"
left=\"227\" top=\"154\" width=\"154\" tiled=\"true\"
backgroundImage=\"seek.bmp\"
foregroundImage=\"seek_fill.bmp\"
thumbImage=\"seek.bmp\"
borderSize=\"0\" min=\"0\"
max=\"wmpprop:player.currentmedia.duration\"
value=\"wmpprop:player.Controls.currentPosition\"
onDragEnd=\"player.controls.currentposition=value;\">
</slider>


Explanation:

- toolTip = The name of the object and the mouse over tooltip text.
- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Width = Width in pixels of the object.
- Tiled = If the fill image is repeated (almost always true value)
- Background Image = The background image of the slider.
- Foreground Image = The image when the volume is over this position. (can be repeated, make it 1 px width)
- ThumbImage = Same as Background Image in most case.
- Bordersize = The size of the border if you need one. (Put it in the background image instead)
- Min = The mininum value of the slider.
- Max = The maximum value of the slider (which is the current song or movie position).
- Value = This retrieve the actual position of the song or movie.
- onDragEnd = When the user release the slider, the seek position change to the new value.


- Media Name

This object display the current media name. It's a text object.

The Code:
<text left=\"182\" top=\"69\" width=\"160\"
tooltip=\"Current Media\" justification=\"Center\"
foregroundColor=\"#FFFFFF\" fontSize=\"8\"
value=\"wmpprop:player.currentMedia.name\">
</text>


Explanation:

- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Width = Width in pixels of the object.
- toolTip = The name of the object and the mouse over tooltip text.
- Justification = Position of the text inside the object itself.
- foregroundColor = The color of the text in HEX colour code
- fontSize = The size of the text
- value = Retrieves the name of the media.


- Current Position of the Media

This object display the current position of the media. It's a text object.
Display Example: 3:43

The Code:
<text left=\"306\" top=\"95\" width=\"60\"
tooltip=\"Current Position\" justification=\"Right\"
foregroundColor=\"#FFFFFF\" fontSize=\"10\" fontStyle=\"Bold\"
value=\"wmpprop:player.controls.currentPositionString\">
</text>


Explanation:

- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Width = Width in pixels of the object.
- toolTip = The name of the object and the mouse over tooltip text.
- Justification = Position of the text inside the object itself.
- foregroundColor = The color of the text in HEX colour code.
- fontSize = The size of the text.
- fontStyle = Bold, Italic, etc.
- value = Retrieves the current position of the media.


- Current Status of the Media

(not in the example file, you can find it in the Twodded Skin)

This object display the current status of the media. It's a text object.
Display Example: Buffering..., Playing

The Code:
<text left=\"0\" top=\"0\" width=\"85\"
tooltip=\"Current Media\" justification=\"Center\"
foregroundColor=\"#000000\" fontSize=\"7\"
value=\"wmpprop:player.status\">
</text>


Explanation:

- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Width = Width in pixels of the object.
- toolTip = The name of the object and the mouse over tooltip text.
- Justification = Position of the text inside the object itself.
- foregroundColor = The color of the text in HEX colour code.
- fontSize = The size of the text.
- value = Retrieves the current status of the media.



Chapter 8 - Writing the XML - Buttons

The buttons is in fact one object that groups all the buttons. You can specify the mask that determines the buttons position, the mouse over position of the buttons and a down state of the buttons.

First, we need to set the ButtonGroup. Copy-paste this code:

<buttongroup
mappingImage=\"mask.jpg\"
hoverImage=\"hoverimage.bmp\"
downImage=\"downimage.bmp\">


the hover (mouse-over state) and down image are optional but it's always useful for the user to feel that they are clicking on something. All these images needs to be the same EXACT size as the main skin background (unless using moving panels, the main skin background can be bigger than the mask).

You can add the end tag of the buttongroup:

From this point, i'll split this chapter into objects, such scroll down to the object you want to insert in your skin or simple follow it in order. Each object code goes in the ButtonGroup Tag.

For each object, the mappingColor is the HEX colour code of the color corresponding to that button in the mask image file. For example, if the color of the play button in the mask file is black then the HEX colour code is #000000.

- Play Button

This object affects a play button to the mapped color.

The Code:
<playelement mappingColor=\"#CCFFFF\">
</playelement>



- Pause Button

This object affects a pause button to the mapped color.

The Code:
<pauseelement mappingColor=\"#FE9900\">
</pauseelement>



- Stop Button

This object affects a stop button to the mapped color.

The Code:
<stopelement mappingColor=\"#669ACC\">
</stopelement>



- Minimize Button

This object affects a "minimize the player" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#65FFFF\"
upToolTip=\"Minimize\"
onClick=\"view.minimize();\">
</buttonelement>


Explanation:

- upToolTip = The tooltip message when you mouse over this button.
- onClick = Give the action to minimize the player into the taskbar.


- Close/Exit Button

This object affects a "Close/Exit the player" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#99FE00\"
upToolTip=\"Close\"
onClick=\"view.close();\"></buttonelement>


Explanation:

- upToolTip = The tooltip message when you mouse over this button.
- onClick = Give the action to close/exit the player.


- Return to full mode Button

This object affects a "Return to full mode" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#41BD99\"
upToolTip=\"Return to Full Mode\"
onClick=\"view.returnToMediaCenter();\"></buttonelement>


Explanation:

- upToolTip = The tooltip message when you mouse over this button.
- onClick = Give the action to return to the full player mode.


- Next Button

This object affects a "Next song/media" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#320000\"
onclick=\"jscript:player.controls.next()\"
upToolTip=\"Next\"
cursor=\"system\"
enabled=\"wmpenabled:player.controls.next\">
</buttonelement>


Explanation:

- upToolTip = The tooltip message when you mouse over this button.
- onClick = Give the action to play the next media.
- cursor = Reset the cursor to the system default.
- enable = Enable this fonction.

- Previous Button

This object affects a "Previous song/media" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#0033FF\"
onclick=\"jscript:player.controls.previous()\"
upToolTip=\"Previous\"
cursor=\"system\"
enabled=\"wmpenabled:player.controls.previous\">
</buttonelement>


Explanation:

- upToolTip = The tooltip message when you mouse over this button.
- onClick = Give the action to play the previous media.
- cursor = Reset the cursor to the system default.
- enable = Enable this fonction.


- Mute Button

(note used in the example file, you can find it in the Twodded Skin)

This object affects a "Mute" button to the mapped color.

The Code:
<buttonelement mappingColor=\"#123456\"
onClick=\"jscript:player.settings.mute=down;\"
upToolTip=\"Mute\" downToolTip=\"Sound\"
down=\"wmpprop:player.settings.mute\"
sticky=\"true\"></buttonelement>


Explanation:

- onClick = Mute any sound made by the player.
- upToolTip = The tooltip message when you mouse over this button.
- downToolTip = The tooltip message when you mouse over this button in mute state.
- down = Tell the player to perform the alternate mute action.
- sticky = The button stays in down state when clicked.



Chapter 9 - Moving Panels

Moving panels are used to hide more features of the skin below the main skin. Which let you have a small skin but a wide collection of feature. For example, at the bottom of your skin, you could set a panel that can slide below and display an equalizer or a video window (what we call a theater mode).

Let's start with the design itself.

1) Open your design software.

2) Make a rectangle of the size of your choice THAT CAN HIDE BELOW YOUR MAIN SKIN.

3) Export it as BMP, JPG or GIF.

Here's what i've done for my example skin:
Final Panel Version

Now let's add a new SUBVIEW to our skin XML.

Copy-Paste this code below your current SUBVIEW
<SUBVIEW

id=\"drawer\"
left = \"13\"
top = \"49\"
height = \"193\"
clippingColor = \"#F5F5F5\"
backgroundImage = \"sliding_p.jpg\"
zIndex = \"1\">


Explanation:

- ID = the name of the subview (Must be the same as in your scriptfile)
- Left = Position in pixels from the left of the subview.
- Top = Position in pixels from the top of the subview.
- Height = Height in pixels of the object.
- ClippingColor = Not used for this example.
- backgroundImage = The background image of this subview
- zIndex = The order of levels. Remember that this value must stay below your main skin zIndex value so it goes under.

Dont' forget to close your SubView with an end tag:

From this point, you can add the same objects as in the previous chapters. All objects are relative in position (left and top) from the subview itself, not the main skin.

Look at the next chapter for more objects like equalizers, presets, etc.

Now, let's do some javascript.

In this chapter, you are going to see why we need a javascript file. The JS file will do not more than move the panel when the user click a button that you define. This animation is fully customizable such as the speed, the start position and final position.

First, be sure that you made a target script at the beginning of the XML so the JS file is loaded in the skin.

In the VIEW tag properties...
scriptFile = \"scriptfile.js\"


Now, open your JS file in your text editor (or Dreamweaver).

We need to set first a variable that tells if the panel is opened or closed.

Copy-Paste this code:
var g_isOpen = false;


Then we can write the animation script:
Copy-Paste this code below the variable:
function moveDrawer() {
if (g_isOpen) {
drawer.moveTo(310,85,500);
g_isOpen = false;
} else {
drawer.moveTo(66,85,500);
g_isOpen = true;
}
}


Explanation:

if(f_isOpen) ->
drawer = The name of the SUBVIEW group.
moveTo(X,Y,S) = X is the new left position, Y is the new top position, S is the speed
else ->
drawer = The name of the SUBVIEW group.
moveTo(X,Y,S) = X is the original left position, Y is the original top position, S is the speed

Now add this function to a button:

<buttonelement mappingColor=\"#CC00FF\"
onClick=\"JScript:moveDrawer();\"
sticky=\"true\">
</buttonelement>


You can now test your skin!



Chapter 10 - Moving Elements

It's also possible to move objects from a position to another. It can be useful if you have a video window that can be expanded in another panel.

The method is the same as the previous chapter.

This code is used to move a video object to another position on the skin (you can even move it on another subview if you want).

videowin.moveTo(84,119,1);
videowin.height = 87;
videowin.width = 133;


Explanation:

videowin.moveTo(X,Y,S); = videowin is the object name, X is the new left position, Y is the next top position and S is the speed. If you don't want the user to see the object move but simply appear at the specified position, put 1.

videowin.height = 87; = This tells the new height of the video window.
videowin.width = 133; = This tells the new width of the video window.

Note that you can use these settings for any objects.



Chapter 11 - Building an Equalizer

Now that your skin is complete, you want some more? Well, add an equalizer! These aren't easy to make but within this chapter, you'll find all you need in order to make fully working one with complete range.

In this chapter, i use values from the Twodded WMP Skin, you can download the files here:

(.zip)

I recommend to put your equalizer in a separate SUBVIEW since it's a complex group.

You first need to specify that an equalizer is starting (load the current EQ positions):

<EQUALIZERSETTINGS id=\"eq\" enabled=\"true\"/>


Next, we set all the sliders with their text description at the bottom. Since all the sliders are the same for the properties, i'm going to explain them right now then you can get the code for each.

The slider object:

- ID = Name of the equalizer slide #
- Left = Left position from the left of the subview.
- Top = Top position in pixel from the top of the subview.
- Width = Width in pixel of the slider.
- Height = Height in pixel of the slider.
- Enabled = Enable the equalizer when allowed.
- Tooltip = Description of the slider when mouse-over the object.
- Direction = Either the slider is horizontal or vertical.
- Background Image = self-explaining
- ThumbImage Image = The image of the little bar that you move to set the level of that slider.
- Transparency Color = Transparency color of the slider if there's any.
- Min = The minimum value of that slider.
- Max = The maximum value of the slider.
- Value = Set the position of the Thumb image depending on the current value.
- Value_OnChange = Set the new value of the EQ for that slider.
- Enabled_OnChange = Changed the cursor to the specified one when dragging.

The text object:

- ID = Name of the equalizer slide #
- Left = Left position from the left of the subview.
- Top = Top position in pixel from the top of the subview.
- Width = Width in pixel of the slider.
- Height = Height in pixel of the slider.
- Enabled = Enable the equalizer when allowed.
- Foreground color = Color of the text in HEX colour code.
- fontStyle = Bold, Italic property for the text.
- disabledForegroundColor = Color of the text in HEX colour code when the EQ is disabled.
- disabledFontStyle = Style of the text when the EQ is disabled.
- Justification = Position of the text inside the object
- fontFace = Font used for the text.
- Value = The value of the text (what the user see).

Instead of using exact values of the left, top, width and height properties, its better to use relative values. This way, each object position is set based on the last one position.

example: JScript:eq1.left-6

Now, here's the BIG HUGE code for the EQ:

<SLIDER id=\"eq1\" borderSize=\"8\"
left=\"62\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel1\"
value_onchange=\"eq.gainLevel1=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq1\" left=\"JScript:eq1.left-6\" top=\"124\"
width=\"JScript:eq1.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"31\"/>

<SLIDER id=\"eq2\" borderSize=\"8\"
left=\"80\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel2\"
value_onchange=\"eq.gainLevel2=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq2\" left=\"JScript:eq2.left-6\" top=\"124\"
width=\"JScript:eq2.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"62\"/>

<SLIDER id=\"eq3\" borderSize=\"8\"
left=\"98\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel3\"
value_onchange=\"eq.gainLevel3=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq3\" left=\"JScript:eq3.left-6\" top=\"124\"
width=\"JScript:eq3.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"125\"/>

<SLIDER id=\"eq4\" borderSize=\"8\"
left=\"116\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel4\"
value_onchange=\"eq.gainLevel4=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq4\" left=\"JScript:eq4.left-6\" top=\"124\"
width=\"JScript:eq4.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"250\"/>

<SLIDER id=\"eq5\" borderSize=\"8\"
left=\"134\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel5\"
value_onchange=\"eq.gainLevel5=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq5\" left=\"JScript:eq5.left-6\" top=\"124\"
width=\"JScript:eq5.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"500\"/>

<SLIDER id=\"eq6\" borderSize=\"8\"
left=\"152\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel6\"
value_onchange=\"eq.gainLevel6=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq6\" left=\"JScript:eq6.left-6\" top=\"124\"
width=\"JScript:eq6.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"1\"/>

<SLIDER id=\"eq7\" borderSize=\"8\"
left=\"170\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel7\"
value_onchange=\"eq.gainLevel7=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq7\" left=\"JScript:eq7.left-6\" top=\"124\"
width=\"JScript:eq7.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"2\"/>

<SLIDER id=\"eq8\" borderSize=\"8\"
left=\"188\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel8\"
value_onchange=\"eq.gainLevel8=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq8\" left=\"JScript:eq8.left-6\" top=\"124\"
width=\"JScript:eq8.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"4\"/>

<SLIDER id=\"eq9\" borderSize=\"8\"
left=\"206\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel9\"
value_onchange=\"eq.gainLevel9=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq9\" left=\"JScript:eq9.left-6\" top=\"124\"
width=\"JScript:eq9.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"8\"/>

<SLIDER id=\"eq10\" borderSize=\"8\"
left=\"224\" top=\"43\"
width=\"18\" height=\"67\"
enabled=\"wmpprop:bEqOnOff.down\"
toolTip=\"Graphic equalizer control\"
direction=\"vertical\"
backgroundimage=\"equalizer_track.bmp\"
thumbImage=\"equalizer_thumb.bmp\"
transparencyColor=\"#FF00FF\"
min=\"-14\" max=\"14\"
value=\"wmpprop:eq.gainLevel10\"
value_onchange=\"eq.gainLevel10=value;\"
enabled_onchange=\"JScript:cursor=enabled?'hand':'system';\"/>
<TEXT id=\"tEq10\" left=\"JScript:eq10.left-6\" top=\"124\"
width=\"JScript:eq10.width+12\" height=\"15\"
enabled=\"wmpprop:bEqOnOff.down\"
foregroundColor=\"#B3D9F0\"
fontStyle=\"bold\"
disabledForegroundColor=\"#A9A9A9\"
disabledFontStyle=\"normal\"
justification=\"Center\"
fontFace=\"Ariel\"
fontSize=\"7\"
value=\"16\"/>





Chapter 12 - Even more stuff!

- Open File button

Open a browse window to open a new media.

The Code:
<BUTTONELEMENT id=\"bOpenFile\" mappingColor=\"#CCFF00\"
upToolTip=\"Open File\"
onClick=\"OpenMedia();\"
enabled=\"true\"/>


PLUS, add this code into your javascript file:

function OpenMedia() {

newFile = theme.openDialog('FILE_OPEN', 'FILES_ALLMEDIA');
if (newFile) {
player.URL = newFile;
player.controls.play();
}
}


- Equalizer Preset List button

Display a small list of available presets when clicking on a button.

The Code: (must be under )
<BUTTON id=\"bPresetSelect\" left=\"252\" top=\"99\"
width=\"24\" height=\"27\"
image=\"equalizer_preset_button.bmp\"
downImage=\"equalizer_preset_button_down.bmp\"
enabled=\"wmpprop:bEqOnOff.down\"
transparencyColor=\"#FF00FF\"
upToolTip=\"Presets\"
onClick=\"JScript:popupPreset.selectedItem=eq.currentPreset;popupPreset.show();\"/>

<POPUP id=\"popupPreset\" left=\"wmpprop:bPresetSelect.left\" top=\"wmpprop:bPresetSelect.top\"
backgroundColor=\"#FFFFFF\"
foregroundColor=\"#000000\"
selectedItem_onchange=\"JScript:eq.currentPreset=popupPreset.selectedItem;\"/>


The first code is a button with the same properties as a normal one. The second code creates a popup list when the button is clicked. You can specify the background color and the foreground color of that list. The list will appear next to the button when clicked.

You also need to put that code in your javascript file to tell the player to load the available presets when the player is loaded. If you don't put this code, your list is going to be empty.

function OnLoad() {

player.settings.autoStart = true;

/* load the preset popups */
for (i = 0; i < eq.presetCount; i++) {
popupPreset.appendItem(eq.presetTitle(i));
}
}


- Using Transparency

You can set a transparency level to a specific object, a subview or the view itself (the complete skin).

The Code:
JScript:elementID.alphaBlend=255


More details from MSDN:

This attribute is a read/write Number (long) with a value ranging from 0 (no opacity) to 255 (full opacity) and a default value of 255.

The less opacity, the more transparent the element will appear. Each element in the skin can have a separate opacity value except for button elements in a BUTTONGROUP control. When alphaBlend is set in VIEW, the opacity of the entire skin will be set. Alpha blend will not work for windowed controls, including PLAYLIST, EFFECTS, LISTBOX, POPUP, EDITBOX, and VIDEO (if windowless is set to false). When alphaBlend is set on VIEW, the whole skin becomes transparent. The transparencyColor attributes used by several elements are not supported with alphaBlend.

When you use alphaBlend with a TEXT element that does not have the backgroundColor specified, a background color of black will be used. If the foreground color is also black (which is the default value for TEXT.foregroundColor), your text may become unreadable. In order to prevent this, always specify the backgroundColor attribute, or set foregroundColor to a color other than black.

Note: This attribute is not supported in Windows 98.

---


- Visibility - Hide/Show

It is possible to hide or show an object on a particular even such as clicking on a button.

The Code:
JScript:elementID.visible=false




Chapter 13 - Making the Final Package

You've done your skin, it's now time to make the final package. To do so, you need WinZip.

1) Verify that all your files are in the same folder (no sub-folders).
2) Verify that your skin XML has a .wms extension.
3) Verify that your script file is linked in your XML and has a .js extension.
4) ZIP all your files (not the folder, the files) and make a .zip file.
5) Rename your file as yourskinname.wmz
6) Be sure to read the next chapter for some important tips.



Chapter 14 - Distribution

Now that your .wmz file is packed, there're some tips that you should know.

- Never put your download directly as .wmz, some browsers open them as ZIP files and will extract all your file content. Instead, zip your .wmz again as .zip and put this zip file as download. People will download this file and extract the .wmz, then they only have to double-click to see your skin.

- When submitting your skin on skins website (such as WinCustomize, DeviantArt, WMPlugins, etc) , be sure to include a screenshot of your skin working in expanded mode. This means open all your panels and play a song while taking the screenshot so the users see all the features of your skin before downloading.

And finally, be sure to fully test your skin before going into distribution, a button could have some problems or a feature isn't working as it should.



Chapter 15 - Using Round Skin

Using a round skin (like the Twodded WMP Skin one) is much harder to make since borders aren't anti-aliased. Also, you can't set a weird color like pink when you use a blue theme skin. If you do, you are going to see a little pink border on your skin.

Here's an example:
Pink border

To do so, you must find a color that is near the border color of your skin but that is not in your main skin at all (Or your skin will have some transparent spots :) ).

I've taken a color that is some levels brighter than the border color, here's the result:
Normal border

The easiest way is to fade your borders with another color then use a color brighter for the mask.
Good luck! :)



Chapter 16 - Notes & Legal Stuff

If you have any questions concerning this guide, post a comment or PM me. :)

You can find all the objects, attributes, handle events and more on the MSDN WMP SDK:
Click here...

Writting a such big tutorial is confusing sometimes with a lot of codes and stuff, i can't review everything in this tutorial if you ever find some errors or anything wrong in the tutorial, please PM me to report it. It's a big help.

This guide has been written by NGPixel. You cannot edit or modify this document in any way. This tutorial can ONLY be displayed on Twodded (Pixel2Life) website. You are only authorized to put a link to this page.

2005 � Pixel2Life | All rights reserved
Premium Publisher
Dig this tutorial?
Thank the author by sending him a few P2L credits!

Send
NGPixel

Lead Programmer at Pixel2Life

My tutorials are mostly about PHP, MySQL, XHTML, CSS and Fireworks.
View Full Profile Add as Friend Send PM
Pixel2Life Home Advanced Search Search Tutorial Index Publish Tutorials Community Forums Web Hosting P2L On Facebook P2L On Twitter P2L Feeds Tutorial Index Publish Tutorials Community Forums Web Hosting P2L On Facebook P2L On Twitter P2L Feeds Pixel2life Homepage Submit a Tutorial Publish a Tutorial Join our Forums P2L Marketplace Advertise on P2L P2L Website Hosting Help and FAQ Topsites Link Exchange P2L RSS Feeds P2L Sitemap Contact Us Privacy Statement Legal P2L Facebook Fanpage Follow us on Twitter P2L Studios Portal P2L Website Hosting Back to Top