Sample AMG Search script: Difference between revisions

From MediaMonkey Wiki
Jump to navigation Jump to search
m (Added remark about wiki problem, and added/removed spaces)
No edit summary
 
(5 intermediate revisions by 3 users not shown)
Line 1: Line 1:
==Attention==
'''Maybe this script should be changed to one using a website that allows this kind of action. ''AMG does not.'''''
----
This script demonstrates how to plug-in into MediaMonkey Web Search dialog. It searches AMG web a lets user tag some basic fields. Don't forget that it's rather a sample of what [[Search scripts]] can do than fully working script.
This script demonstrates how to plug-in into MediaMonkey Web Search dialog. It searches AMG web a lets user tag some basic fields. Don't forget that it's rather a sample of what [[Search scripts]] can do than fully working script.




It currently searches AllMusicGuide's web for the given album, presents user results found and lets tag some basic fields:
It currently searches AllMusic's website for the given album, presents user results found and lets tag these fields:
* Album
* Album
* Artist
* Artist
* Track titles
* Track titles
* Album art
* Album art
* Release year
* Genres
* Styles
* Moods
* Themes




Line 17: Line 27:


It's quite well documented, and so it can help in creation of your own Search scripts.
It's quite well documented, and so it can help in creation of your own Search scripts.
'''Important remark: due to a problem in the Wiki software, ''Shell_Explorer'' is displayed with an underscore instead of a dot. This isn't correct and the script won't work. Before running the script, be sure to change the underscore ( _ ) to a dot ( . )'''


<source lang="vb">
<source lang="vb">
Line 29: Line 36:
' [SearchAMG]
' [SearchAMG]
' FileName=SearchAMG.vbs
' FileName=SearchAMG.vbs
' ProcName=SearchAMG
' Order=10
' Order=10
' DisplayName=Search All Music Guide
' DisplayName=Search All Music Guide
Line 44: Line 50:


   ' This is a web browser that we use to present results to the user
   ' This is a web browser that we use to present results to the user
   Set WB = UI.NewActiveX(Panel, "Shell_Explorer")
   Set WB = UI.NewActiveX(Panel, "Shell.Explorer")
   WB.Common.Align = 5      ' Fill whole client rectangle
   WB.Common.Align = 5      ' Fill whole client rectangle
   WB.Common.ControlName = "WB"
   WB.Common.ControlName = "WB"


   ' This is a hidden browser that we use to find results (a better solution can be used, but this seems to be the easiest...)
   ' This is a hidden browser that we use to find results (a better solution can be used, but this seems to be the easiest...)
   Set WB2 = UI.NewActiveX(Panel, "Shell_Explorer")
   Set WB2 = UI.NewActiveX(Panel, "Shell.Explorer")
   WB2.Common.ControlName = "WB2"
   WB2.Common.ControlName = "WB2"


Line 190: Line 196:
       If Left(itm.src,Len("http://image.allmusic.com/")) = "http://image.allmusic.com/" Then
       If Left(itm.src,Len("http://image.allmusic.com/")) = "http://image.allmusic.com/" Then
         SDB.Tools.WebSearch.AlbumArtURL = itm.src
         SDB.Tools.WebSearch.AlbumArtURL = itm.src
      End If
    Next
    ' Get release year
    Set SpanColl = Doc.getElementsByTagName("span")
    For Each itm In SpanColl
      pos = InStr(itm.innerText, "Release Date")
      If pos > 0 Then
        Set Parnt = itm.parentNode.parentNode.parentNode.parentNode
        Set TDColl = Parnt.getElementsByTagName("td")
        For Each itm2 In TDColl
          If itm2.className = "sub-text" Then
            ReleaseYear = Right(itm2.innerText, 4)
            Exit For
          End If
        Next
        Exit For
      End If
    Next
   
    ' Get genres/styles/moods/themes
    ListCnt = 0
    Set DivColl = Doc.getElementsByTagName("div")
    For Each itm In DivColl
      pos = InStr(itm.id, "left-sidebar-list")
      If pos > 0 Then
        Set AColl = itm.getElementsByTagName("a")
        MyList = ""
        For Each itm2 In AColl
          If MyList <> "" Then MyList = MyList & ";"
          MyList = MyList & itm2.innerText
        Next
        ListCnt = ListCnt + 1
        Select Case ListCnt
          Case 1
            Genres = MyList
          Case 2
            Styles = MyList
          Case 3
            Moods = MyList
          Case 4
            Themes = MyList
        End Select
       End If
       End If
     Next
     Next
Line 204: Line 253:
       SDB.Tools.WebSearch.NewTracks.Item(i).ArtistName = ArtistTitle
       SDB.Tools.WebSearch.NewTracks.Item(i).ArtistName = ArtistTitle
       SDB.Tools.WebSearch.NewTracks.Item(i).AlbumName = AlbumTitle
       SDB.Tools.WebSearch.NewTracks.Item(i).AlbumName = AlbumTitle
      SDB.Tools.WebSearch.NewTracks.Item(i).Year = ReleaseYear
      SDB.Tools.WebSearch.NewTracks.Item(i).Genre = Genres
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom1 = Styles
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom2 = Moods
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom3 = Themes
     Next
     Next
     SDB.Tools.WebSearch.RefreshViews  ' Tell MM that we have made some changes
     SDB.Tools.WebSearch.RefreshViews  ' Tell MM that we have made some changes

Latest revision as of 09:29, 19 January 2018

Attention

Maybe this script should be changed to one using a website that allows this kind of action. AMG does not.


This script demonstrates how to plug-in into MediaMonkey Web Search dialog. It searches AMG web a lets user tag some basic fields. Don't forget that it's rather a sample of what Search scripts can do than fully working script.


It currently searches AllMusic's website for the given album, presents user results found and lets tag these fields:

  • Album
  • Artist
  • Track titles
  • Album art
  • Release year
  • Genres
  • Styles
  • Moods
  • Themes


There's a lot that could be improved, namely:

  • Error handling - currently many possible problems aren't solved
  • More fields could be tagged
  • Results could be formatted using custom HTML page (not the downloaded one)
  • Many others...


It's quite well documented, and so it can help in creation of your own Search scripts.

' Sample AMG Search script
'
' This script demonstrates how to plug-in into MediaMonkey Web Search dialog. You should save it to Scripts folder as
' SearchAMG.vbs. It has to be in Scripts.ini file, where entries can be as follows:
'
' [SearchAMG]
' FileName=SearchAMG.vbs
' Order=10
' DisplayName=Search All Music Guide
' Language=VBScript
' ScriptType=3

Dim WB, WB2
Dim FoundLinks
Dim Tmr

' MediaMonkey calls this method whenever a search is started using this script
Sub StartSearch(Panel, SearchTerm, SearchArtist, SearchAlbum)
  Set UI = SDB.UI

  ' This is a web browser that we use to present results to the user
  Set WB = UI.NewActiveX(Panel, "Shell.Explorer")
  WB.Common.Align = 5      ' Fill whole client rectangle
  WB.Common.ControlName = "WB"

  ' This is a hidden browser that we use to find results (a better solution can be used, but this seems to be the easiest...)
  Set WB2 = UI.NewActiveX(Panel, "Shell.Explorer")
  WB2.Common.ControlName = "WB2"

  WB.Common.BringToFront

  ' The following HTML is taken from AMG web pages - so that we don't have to load the search page and can post the query directly
  ' The following line will probably need some better way of retrieving server name from AMG. Using www.allmusicguide.com doesn't work at this moment.
  html = "<form name=""search"" action=""http://wm08.allmusic.com/cg/amg.dll"" method=""post"">"
  html = html & "<input type=""hidden"" name=""P"" value=""amg"" />"
  html = html & "<p><input type=""text"" name=""sql"" id=""search_txt"" />"
  html = html & "<input type=""image"" src=""/i/pages/wide/go.gif"" id=""search_button"" /></p>"
  html = html & "<p><select name=""opt1"" id=""search_opt"">"
  html = html & "  <option value=""1"" selected=""selected"">Artist/Group</option>"
  html = html & "  <option value=""2"">Album</option>"
  html = html & "  <option value=""3"">Song</option>"
  html = html & "  <option value=""55"">Classical Work</option>"
  html = html & "</select></p>"
  html = html & "</form>"

  Set WB2Intf = WB2.Interf
  WB2Intf.Visible = false

  WB2.SetHTMLDocument html

  Set Doc2 = WB2Intf.Document
  Set SrchTxt = Doc2.getElementById("search_txt")
  If SearchAlbum <> "" Then
    SrchTxt.Value = SearchAlbum
  Else
    SrchTxt.Value = SearchTerm
  End If

  Set SrchType = Doc2.getElementById("search_opt")
  SrchType.selectedIndex = 1  ' Search for an album

  Set SrchButton = Doc2.getElementById("search_button")
  SrchButton.Click

  Set Tmr = SDB.CreateTimer(40)
  Script.RegisterEvent Tmr, "OnTimer", "ContinueSearch"
End Sub

' We use this procedure as a callback using Timer, so that we can present results as soon as they are downloaded
Sub ContinueSearch(Timer)
  Script.UnregisterEvents Tmr
  Set Tmr = Nothing

  Set WB2Intf = WB2.Interf

  If Len(WB2Intf.LocationURL) < 10 Then        ' A trick - wait until navigation to the search results page starts
    Set Tmr = SDB.CreateTimer(40)
    Script.RegisterEvent Tmr, "OnTimer", "ContinueSearch"
    Exit Sub
  End If

  If WB2Intf.ReadyState = 1 Or WB2Intf.Busy Then
    Set Tmr = SDB.CreateTimer(40)
    Script.RegisterEvent Tmr, "OnTimer", "ContinueSearch"
    Exit Sub
  End If

  Set Doc2 = WB2Intf.Document

  Set DivResults = Doc2.body

  Set Results = SDB.NewStringList
  Set FoundLinks = SDB.NewStringList
  If IsObject(DivResults) And Not IsNull(DivResults) Then
    Set AColl = DivResults.getElementsByTagName("A")
    For Each itm In AColl
      Set Imgs = itm.getElementsByTagName("img")
      pos = InStr(CStr(itm.href), ".com/")
      If pos > 0 Then
        href = Mid(itm.href, pos)
        If Left(href,Len(".com/cg/amg.dll?p=amg&sql=10:")) = ".com/cg/amg.dll?p=amg&sql=10:" And Imgs.length = 0 Then
          Results.Add itm.innerText
          FoundLinks.Add itm.href
        End If
      End If
    Next

    SDB.Tools.WebSearch.SetSearchResults Results
    If Results.Count > 0 Then
      SDB.Tools.WebSearch.ResultIndex = 0
    End If
  Else
    WB.SetHTMLDocument = Doc2.documentElement.innerHTML
  End If
End Sub

' This procedure is called by MediaMonkey when user selects some of search results
Sub ShowResult(ResultID)
  If ResultID >= 0 And ResultID < FoundLinks.Count Then
    SDB.Tools.WebSearch.ClearTracksData   ' Tell MM to disregard any previously set tracks' data
    WB.SetHTMLDocument ""                 ' To prevent usage of this data
    WB.Interf.Navigate FoundLinks.Item(ResultID)

    Set Tmr = SDB.CreateTimer(500)
    Script.RegisterEvent Tmr, "OnTimer", "ResultFullyLoaded"
  End If
End Sub

' This is a callback handled by a timer, so that we can respond as soon as album results are loaded
Sub ResultFullyLoaded(Timer)
  Script.UnregisterEvents Tmr
  Set Tmr = Nothing

  Set Tracks = SDB.NewStringList

  Set Doc = WB.Interf.Document

  If IsObject(Doc) Then
    ' Get track titles
    Set AColl = Doc.getElementsByTagName("A")
    For Each itm In AColl
      Set Imgs = itm.getElementsByTagName("img")
      pos = InStr(CStr(itm.href), ".com/")
      If pos > 0 Then
        href = Mid(itm.href, pos)
        If Left(href,Len(".com/cg/amg.dll?p=amg&sql=33:")) = ".com/cg/amg.dll?p=amg&sql=33:" And Imgs.length = 0 Then
          Tracks.Add itm.innerText
        End If
      End If
      If itm.className = "subtitle" Then
        ArtistTitle = itm.innerText
      End If
    Next

    ' Get album title
    Set SpanColl = Doc.getElementsByTagName("Span")
    For Each itm in SpanColl
      If itm.className = "title" Then
        AlbumTitle = itm.innerText
      End If
    Next

    ' Get Album art URL
    Set ImgColl = Doc.getElementsByTagName("Img")
    For Each itm in ImgColl
      If Left(itm.src,Len("http://image.allmusic.com/")) = "http://image.allmusic.com/" Then
        SDB.Tools.WebSearch.AlbumArtURL = itm.src
      End If
    Next

    ' Get release year
    Set SpanColl = Doc.getElementsByTagName("span")
    For Each itm In SpanColl
      pos = InStr(itm.innerText, "Release Date")
      If pos > 0 Then
        Set Parnt = itm.parentNode.parentNode.parentNode.parentNode
        Set TDColl = Parnt.getElementsByTagName("td")
        For Each itm2 In TDColl
          If itm2.className = "sub-text" Then
            ReleaseYear = Right(itm2.innerText, 4)
            Exit For
          End If
        Next
        Exit For
      End If
    Next
    
    ' Get genres/styles/moods/themes
    ListCnt = 0
    Set DivColl = Doc.getElementsByTagName("div")
    For Each itm In DivColl
      pos = InStr(itm.id, "left-sidebar-list")
      If pos > 0 Then
        Set AColl = itm.getElementsByTagName("a")
        MyList = ""
        For Each itm2 In AColl
          If MyList <> "" Then MyList = MyList & ";"
          MyList = MyList & itm2.innerText
        Next
        ListCnt = ListCnt + 1
        Select Case ListCnt
          Case 1
            Genres = MyList
          Case 2
            Styles = MyList
          Case 3
            Moods = MyList
          Case 4
            Themes = MyList
        End Select
      End If
    Next
  End If

  If Tracks.Count = 0 Then
    ' Nothing found yet, wait some more time
    Set Tmr = SDB.CreateTimer(500)
    Script.RegisterEvent Tmr, "OnTimer", "ResultFullyLoaded"
  Else
    ' Some results were found, notify MediaMonkey
    SDB.Tools.WebSearch.SmartUpdateTracks Tracks
    For i = 0 To SDB.Tools.WebSearch.NewTracks.Count - 1
      SDB.Tools.WebSearch.NewTracks.Item(i).ArtistName = ArtistTitle
      SDB.Tools.WebSearch.NewTracks.Item(i).AlbumName = AlbumTitle
      SDB.Tools.WebSearch.NewTracks.Item(i).Year = ReleaseYear
      SDB.Tools.WebSearch.NewTracks.Item(i).Genre = Genres
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom1 = Styles
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom2 = Moods
      SDB.Tools.WebSearch.NewTracks.Item(i).Custom3 = Themes
    Next
    SDB.Tools.WebSearch.RefreshViews   ' Tell MM that we have made some changes
  End If
End Sub

' This does the final clean up, so that our script doesn't leave any unwanted traces
Sub FinishSearch(Panel)
  ' Correctly terminate all the actions we have started
  WB.Common.DestroyControl      ' Destroy the external control
  WB2.Common.DestroyControl     '    "     "     "        "
  Set WB = Nothing              ' Release global variable
  Set WB2 = Nothing             '    "      "        "
  Set FoundLinks = Nothing      '    "      "        "
  If IsObject(Tmr) Then
    Script.UnregisterEvents Tmr ' Unregister timer events
    Set Tmr = Nothing           ' Release global variable
  End If
End Sub