- you can now specify how many songs (in %) shall be ingnored in the next shuffle list
- you can now specify how much songs should be favored that you have not heared in a long time
- progresbar while filling node
- separate ini-file
- made it a Media-Monkey installation package (mmip)
- using shuffle instead of true random
- added additional param to option dialog due to shuffle
- made it an auto script
- Cleaned up the code a bit.
- Fixed wrong trace output
Changed the code when and where options are saved to and loaded from file.
Changed logging to use random filenames for each script instance.
Logging still disabled by default.
The strange messagebox saying "Unknown name" doesn't appear anymore.
It turned out, that the subs "InitOptionSheet" and "SaveOptionSheet"
must exist, even if they are not used.
chooseWheigtedRating checks if songlists for a randomly chosen rating
are empty. If they are, another rating is generated.
Logging is disabled by default.
- I changed the error checking code completely
- A few other bugfixes (e.g. unknown variable ratesSongLists)
- changed the ratings to ranges (as Big_Berny sugested)
I have written a script that plays music based on their ratings.
Auto-DJ, AutoDJ, Rating, Weighting, Radio, Radio-DJ, highly configurable
Play music based on their rating. Allows user defined weightingsand is highly configurable. Supports Auto-DJ. Uses a Playlist as input.
Reason / Motivation:
I wanted a script where
- I could define my own weightings (and save them)
- I could define which music files should be used.
- I could use as Auto-DJ.
I searched around and found for example scripts like "RadioFreeMonkey" or "JustPlaySomething" (to mention just the best of the scripts i found), but they had not (all of) the above mentioned functionality I wanted.
All scripts I found used the whole music library.
I could either not modify the weightings or just by editing the source code.
In one case the 11 ratings of MM were internally reduced to 2 (two!) rating classes
So I decided to write my own
Since in this forum there were some people asking for exactly such a script I post it to this forum. Have fun!
If you find bugs, have questions or have ideas for this script
please post them in this thread.
Please be patient. I will probably only have time on weekends to answer your questions.
Description for users:
See download link at the end of this posting.
It is a MediaMonkey instalattion package, so you just have to execute it.
I use a separate ini-file sinve V1.2.0 to store the settings.
When you have used V1.1 or earlier, your settings will be copied to the new ini-file. The old values will then be removed. That means: if you want to use an earlier version afterwards, it will revert to default settings.
If you prefer to install the script manually do the following:
Copy the file RadioDJ.vbs from the installation package to the directory ...\MediaMonkey\Scripts\auto.
Edit the file ...\MediaMonkey\Scripts\Scripts.ini.
Add the following lines:
DisplayName=Radio-DJ as Auto-DJ Plug-in
How to use:
After starting MM you have a new options dialog in "Tools / Options / RadioDJ Options".
You also have a new node "Radio-DJ Vx.x.x", but for the moment the options
are more important.
In the new Options dialog you can configure the weightings. For each rating (e.g.
bomb, half star, one star etc.) you can define a number which is the weighting.
In addition you must define the name of a playlist where the script takes the
songs from. Default name for that playlist is "RadioDJ_Input", but you can use whatever name you like.
If you want to use your whole library, just create an auto-playlist
with Status="is reachable". Personaly I prefer a playlist where I choose some genre and
a minimum rating.
Go to the Options page for Auto-DJ and select "Radio-DJ as Auto-DJ Plug-in" from the drop down list.
To start Radio-DJ open the menu "play" and enable "Auto-DJ".
Start the player.
Now you should hear songs randomly but according to the weightings you have
defined in the options dialog.
In addition to the Auto-DJ functionality there is also a new node in the MM-Tree
called "Radio-DJ Vx.x.x". This Node is populated with songs each time you enter
it. It also uses the mentioned weightings. The amount of songs that is put below
this node is also defined in the options dialog. Just change maxSongs to the
amount you prefer.
Important to know:
Reagarding the repetition of a single song, there is not only the weighting important, but also the amount of songs per rating.
Lets have a look at this example:
Code: Select all
Let's say we have the following amount of songs in MM Amount of Rating songs -------- -------- 5 Stars 20 4 Stars 700 3 Stars 1000 This brings us to the following list where I have assumed a weighting that you maybe would use. I also computed the resulting probability for each rating and what this means in terms of "How often is a song from this rating in my playlist?". Finaly you can see after how many songs a song from a rating gets repeated. Probability Every x-th Amount of for this song comes repetition Rating songs Weighting rating from this rating after x songs -------- -------- --------- ------ ---------------- ------------- 5 Stars 20 20 57,14% 1,75 35 4 Stars 700 10 28,57% 3,5 2450 3 Stars 1000 5 14,29% 7 7000 Now I have set all the weightings to the same number. Surprisingly this doesn't mean, that every song is played as often as each other song. It only means, that the probability for each rating is the same. But since we have only very few songs in the 5 star rating, a song from the 5 star rating gets repeated much more often than every other song. Probability Every x-th Amount of for this song comes repetition Rating songs Weighting rating from this rating after x songs -------- -------- --------- ------ ---------------- ------------- 5 Stars 20 10 33,33% 3 60 4 Stars 700 10 33,33% 3 2100 3 Stars 1000 10 33,33% 3 3000 This is just to show you, that even with a weighting in 5 stars, that is less than the weighting of 4 stars, songs from 5 stars still get repeated more often than other songs. Probability Every x-th Amount of for this song comes repetition Rating songs Weighting rating from this rating after x songs -------- -------- --------- ------ ---------------- ------------- 5 Stars 20 5 16,67% 6 120 4 Stars 700 20 66,67% 1,5 1050 3 Stars 1000 5 16,67% 6 6000 In this example you can see which weightings you would need so that every song gets repeated more or less the same. (just in this very special example) Probability Every x-th Amount of for this song comes repetition Rating songs Weighting rating from this rating after x songs -------- -------- --------- ------ ---------------- ------------- 5 Stars 20 0,35 1,2% 85,7 1714,3 4 Stars 700 12 40,0% 2,5 1750,0 3 Stars 1000 17 56,7% 1,8 1764,7 Btw: if you want to know after how many songs a song from a rating will probably be repeated, you can use this formula: repeat_after_n_songs = amount_of_songs_in_that_rating * sum_of_all_weightings / weighting_of_that_rating
Each time the script is started, it builds internal lists with songs. One list per rating.
When populating the node or the playlist in Auto-DJ mode, each song that gets added to
the node / playlist is removed from the internal list. When an internal list is empty, it gets
recreated. That way we get the shuffle.
MM starts this script quite often. Every click on the node starts this script
thus building the internal lists from scratch. When you enable or disable Auto-DJ,
the sript gets restarted. When you open / close the options dialog the script gets
restarted (you don't even need to enter the options page for Radio-DJ). And of
corse when you restart MM. (I'm not sure if this list is complete, but at least at
these occations I observed, that my script is restarted).
This could lead to the effect, that you have just heard a song. Then for some reason
the script gets restarted and you hear the same song again, since the internal list
would have been rebuilt.
To get around this situation, I have introduced the param "Skip most recently played". It means, that when populating the internal lists, for each rating the most recently x percent are ignored.
For this feature to work, the input playlist must be sorted by the atribute "Last Played" from Z..A (songs just played are on top, songs not played for a long tome are on the bottom). When usin static playlist as input for Radio-DJ, this sorting is done by the script. But if you use auto playlists as input for Radio-DJ (as I do), than you have to make sure, that the auto playlist is sorted, by yourself.
In addition you can define what I called a "Favor Factor". With this number (from 0..5) you can the the randomizer how much it should favor songs that have not been played for a long time. This is in addition the the weightings. First the weighting is choosen then within the weighting a song is choosen according to the Favor Factor. When you set the Favor Factor to zero (0) disable the Favor Factor and every song within this rating has the same posibillity (as in previous versions). When you set it to one (1), songs that have not been played for a long time get a slightly higher possibility. When you set it to five (5), songs that have not been played for a long time get a very stron emphasis.
As before: For this feature to work, the input playlist must be sorted by the atribute "Last Played" from Z..A.
Please have in mind, that MM may start this script twice (or more) at the same time
(e.g. Auto-DJ is working and click on the Radio-DJ node). If this happens, both instances
are completely independent of each other. The fact that you just created a long list of
songs in the Radio-DJ node has no influence on the songs that get played via Auto-DJ.
Description for the technically interested / script developers:
The engine of this script is a class called ratedSongList with three (main) functions called
The last one (chooseWeightedRating) is probably the most important.
It returns a rating randomly but weighted. This uses the weightings i.e. the
distribution defined by the user in the option dialog.
To get the distribution, all the weightings are "added" or better, they
get placed one after another on a line.
Let's have a look at this example:
We have 3 Ratings: A, B, C
They are weighted like this:
A = 1
B = 15
C = 50
Drawn on a line this could look s.th. like this:
Code: Select all
0 1 16 66 +-+---------------+--------------------------------------------------+ A B C
If the result is between 16 and 66 the chosen weighting is C. If the result
is between 1 and 16 the chosen weighting is B. If the result is between 0
and 1 the chosen weighting is A.
Thus even if the randomizer uses a uniform distribution, the distribution
of the ratings is NOT uniform but weighted.
createRatedSongLists creates an array of SongLists.
In each SongList are only songs with the same rating. This is somewhat similar
to the rating node in MM. Just that it only has the songs coming from the
playlist defined in the options dialog and not all songs as in MM.
In addition the most recently played x% are ignored.
Finally chooseRandomSong returns a Song randomly. This uses the rating returned
by chooseRandomRating, i.e. the weighted distribution defined by the user.
The algorithm to return a song randomly but with the possibillity for the user to select a "Favor Factor" is somewhat complicated. It is documented in the code. Basically it involves the function y=(x+1)^n, where n is the Favor Factor and x is the position of the song in the sorted list. Since in the code I get a random number from which I must calculate the song, I have to build the integral of the above function and convert it to the inverse function. If somebody is really interested in this, pleas ask me in the forum. I will then be hapy to explain it in detail.
Additionally there is a class called DynamicArray. This class is the basic data structure
for the shuffle algorithm. Each item is accessible via an index, but items can be added
and removed. Internally it uses a dictionary object. When removing item, the sort oder can be kept (needs more time) or a fast remove can be done (destroys the order of the items).
Then there is a class called ConfigData that holds all the data from the options dialog.
All other code / classes is "normal" code; i.e. a class to read and write
the config data from the options dialog to an ini file. A class for trace
prints to a log file, the options dialog etc.
NOTE TO OTHER SCRIPTERS:
Do not post a modified copy or copy of the Radio-DJ script anywhere.
Modification should be posted in this thread only, and only the part
that is modified.
http://www.mediafire.com/?sharekey=0630 ... f6e8ebb871
Just execute the installation package.