// EasyStats Webcasters Toolkit (#ES8P653-909392107)
// Copyright © 2002, Randall Krause.
// Unauthorized reproduction prohibited.

// ====================================== DEFINES

LS = new Object( );
LS.Filters = new Object( );
LS.Widgets = new Object( );
LS.CFields = new Array( );
LS.AFields = new Array( );

LS_QUERY_CTRLSTATE_RESET = 2;
LS_QUERY_CTRLSTATE_INIT = 1;
LS_QUERY_CTRLSTATE_READY = 0;
LS_QUERY_CHECKTIME = 4;
LS_QUERY_REFRESHTIME = 300;
LS_QUERY_STATIONID = 296699;

LS_QUERY_LICENSEID = '8P653-909392107';

LS.TransferState = LS_QUERY_CTRLSTATE_INIT;

// ====================================== SUPPORT

LS.ScaledText =
	function ( AlphaText, BetaText, AlphaStyle, BetaStyle ) { if( AlphaText != null ) this.AlphaText = AlphaText; if( BetaText != null ) this.BetaText = BetaText; if( AlphaStyle != null ) this.AlphaStyle = AlphaStyle; if( BetaStyle != null ) this.BetaStyle = BetaStyle; this.GetScale = function ( Value, Length ) { var Output; if( Value == -1 ) { return this.ErrorText; } Output = '<FONT CLASS="' + this.AlphaStyle + '">'; for( Count = 0; this.Algorithm( Value, Count ) == true && Count < Length; Count++ ) Output += this.AlphaText; Output += '</FONT><FONT CLASS="' + this.BetaStyle + '">'; for( ; Count < Length; Count++ ) Output += this.BetaText != null ? this.BetaText : this.AlphaText; Output += '</FONT>'; return Output; }; }; // v01
LS.ScaledImage =
	function ( ImageSrc, ImageWidth, ImageHeight, ImagePadding ) { this.ImageSrc = ImageSrc; this.ImageWidth = ImageWidth; this.ImageHeight = ImageHeight; if( ImagePadding != null ) this.ImagePadding = ImagePadding; this.GetScale = function ( Value, Length ) { var Output = ''; if( Value == -1 ) { return this.ErrorText; } for( Count = 0; this.Algorithm( Value, Count ) == true && Count < Length; Count++ ) { Output += '<IMG SRC="' + this.ImageSrc + '" ALT="' + Value + '"'; if( this.ImagePadding != null ) Output += ' HSPACE="' + this.ImagePadding + '"'; Output += ' WIDTH="' + this.ImageWidth + '" HEIGHT="' + this.ImageHeight + '">'; } return Output; }; }; // v01

// ====================================== GENERAL

Number.prototype.toTimeString = function ( FWidth ) { return Math.floor( Math.abs( this / 60 ) ).toPadString( FWidth ) + ':' + ( this % 60 ).toPadString( 2 ); };
Number.prototype.toDecString = function ( FPrecision ) { var FValue = Math.abs( this ); var FInt, FDec; FInt = Math.floor( FValue ); FDec = 1 + FValue - FInt; FDec = FDec + Math.pow( 10, -1 - FPrecision ); FDec = Math.floor( FDec * Math.pow( 10, FPrecision ) ); return( FInt + '.' + FDec.toString( ).slice( 1 ) ); };
Number.prototype.toPadString = function ( FWidth ) { var FValue = Math.abs( this ); var FInt, FDec; FInt = Math.floor( FValue ); if( FWidth > FInt.toString( ).length ) FInt = ( FInt + Math.pow( 10, FWidth ) ).toString( ).slice( 1 ); return( FInt ); };

// ====================================== SYSTEM

LS.CFields.Add = LS.AFields.Add = function ( Elem ) { this[ this.length ] = Elem; };
LS.Widget = LS.CField = function ( Filter, Width, Height, Color, Style ) { LS.CFields.Add( this ); this.Filter = Filter; this.Filter.Widget = this; if( Style == null ) Style = Filter.Style; if( Width == null ) Width = Filter.Width; if( Color == null ) Color = Filter.Color; this.Field = this.Filter.Field = new LS.AField( Width, Height, Color, Style ); this.Update = function ( Results ) { this.Field.SetText( this.Filter.Read( Results ) ); }; };
LS.Field = LS.AField = function ( Width, Height, Color, Style, Text ) { var Output; LS.AFields.Add( this ); if( Color != null ) this.Color = Color; if( Style != null ) this.Style = Style; if( Width != null ) this.Width = Width; if( Text != null ) this.Text = Text; if( window.document.layers == null ) { Output = '<SPAN CLASS="' + this.Style + '" ID="LSField' + LS.AFields.length + '" STdYLE="position: relative;'; if( this.Color != null ) Output += ' background-color: ' + this.Color + ';'; Output += '">&nbsp;</SPAN>'; document.write( Output ); this.Layer = window.document.all[ 'LSField' + LS.AFields.length ]; } else { Output = '<ILAYER CLASS="' + this.Style + '" ID="LSField' + LS.AFields.length + '">'; Output += '<LAYER'; if( this.Color != null ) Output += ' BGCOLOR="' + this.Color + '"'; Output += '>&nbsp;</LAYER>&nbsp;'; Output += '<SPACER TYPE=block HEIGHT="1" ALIGN=top WIDTH="' + this.Width + '"></ILAYER>'; document.write( Output ); this.Layer = window.document.layers[ 'LSField' + LS.AFields.length ]; } this.SetColor = function ( Color ) { if( window.document.layers == null ) this.Layer.style.backgroundColor = Color; else this.Layer.layers[ 0 ].bgColor = Color; }; this.SetText = function( Text ) { if( window.document.layers == null ) this.Layer.innerHTML = ( Text != '' ? Text : '&nbsp;' ); else { this.Layer.layers[ 0 ].document.open( ); this.Layer.layers[ 0 ].document.write( '<DIV CLASS="' + this.Style + '">' + Text + '&nbsp;' + '</DIV>' ); this.Layer.layers[ 0 ].document.close( ); } }; this.Reset = function ( ) { this.SetText( this.Text ); this.SetColor( this.Color ); }; this.Clear = function ( ) { this.SetText( '' ); }; };
LS.GetQueryAge = function ( ) { return Math.round( ( new Date( ) ).getTime( ) / 1000 ) - LS.QueryTimestamp; };
LS.UpdateWidgets = function ( ) { var FieldIndex, IsFirstQuery, IsNextTrack; LS.QueryTimestamp = Math.round( ( new Date( ) ).getTime( ) / 1000 ); if( LS.TransferState != LS_QUERY_CTRLSTATE_RESET ) return; if( LS.ResultsLayer.Station == null || LS.ResultsLayer.Station.IsValid == false ) return; IsFirstQuery = LS.TrackSource == null; IsNextTrack = LS.TrackSource == '' || LS.TrackSource != LS.ResultsLayer.Station.TrackSource; if( IsNextTrack == true ) LS.TrackSource = LS.ResultsLayer.Station.TrackSource; for( FieldIndex = 0; FieldIndex < LS.CFields.length; FieldIndex++ ) { LS.CFields[ FieldIndex ].Update( LS.ResultsLayer.Station, IsFirstQuery, IsNextTrack ); } LS.TransferState = LS_QUERY_CTRLSTATE_READY; LS.TimerID = setTimeout( LS.ReloadResults, Math.min( LS.ResultsLayer.Station.TrackRemain + LS_QUERY_CHECKTIME - LS.GetQueryAge( ), LS_QUERY_REFRESHTIME ) * 1000 ); };
LS.DestroyWidgets = window.onunload = function ( ) { var FieldIndex; for( FieldIndex = 0; FieldIndex < LS.CFields.length; FieldIndex++ ) if( LS.CFields[ FieldIndex ].Destroy != null ) LS.CFields[ FieldIndex ].Destroy( ); clearTimeout( LS.TimerID ); };
LS.ReloadResults = function ( ) { LS.TransferState = LS_QUERY_CTRLSTATE_RESET; if( window.document.layers == null ) LS.ResultsLayer.location.reload( true ); else location.reload( ); };
window.onload = function ( ) { if( LS.ResultsLayer.Station != null ) return; LS.ResultsLayer.document.open( ); LS.ResultsLayer.document.write( '<BODY onLoad="parent.LS.UpdateWidgets( );"></BODY>' ); LS.ResultsLayer.document.write( '<SCRIPT SRC="http://www.searstower.org/EasyStats/services/query.cgi?' + LS_QUERY_LICENSEID + '"></SCRIPT>' ); setTimeout( 'LS.ResultsLayer.document.close( );' ); };
document.write( '<LAYER ID="LSResults"></LAYER>\n' );
document.write( '<IFRAME ID="LSResults" STYLE="display: none;"></IFRAME>\n' );
LS.ResultsLayer = window.document.layers == null ? document.frames.LSResults : document.layers.LSResults;
LS.TransferState = LS_QUERY_CTRLSTATE_RESET;

// ====================================== COMPONENTS

LS.Widgets.Playlist =
	function ( Width, Length, Text, ErrorText, Style, HiliteColor, BackColor ) { var TrackCount; if( Width != null ) this.Width = Width; if( Length != null ) this.Length = Length; if( Text != null ) this.Text = Text; if( ErrorText != null ) this.ErrorText = ErrorText; if( Style != null ) this.Style = Style; if( HiliteColor != null ) this.HiliteColor = HiliteColor; if( BackColor != null ) this.BackColor = BackColor; this.Fields = new Array( this.Length ); this.History = new Array( ); document.write( '<TABLE WIDTH="' + this.Width + '" CELLPADDING="2" CELLSPACING="0" BORDER="0">\n' ); for( TrackCount = this.Length; TrackCount >= 0; TrackCount-- ) { document.write( '<TR BGCOLOR=' + ( TrackCount == 0 ? this.HiliteColor : this.BackColor ) + '><TD WIDTH="100%">' ); this.Fields[ TrackCount ] = ( new LS.AField( this.Width - 4, null, null, this.Style ) ); document.write( '</TD></TR>' ); } document.write( '</TABLE>' ); this.Update = function ( Results, IsFirstQuery, IsNextTrack ) { if( Results.TrackLength == -1 ) this.Fields[ 0 ].SetText( this.ErrorText ); else if( IsNextTrack == true ) this.AddTrack( Results.TrackArtist, Results.TrackTitle, Results.TrackAlbum, Results.TrackLength, Results.TrackSource ); }; this.AddTrack = function ( TrackArtist, TrackTitle, TrackAlbum, TrackLength, TrackSource ) { var Results = new Object( ); Results.TrackArtist = TrackArtist; Results.TrackTitle = TrackTitle; Results.TrackAlbum = TrackAlbum; Results.TrackLength = TrackLength; Results.TrackSource = TrackSource; this.History.Add( this.TrackRenderHook, Results ); }; this.History.Add = function ( RenderHook, Results ) { var TrackRecord = new Object( ); TrackRecord.RenderHook = RenderHook; TrackRecord.Results = Results; this[ this.length ] = TrackRecord; this.Parent.DrawTracks( ); }; this.History.Parent = this; this.DrawTracks = function ( ) { var TrackCount, Output; for( TrackCount = 0; TrackCount <= this.Length; TrackCount++ ) { var Output = ''; if( this.History.length > TrackCount ) Output += this.History[ this.History.length - TrackCount - 1 ].RenderHook( TrackCount, this.History.length ); this.Fields[ TrackCount ].SetText( Output ); } }; this.TrackRenderHook = function TrackRenderHook( TrackCount, HistoryLength ) { return ( new LS.Filters.TrackDetails( TrackRenderHook.Parent.Text ) ).Read( this.Results ).replace( /%6/, TrackCount + 1 ).replace( /%7/, ( HistoryLength - TrackCount ).toPadString( 2 ) ); }; TrackRenderHook.Parent = this; LS.CFields.Add( this ); }; // v05
LS.Widgets.TrackCounter =
	function ( Width, Style, IsReversed ) { if( Width != null ) this.Width = Width; if( Style != null ) this.Style = Style; if( IsReversed != null ) this.IsReversed = IsReversed; this.Field = new LS.AField( this.Width, null, null, this.Style ); this.Update = function ( Results, IsFirstQuery, IsNextTrack ) { if( IsNextTrack == false ) return; this.TrackFinish = Math.round( ( new Date( ) ).getTime( ) / 1000 ) + Results.TrackRemain - LS.GetQueryAge( ); this.TrackStart = this.TrackFinish - ( Results.TrackLength != -1 ? Results.TrackLength : Results.TrackRemain ); this.Start( ); }; this.DrawCounter = function DrawCounter( ) { var Parent = DrawCounter.Parent; var CurrentTime = Math.round( ( new Date( ) ).getTime( ) / 1000 ); var TrackTime = Parent.IsReversed == true ? Math.max( 0, Parent.TrackFinish - CurrentTime ) : Math.min( Parent.TrackFinish - Parent.TrackStart, CurrentTime - Parent.TrackStart ); Parent.Field.SetText( TrackTime.toTimeString( 2 ) ); }; DrawCounter.Parent = this; this.Start = function ( ) { if( this.TimerID != null ) this.Stop( ); this.TimerID = setInterval( this.DrawCounter, 1000 ); this.DrawCounter( ); }; this.Stop = function ( ) { clearInterval( this.TimerID ); this.TimerID = null; }; this.Destroy = this.Stop; this.Reverse = function ( ) { this.IsReversed = !this.IsReversed; this.DrawCounter( ); }; LS.CFields.Add( this ); }; // v02
LS.Widgets.TrackProgressScale =
	function ( Width, AlphaText, BetaText, AlphaStyle, BetaStyle ) { if( Width != null ) this.Width = Width; this.Base = LS.ScaledText; this.Base( AlphaText, BetaText, AlphaStyle, BetaStyle ); this.Field = new LS.AField( this.Width, null, null, null ); this.Update = function ( Results, IsFirstQuery, IsNextTrack ) { if( IsNextTrack != true ) return; this.TrackLength = ( Results.TrackLength != -1 ? Results.TrackLength : Results.TrackRemain ); this.TrackStart = Math.round( ( new Date( ) ).getTime( ) / 1000 ) - ( this.TrackLength - Results.TrackRemain ) - LS.GetQueryAge( ); this.Start( ); }; this.DrawProgress = function DrawProgress( ) { var Parent = DrawProgress.Parent; var CurrentTime = Math.round( ( new Date( ) ).getTime( ) / 1000 ); var TrackPosition = Math.floor( ( CurrentTime - Parent.TrackStart ) / Parent.TrackLength * 10 ); Parent.Field.SetText( Parent.GetScale( TrackPosition, 10 ) ); }; DrawProgress.Parent = this; this.Start = function ( ) { if( this.TimerID != null ) this.Stop( ); this.TimerID = setInterval( this.DrawProgress, 1000 ); this.DrawProgress( ); }; this.Stop = function ( ) { clearInterval( this.TimerID ); this.TimerID = null; }; this.Destroy = this.Stop; this.Algorithm = function ( Value, Count ) { return Count < Value; }; LS.CFields.Add( this ); }; // v02
LS.Widgets.TrackGraphic =
	function ( Width, Height, BasePath, DefaultImage ) { if( DefaultImage != null ) this.DefaultImage = DefaultImage; this.BasePath = BasePath; this.Width = Width; this.Height = Height; this.Update = function ( Results ) { this.Image.src = this.BasePath + '/' + ( Results.TrackGraphic != '' ? Results.TrackGraphic : this.DefaultImage ); }; document.write( '<IMG SRC="' + this.BasePath + '/' + this.DefaultImage + '" WIDTH="' + Width + '" HEIGHT="' + Height + '">' ); this.Image = document.images[ document.images.length - 1 ]; LS.CFields.Add( this ); }; // v01
LS.Widgets.TrackCaption =
	function ( DefaultText, Width, Style ) { if( DefaultText != null ) this.DefaultText = DefaultText; if( Style != null ) this.Style = Style; if( Width != null ) this.Width = Width; this.Field = ( new LS.AField( this.Width, null, null, this.Style ) ); this.Update = function ( Results ) { var Text = Results.TrackCaption != '' ? Results.TrackCaption : this.DefaultText; Text = Text.replace( /%1/g, Results.TrackArtist ).replace( /%2/g, Results.TrackTitle ).replace( /%3/g, Results.TrackAlbum ); this.Field.SetText( Text ); }; LS.CFields.Add( this ); }; // v01
LS.Widgets.TrackLyricSubtitles =
	function ( DefaultText, Width, Style ) { if( DefaultText != null ) this.DefaultText = DefaultText; if( Style != null ) this.Style = Style; if( Width != null ) this.Width = Width; this.Field = ( new LS.AField( this.Width, null, null, this.Style ) ); this.TimerIDs = new Array( 0 ); this.Update = function ( Results, IsFirstQuery, IsNextTrack ) { if( Results.TrackSubtitleMode != 2 ) { this.Field.SetText( this.DefaultText ); return; } if( IsNextTrack == true ) { this.Elapsed = Results.TrackLength - Results.TrackRemain; this.Subtitles = Results.TrackSubtitles; this.SubtitleID = null; this.Start( ); } }; this.DrawSubtitle = function DrawSubtitle( ) { var Parent = DrawSubtitle.Parent; Parent.Field.SetText( Parent.SubtitleID == Parent.Subtitles.length ? Parent.DefaultText : Parent.Subtitles[ Parent.SubtitleID ].Text ); Parent.SubtitleID++; }; DrawSubtitle.Parent = this; this.Start = function ( ) { var Count, TrackElapsed; if( this.TimerIDs.length != 0 ) this.Stop( ); TrackElapsed = this.Elapsed + LS.GetQueryAge( ); for( Count = 0; TrackElapsed >= 0 && Count < this.Subtitles.length; Count++ ) TrackElapsed -= this.Subtitles[ Count ].Length; if( this.SubtitleID != Count ) { this.SubtitleID = TrackElapsed < 0 ? Count - 1 : Count; this.DrawSubtitle( ); } if( TrackElapsed < 0 ) { this.TimerIDs[ this.TimerIDs.length ] = setTimeout( this.DrawSubtitle, -TrackElapsed * 1000 ); for( TrackElapsed = -TrackElapsed; Count < this.Subtitles.length; Count++ ) this.TimerIDs[ this.TimerIDs.length ] = setTimeout( this.DrawSubtitle, ( TrackElapsed += this.Subtitles[ Count ].Length ) * 1000 ); } }; this.Stop = function ( ) { var Count; for( Count in this.TimerIDs ) clearTimeout( this.TimerIDs[ Count ] ); this.TimerIDs = new Array( 0 ); }; this.Destroy = this.Stop; LS.CFields.Add( this ); }; // v02
LS.Widgets.TrackMixSubtitles =
	function ( PlaylistObj, Text ) { this.PlaylistObj = PlaylistObj; if( Text != null ) this.Text = Text; this.TimerIDs = new Array( 0 ); this.Source = null; this.Update = function ( Results, IsFirstQuery, IsNextTrack ) { if( Results.TrackSubtitleMode != 1 ) return; this.Elapsed = Results.TrackLength - Results.TrackRemain; if( IsNextTrack == true ) { this.Source = Results.TrackSource; this.Subtitles = Results.TrackSubtitles; this.SubtitleID = null; this.Start( ); } }; this.PushSubtitles = function PushSubtitles( ) { var Results = new Object( ); var Parent = PushSubtitles.Parent; var Subtitle = Parent.Subtitles[ Parent.SubtitleID ]; Results.TrackArtist = Subtitle.Artist; Results.TrackTitle = Subtitle.Title; Results.TrackAlbum = Subtitle.Album; Results.TrackLength = Subtitle.Length; Results.TrackSource = Parent.Source; Parent.PlaylistObj.History.Add( Parent.TrackRenderHook, Results ); Parent.SubtitleID++; }; PushSubtitles.Parent = this; this.TrackRenderHook = function TrackRenderHook( TrackCount, HistoryLength ) { return ( new LS.Filters.TrackDetails( TrackRenderHook.Parent.Text ) ).Read( this.Results ).replace( /%6/, TrackCount + 1 ).replace( /%7/, ( HistoryLength - TrackCount ).toPadString( 2 ) ); }; TrackRenderHook.Parent = this; this.Start = function ( ) { var Count, TrackElapsed; if( this.TimerIDs.length != 0 ) this.Stop( ); TrackElapsed = this.Elapsed + LS.GetQueryAge( ); for( Count = 0; TrackElapsed >= 0 && Count < this.Subtitles.length; Count++ ) TrackElapsed -= this.Subtitles[ Count ].Length; if( this.SubtitleID != Count ) { this.SubtitleID = Count - 1; this.PushSubtitles( ); } if( Count != this.Subtitles.length ) { this.TimerIDs[ this.TimerIDs.length ] = setTimeout( this.PushSubtitles, -TrackElapsed * 1000 ); for( TrackElapsed = -TrackElapsed; Count < this.Subtitles.length - 1; Count++ ) this.TimerIDs[ this.TimerIDs.length ] = setTimeout( this.PushSubtitles, ( TrackElapsed += this.Subtitles[ Count ].Length ) * 1000 ); } }; this.Stop = function ( ) { var Count; for( Count in this.TimerIDs ) clearTimeout( this.TimerIDs[ Count ] ); this.TimerIDs = new Array( 0 ); }; this.Destroy = this.Stop; LS.CFields.Add( this ); }; // v04
LS.Widgets.TrackVoteSelect =
	function ( OptionText ) { if( OptionText != null ) this.OptionText = OptionText; var Count; this.HasVoted = false; this.Update = function ( Results ) { if( this.TrackSource == Results.TrackSource ) return; this.HasVoted = false; this.Menu.selectedIndex = 0; this.TrackSource = Results.TrackSource; }; document.write( '<SELECT><OPTION NAME="0">&#151;</OPTION>' ); for( Count = 0; Count < 5; Count++ ) { document.write( '<OPTION VALUE="' + Count + '">' + this.OptionText[ Count ] + '</OPTION>' ); } document.write( '</SELECT>\n' ); this.Menu = document.forms[ document.forms.length - 1 ]; this.Menu = this.Menu[ this.Menu.length - 1 ]; this.Submit = function ( ) { var TrackVote = new Image( ); if( LS.TransferState != LS_QUERY_CTRLSTATE_READY || this.Menu.selectedIndex == 0 ) return; if( this.TrackSource == '' ) { alert( this.AlertFailure2Text ); return; } if( this.HasVoted == true ) { alert( this.AlertFailure1Text ); return; } this.HasVoted = true; TrackVote.Parent = this; TrackVote.onerror = function ( ) { alert( this.Parent.AlertFailure3Text ); }; TrackVote.onload = function ( ) { alert( this.Parent.AlertSuccessText ); this.Parent.Menu.selectedIndex = 0; }; TrackVote.src = 'http://searstower.org/EasyStats/services/track_vote.cgi?' + LS_QUERY_LICENSEID + '&' + this.Menu.options[ this.Menu.selectedIndex ].value + '&' + escape( this.TrackSource ) + '.gif'; return false; }; this.Menu.Parent = this; LS.CFields.Add( this ); }; // v03
LS.Widgets.TrackVoteSubmit =
	function ( TrackVoteSelectObj, Text ) { if( Text != null ) this.Text = Text; this.TrackVoteSelectObj = TrackVoteSelectObj; document.write( '<INPUT TYPE=button VALUE="' + this.Text + '">' ); this.Button = document.forms[ document.forms.length - 1 ]; this.Button = this.Button[ this.Button.length - 1 ]; this.Button.onclick = function ( ) { this.Parent.TrackVoteSelectObj.Submit( ); }; this.Button.Parent = this; }; // v01
LS.Widgets.Hyperlink =
	function ( URLFilter, Text, Target ) { if( Text != null ) this.Text = Text; if( Target != null ) this.Target = Target; this.URLFilter = URLFilter; this.Update = function ( Results ) { var Value = this.URLFilter.Read( Results ); if( Value == '' ) { this.Link.href = 'javascript: void( 0 );'; this.Link.target = '_self'; } else { this.Link.href = Value; this.Link.target = this.Target; } }; document.write( '<A HREF="javascript: void( 0 );">' + this.Text + '</A>' ); this.Link = document.links[ document.links.length - 1 ]; this.Link.title = this.Tooltip; LS.CFields.Add( this ); }; // v02
LS.Widgets.TrackTimeLink =
	function ( TrackCounterObj, Text ) { if( Text != null ) this.Text = Text; this.TrackCounterObj = TrackCounterObj; document.write( '<A HREF="javascript: void( 0 );">' + this.Text + '</A>' ); this.Link = document.links[ document.links.length - 1 ]; this.Link.title = this.Tooltip; this.Link.onclick = function ( ) { if( LS.TransferState != LS_QUERY_CTRLSTATE_READY ) return; this.Parent.TrackCounterObj.Reverse( ); }; this.Link.Parent = this; }; // v01
LS.Widgets.TrackInfoLink =
	function ( Text, Target ) { this.Base = LS.Widgets.Hyperlink; this.Base( new LS.Filters.TrackURL( this.Location, true ), Text, Target ); }; // v02
LS.Widgets.TrackBuyLink =
	function ( Text, Target ) { this.Base = LS.Widgets.Hyperlink; this.Base( new LS.Filters.TrackURL( this.Location, false ), Text, Target ); }; // v02
LS.Filters.TrackRatingScore =
	function ( Text, LegendText, ErrorText ) { if( Text != null ) this.Text = Text; if( LegendText != null ) this.LegendText = LegendText; if( ErrorText != null ) this.ErrorText = ErrorText; this.Read = function ( Results ) { var Output = this.Text; if( Results.TrackRatingScore == -1 ) return this.ErrorText; Output = Output.replace( /%1/g, Results.TrackRatingScore.toDecString( 2 ) ); Output = Output.replace( /%2/g, Results.TrackRatingVotes ); Output = Output.replace( /%3/g, this.LegendText[ Math.floor( Results.TrackRatingScore ) ] ); return Output; }; }; // v02
LS.Filters.TrackURL =
	function ( Location, SetArtistPacked ) { this.Location = Location; this.SetArtistPacked = SetArtistPacked; this.Read = function ( Results ) { var Output; if( Results.TrackArtist == '' ) return ''; Output = this.SetArtistPacked == true ? Results.TrackArtist.replace( /\s+/g, '' ) : Results.TrackArtist; Output = this.Location.replace( /%%1/g, escape( Output ) ).replace( /%%2/g, escape( Results.TrackTitle ) ).replace( /%%3/g, escape( Results.TrackAlbum ) ); return Output; }; }; // v01
LS.Filters.TrackDetails =
	function ( Text, ErrorText ) { if( Text != null ) this.Text = Text; if( ErrorText != null ) this.ErrorText = ErrorText; this.Read = function ( Results ) { var Output = this.Text; if( Results.TrackLength == -1 ) return this.ErrorText; Output = Output.replace( /%2/, Results.TrackTitle ); Output = Results.TrackArtist != '' ? Output.replace( /%1/, Results.TrackArtist ) : Output.replace( /[^|]*%1[^|]*/, '' ); Output = Results.TrackAlbum != '' ? Output.replace( /%3/, Results.TrackAlbum ) : Output.replace( /[^|]*%3[^|]*/, '' ); Output = Output.replace( /\|/g, '' ); Output = Output.replace( /%4/, ( new LS.Filters.TrackLength( ) ).Read( Results ) ); return Output; }; }; // v04
LS.Filters.TrackLength =
	function ( ) { this.Read = function ( Results ) { if( Results.TrackLength == -1 ) return ''; return Results.TrackLength.toTimeString( 1 ); }; }; // v01
LS.Filters.StreamStatus =
	function ( OnlineText, OfflineText ) { if( OnlineText != null ) this.OnlineText = OnlineText; if( OfflineText != null ) this.OfflineText = OfflineText; this.Read = function ( Results ) { return Results.IsOnline == true ? this.OnlineText : this.OfflineText; }; }; // v01
LS.Filters.StreamMode =
	function ( LiveText, BasicText ) { if( BasicText != null ) this.BasicText = BasicText; if( LiveText != null ) this.LiveText = LiveText; this.Read = function ( Results ) { return Results.IsLive == true ? this.LiveText : this.BasicText; }; }; // v01
LS.Filters.StreamBitrate =
	function ( ) { this.Read = function ( Results ) { return Results.Bitrate + ' kbps'; }; }; // v01
LS.Filters.StreamSpeed =
	function ( BitrateText ) { if( BitrateText != null ) this.BitrateText = BitrateText; this.Read = function ( Results ) { return this.BitrateText[ 'Speed' + Results.Bitrate ]; }; }; // v02
LS.Filters.GenreList =
	function ( Separator ) { if( Separator != null ) this.Separator = Separator; this.Read = function ( Results ) { var Output = ''; for( Count = 0; Count < 3 && LS.Results.Genres[ Count ] != ''; Count++ ) { if( Count > 0 ) Output += this.Separator; Output += Results.Genres[ Count ]; } return Output; }; }; // v01
LS.Filters.RatingScore =
	function ( Text, LegendText, ErrorText ) { if( Text != null ) this.Text = Text; if( LegendText != null ) this.LegendText = LegendText; if( ErrorText != null ) this.ErrorText = ErrorText; this.Read = function ( Results ) { var Output = this.Text; if( Results.RatingScore == -1 ) return this.ErrorText; Output = Output.replace( /%1/g, Results.RatingScore.toDecString( 2 ) ); Output = Output.replace( /%2/g, Results.RatingVotes ); Output = Output.replace( /%3/g, this.LegendText[ Math.floor( Results.RatingScore / 2 ) ] ); return Output; }; }; // v02
LS.Filters.ListenerHours =
	function ( ) { this.Read = function ( Results ) { return Results.ListenerHours; }; }; // v01
LS.Filters.ListenerCount =
	function ( ErrorText ) { if( ErrorText != null ) this.ErrorText = ErrorText; this.Read = function ( Results ) { if( Results.ListenerCount == -1 ) return this.ErrorText; return Results.ListenerCount; }; }; // v01
LS.Filters.RatingScoreScale =
	function ( AlphaText, BetaText, AlphaStyle, BetaStyle ) { this.Base = LS.ScaledText; this.Base( AlphaText, BetaText, AlphaStyle, BetaStyle ); this.Read = function ( Results ) { return this.GetScale( Results.RatingScore, 5 ); }; this.Algorithm = function ( Value, Count ) { return Math.round( Value / 2 ) >= Count + 1; }; }; // v01
LS.Filters.ListenerCountScale =
	function ( AlphaText, BetaText, AlphaStyle, BetaStyle ) { this.Base = LS.ScaledText; this.Base( AlphaText, BetaText, AlphaStyle, BetaStyle ); this.Read = function ( Results ) { return this.GetScale( Results.ListenerCount, 5 ); }; this.Algorithm = function ( Value, Count ) { return Value >= Math.pow( 5, Count ); }; }; // v01
LS.Filters.ListenerHoursScale =
	function ( AlphaText, BetaText, AlphaStyle, BetaStyle ) { this.Base = LS.ScaledText; this.Base( AlphaText, BetaText, AlphaStyle, BetaStyle ); this.Read = function ( Results ) { return this.GetScale( Results.ListenerHours, 5 ); }; this.Algorithm = function ( Value, Count ) { return Value >= Math.pow( 10, Count ); }; }; // v01
LS.Filters.RatingScoreFX =
	function ( ImageSrc, ImageWidth, ImageHeight, ImagePadding ) { this.Base = LS.ScaledImage; this.Base( ImageSrc, ImageWidth, ImageHeight, ImagePadding ); this.Read = function ( Results ) { return this.GetScale( Results.RatingScore, 5 ); }; this.Algorithm = function ( Value, Count ) { return Math.round( Value / 2 ) >= Count + 1; }; }; // v01
LS.Filters.ListenerCountFX =
	function ( ImageSrc, ImageWidth, ImageHeight, ImagePadding ) { this.Base = LS.ScaledImage; this.Base( ImageSrc, ImageWidth, ImageHeight, ImagePadding ); this.Read = function ( Results ) { return this.GetScale( Results.ListenerCount, 5 ); }; this.Algorithm = function ( Value, Count ) { return Value >= Math.pow( 5, Count ); }; }; // v01
LS.Filters.ListenerHoursFX =
	function ( ImageSrc, ImageWidth, ImageHeight, ImagePadding ) { this.Base = LS.ScaledImage; this.Base( ImageSrc, ImageWidth, ImageHeight, ImagePadding ); this.Read = function ( Results ) { return this.GetScale( Results.ListenerHours, 5 ); }; this.Algorithm = function ( Value, Count ) { return Value >= Math.pow( 10, Count ); }; }; // v01

// ====================================== DEFAULTS

LS.Field.prototype.Color = null;
LS.Field.prototype.Style = 'LSDefault';
LS.Field.prototype.Width = 50;

with( LS.Widgets )
{
	Playlist.prototype.Width			= 400;
	Playlist.prototype.Text				= '<B>%7</B>:&nbsp; |<B>%1</B> - |<I>"%2"</I>| - %3| &nbsp;<FONT CLASS="Time">(%4)</FONT>';
	Playlist.prototype.ErrorText			= 'Playlist Not Available';
	Playlist.prototype.Style			= 'LSPlaylist';
	Playlist.prototype.Length			= 3;
	Playlist.prototype.BackColor			= 'black';
	Playlist.prototype.HiliteColor			= 'darkblue';
	TrackCounter.prototype.IsReversed		= false;
	TrackCounter.prototype.Width			= 120;
	TrackCounter.prototype.Style			= 'LSTrackCounter';
	TrackProgressScale.prototype.AlphaText		= '>';
	TrackProgressScale.prototype.BetaText		= '<';
	TrackProgressScale.prototype.AlphaStyle		= 'LSTrackProgressScaleA';
	TrackProgressScale.prototype.BetaStyle		= 'LSTrackProgressScaleB';
	TrackGraphic.prototype.DefaultImage		= 'default.gif';
	TrackCaption.prototype.Width			= 60;
	TrackCaption.prototype.DefaultText		= 'No Information';
	TrackCaption.prototype.Style			= 'LSTrackCaption';
	TrackLyricSubtitles.prototype.Width		= 250;
	TrackLyricSubtitles.prototype.DefaultText	= '';
	TrackLyricSubtitles.prototype.Style		= 'LSTrackSubtitle';
	TrackMixSubtitles.prototype.PlaylistText	= '&nbsp; &nbsp; &nbsp; &#167; |<B>%1</B> - |<I>"%2"</I>| - %3';
	TrackVoteSelect.prototype.AlertFailure1Text	= 'You cannot rate this track again.';
	TrackVoteSelect.prototype.AlertFailure2Text	= 'You cannot rate this type of track.';
	TrackVoteSelect.prototype.AlertFailure3Text	= 'Your vote could not be successfully submitted.';
	TrackVoteSelect.prototype.AlertSuccessText	= 'Thank you for rating this track.';
	TrackVoteSelect.prototype.OptionText		= [ 'Poor', 'Okay', 'Average', 'Good', 'Very good', 'Excellent' ];
	TrackVoteSubmit.prototype.Text			= 'Submit';
	TrackTimeLink.prototype.Text			= '[Time]';
	TrackTimeLink.prototype.Tooltip			= 'Switch between elapsed and remaining track time.';
	TrackInfoLink.prototype.Location =		'http://www.allmusic.com/cg/amg.dll?sql=%%1&opt1=1&uid=SEARCH&P=amg';
	TrackInfoLink.prototype.Text			= '[Info]';
	TrackInfoLink.prototype.Target			= '_blank';
	TrackInfoLink.prototype.Tooltip			= 'Get info on this artist from AllMusicGuide.';
	TrackBuyLink.prototype.Location =		'http://www.amazon.com/exec/obidos/external-search?tag=blackgospelmusic&keyword=%%1+%%2&mode=blended';
	
	TrackBuyLink.prototype.Text			= '[Buy]';
	TrackBuyLink.prototype.Target			= '_blank';
	TrackBuyLink.prototype.Tooltip			= 'Purchase this album from Amazon.com.';
}
with( LS.Filters )
{
	TrackRatingScore.prototype.Text			= '%3 by %2 people';
	TrackRatingScore.prototype.ErrorText		= 'None';
	TrackRatingScore.prototype.LegendText		= [ 'Poor', 'Okay', 'Average', 'Good', 'Very good', 'Excellent' ];
	TrackRatingScore.prototype.Width		= 140;
	TrackDetails.prototype.Text			= '<I>"%2"</I>| by <B>%1</B>';
	TrackDetails.prototype.ErrorText		= 'Playlist Not Available';
	TrackDetails.prototype.Width			= 400;
	StreamStatus.prototype.OnlineText		= 'On-the-Air';
	StreamStatus.prototype.OfflineText		= 'Off-the-Air';
	StreamStatus.prototype.Width			= 90;
	StreamMode.prototype.LiveText			= '[Live]';
	StreamMode.prototype.BasicText			= '';
	StreamBitrate.prototype.Width 			= 75;
	StreamSpeed.prototype.BitrateText		= { Speed56: 'T1/DSL/Cable', Speed32: '56k Modem', Speed24: '33k Modem', Speed16: '28k Modem', Speed8: '14k Modem' };
	StreamSpeed.prototype.Width 			= 100;
	GenreList.prototype.Separator 			= ', ';
	GenreList.prototype.Width 			= 250;
	RatingScore.prototype.Text			= '%1 by %2 people';
	RatingScore.prototype.ErrorText			= 'N/A';
	RatingScore.prototype.LegendText		= [ 'Oh no!', 'So so', 'Average', 'Good', 'Very good', 'Exceptional!' ];
	RatingScore.prototype.Width			= 140;
	ListenerCount.prototype.Width 			= 30;
	ListenerCount.prototype.ErrorText 		= 'N/A';
	ListenerCount.prototype.ErrorText		= 'N/A';
	RatingScoreScale.prototype.AlphaText		= '&#182;';
	RatingScoreScale.prototype.BetaText		= null;
	RatingScoreScale.prototype.Style		= 'LSScaledText';
	RatingScoreScale.prototype.AlphaStyle		= 'A';
	RatingScoreScale.prototype.BetaStyle		= 'B';
	RatingScoreScale.prototype.Width		= 80;
	ListenerCountScale.prototype.AlphaText		= 'i';
	ListenerCountScale.prototype.BetaText		= null;
	ListenerCountScale.prototype.Style		= 'LSScaledText';
	ListenerCountScale.prototype.AlphaStyle		= 'A';
	ListenerCountScale.prototype.BetaStyle		= 'B';
	ListenerCountScale.prototype.Width		= 80;
	ListenerHoursScale.prototype.AlphaText		= 'i';
	ListenerHoursScale.prototype.BetaText		= null;
	ListenerHoursScale.prototype.Style		= 'LSScaledText';
	ListenerHoursScale.prototype.AlphaStyle		= 'A';
	ListenerHoursScale.prototype.BetaStyle		= 'B';
	ListenerHoursScale.prototype.Width		= 80;
	RatingScoreFX.prototype.ErrorText		= 'N/A';
	RatingScoreFX.prototype.ImagePadding		= 1;
	RatingScoreFX.prototype.Width			= 110;
	ListenerCountFX.prototype.ErrorText		= 'N/A';
	ListenerCountFX.prototype.ImagePadding		= 1;
	ListenerCountFX.prototype.Width			= 110;
	ListenerHoursFX.prototype.ImagePadding		= 1;
	ListenerHoursFX.prototype.Width			= 110;
}
