;_______________________________________ ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; Modules.hsp ; ; ・データベースあいまい検索、点数付けモジュール ; ・HTMLソース取得モジュール ; ・改行コードCRLF統一モジュール ; ・曲ファイルから情報取得モジュール ; ・歌詞URLから歌詞を抽出するモジュール ; ・LyricsMasterのテキストを取得・設定・解析 モジュール ; ・タイムタグ付き歌詞生成 モジュール ; ・ツールチップ モジュール ;_______________________________________ ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; データベースあいまい検索、点数付けモジュール ; ; lua-xl.hsp 使用 ;_______________________________________ #module TimetagDataBaseSearch ;******************************************************************************* ; 点数をつける際の各項目の重み付けを設定する ; ; PointInMusicList_option_set p1, p2, p3, p4 ; ; p1=数値 : タイトルの重み[0〜100] ; p2=数値 : アーティストの重み[0〜100] ; p3=数値 : アルバムの重み[0〜100] ; p4=数値 : 再生時間の重み[0〜100] ; ;******************************************************************************* #deffunc PointInMusicList_option_set int p1, int p2, int p3, int p4 Option_WeightTitle=p1 Option_WeightArtsit=p2 Option_WeightAlbum=p3 Option_WeightTime=p4 return ;******************************************************************************* ; 曲情報からデータベース内をあいまい検索。 確からしさ(ポイント)とデータを返す。 ; ; PointInMusicList( p1, p2) ; ; p1=変数 : データベース生データ ; p2=文字列 : "タイトル<>アーティスト<>アルバム<>再生時間(秒)" ; ; 戻り値 : "ポイント<>KEY<>タイトル<>アーティスト<>歌詞サイト<>タイムタグFileName<>wikiURL<>アルバム<>最終更新日時<>再生時間(ミリ秒)<>投稿者<>コメント" ; ;******************************************************************************* #defcfunc PointInMusicList var lists, str _tester // HSPでは速度が出なかったのでLUAに投げる。←それでも数捌くのは時間がかかる(- -; _lm_LuaScript = {" function PointInMusicList(lists,tester,weight) -- test_TAAT=split_as_cgidata(tester) test_titles_num, test_titles = arraysplit(test_TAAT[1]) test_artists_num, test_artists = arraysplit(test_TAAT[2]) test_albums_num, test_albums = arraysplit(test_TAAT[3]) test_titles_strlen = string.len(test_TAAT[1]) test_artists_strlen = string.len(test_TAAT[2]) test_albums_strlen = string.len(test_TAAT[3]) if test_TAAT[4]=="0" then test_TAAT[4]="" end local list_point=0 local max_list_point=0 local max_list_point_list="" for list_key, list_title, list_artist, list_lyricsite, list_tagdata, list_wikipage, list_album, list_update, list_time, list_tagging, list_comment in string.gmatch(lists, "(%d-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>(.-)<>.-<><><><>") do title_point = PointTester( list_title, test_titles, test_titles_num, test_titles_strlen) artist_point = PointTester( list_artist, test_artists, test_artists_num, test_artists_strlen) album_point = PointTester( list_album, test_albums, test_albums_num, test_albums_strlen) time_point = PointTesterTime( list_time, test_TAAT[4]) max_total_point=0 total_point=0 --点数に重み付け if title_point = -1 then --タイトル max_total_point = max_total_point + weight.title total_point = total_point + title_point*weight.title/100 end if artist_point = -1 then --アーティスト max_total_point = max_total_point + weight.artist total_point = total_point + artist_point*weight.artist/100 end if album_point = -1 then --アルバム max_total_point =max_total_point + weight.album total_point = total_point + album_point*weight.album/100 end if time_point = -1 then --再生時間 max_total_point = max_total_point + weight.time total_point = total_point + time_point*weight.time/100 end --すべてのトータル点数算出 list_point = total_point*100/max_total_point if max_list_point < list_point then --最大値のときのデータを記録しておく max_list_point = list_point max_list_point_list = list_key.."<>"..list_title.."<>"..list_artist.."<>"..list_lyricsite.."<>"..list_tagdata.."<>"..list_wikipage.."<>"..list_album.."<>"..list_update.."<>"..list_time.."<>"..list_tagging.."<>"..list_comment end end return "" .. math.floor(max_list_point) .. "<>" .. max_list_point_list end function arraysplit(test) if test=="" then return 0,"" end local count=1 local index=1 local tests={} local wbyte=0 repeat if (129<=string.byte(test,index) and string.byte(test,index)<=159) or (224<=string.byte(test,index) and string.byte(test,index)<=252) then wbyte=1 else wbyte=0 end tests[count] = string.sub(test,index,index+wbyte) index = index + 1+wbyte count = count + 1 until index>string.len(test) return count-1, tests end function PointTester(_plist, ptest, num, strlen_ptest) if num==0 or string.len(_plist)==0 then return -1 end local plist="#$%".._plist.."=|" local pt_maxpoint=0 local pt_point=0 local matcher="" for i=1, num do pt_maxpoint = pt_maxpoint + 3 --3point 123 matcher="" if i == 1 then matcher= matcher .. "#$%" else matcher = matcher .. ptest[i-1] end matcher = matcher .. ptest[i] if i == num then matcher = matcher .. "=|" else matcher = matcher .. ptest[i+1] end --print(matcher) if string.find(plist,matcher,1,1) = nil then pt_point = pt_point+3 else --2point 12 matcher="" if i==1 then matcher = matcher .. "#$%" else matcher = matcher .. ptest[i-1] end matcher = matcher .. ptest[i] if string.find(plist,matcher,1,1) = "" then pt_point = pt_point+2 else --2point 23 matcher="" matcher = matcher .. ptest[i] if i==num then matcher = matcher .. "=|" else matcher = mather .. ptest[i+1] end if string.find(plist,matcher,1,1) = nil then pt_point = pt_point+2 else --1point 2 matcher=ptest[i] if string.find(plist,matcher,1,1) = nil then pt_point = pt_point+1 end end end end end local hstrlen_list = string.len(_plist)/2 local hstrlen_ptest = strlen_ptest/2 if hstrlen_list >= hstrlen_ptest then pt_maxpoint = pt_maxpoint + hstrlen_list pt_point = pt_point + hstrlen_ptest else pt_maxpoint = pt_maxpoint + hstrlen_ptest pt_point = pt_point + hstrlen_list end return pt_point*100/pt_maxpoint end function PointTesterTime( p1, p2 ) if p1=="" or p2=="" or p2=="0" then return -1 end local pt = 100 - ( math.abs( math.floor(p1/1000) - p2/1000 )) --時間の差を取ってミリ秒単位を1秒単位にしてズレてなさをポイントにする if pt < 0 then pt = 0 --100秒以上差があるとマイナスになってるから0点にする end return pt end function split_as_cgidata(line) local result= {} for e in string.gmatch(line.."<>" , "([^<>]*)<>" ) do table.insert(result,e) end return result end "} luaL_newstate // Lua初期化 L = stat luaL_openlibs L //Luaスクリプト読み込み luaL_loadstring L, _lm_LuaScript //空実行して関数を認識させる(?) lua_pcall L, 0, 0, 0 if stat!0 { lua_close L // Lua開放 dialog "lua_pcall()=="+stat+"\nLuaスクリプトの読み込みに失敗しました(1)",1,"歌詞検索" return } //LyricsInfoGet関数をスタックに積む lua_getfield L, LUA_GLOBALSINDEX, "PointInMusicList" //引数をスタックに積む lua_pushstring L, lists lua_pushstring L, _tester ;テーブル lua_newtable L lua_pushstring L, ""+Option_WeightTitle ;value lua_setfield L, -2, "title"; ;key lua_pushstring L, ""+Option_WeightArtsit ;value lua_setfield L, -2, "artist"; ;key lua_pushstring L, ""+Option_WeightAlbum ;value lua_setfield L, -2, "album"; ;key lua_pushstring L, ""+Option_WeightTime ;value lua_setfield L, -2, "time"; ;key //スタック最下層を指定して関数を実行 lua_pcall L, 3, LUA_MULTRET, 0 if stat!0 { lua_close L // Lua開放 dialog "lua_pcall()=="+stat+"\nLuaスクリプトの読み込みに失敗しました(2)",1,"歌詞検索" return } //スタックの要素数(戻り値の数)を取得 lua_gettop L //要素の回数繰り返してスタックを全部読み取り除く //引数を取得 lua_tostring L, -1 //ポインタ先の文字列を文字列変数で表せるようにする(クローン変数) dupptr luarefstr,stat,1,2 //要素のスタック位置で種類を特定 temporary = luarefstr lua_pop L,1 lua_close L // Lua開放 return temporary #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; HTMLソース取得モジュール ; ; comobj47.hsp (HSP-NEXT さくら様作) を改造、モジュール化 ; 改行コード置換モジュール(toCRLF)使用 ;_______________________________________ ;***** URLを指定してhtmlテキストを取得 (comobj47.hsp) ***** #define adTypeBinary 1 #define adSaveCreateNotExist 1 #define adSaveCreateOverWrite 2 #define global Char_Auto -1 #enum global Char_SJIS = 0 #enum global Char_UTF8 #enum global Char_EUC #module GetHTML ;******************************************************************************* ; URLを指定してhtmlテキストを取得 ; ; GetHTMLSource( p1 [,p2 [,p3] ] ) ; ; p1=文字列 : URL ; p2=数値 : 取得先の文字コードID (-1) ; -1 = Char_Auto ; 0 = Char_SJIS ; 1 = Char_UTF8 ; 2 = Char_EUC ; p3=数値 : toCRLF命令で改行コードをCRLFに統一 (0) ; 1 = 実行 ; ; 戻り値 : 取得HTMLソース ; ;******************************************************************************* #define global ctype GetHTMLSource(%1,%2=-1,%3=0) _GetHTMLSource(%1,%2,%3) #defcfunc _GetHTMLSource str _sURL, int CharSetCode, int crlf_flg ReturnHTML="" ;▼URLを指定 sURL = _sURL ;sURL = "http://www.google.com/search?hl=ja&q=%E6%AD%8C%E8%A9%9E+site:http://zyouge444.blog81.fc2.com/&btnG=%E6%A4%9C%E7%B4%A2&aq=f&aqi=&aql=&oq=" ;▼セーブする場合のHTML名 (任意) ;sDest = dirinfo(0)+"\\dsthtml.htm" ;▼CharCodeを指定 switch CharSetCode case Char_SJIS charcode = "Shift_JIS" swbreak case Char_UTF8 charcode = "UTF-8" swbreak case Char_EUC charcode = "EUC-JP" swbreak default charcode = "Shift_JIS" swend ;title sURL newcom objXMLHTTP, "Microsoft.XMLHTTP" objXMLHTTP->"Open" "GET", sURL, 0 objXMLHTTP->"Send" ;▼status OKならHTMLテキストファイルを指定のCharCodeで取得 if objXMLHTTP("status") = 200 { newcom objRS,"ADODB.Stream" if stat!0 : dialog "ADODB.Streamがサポートされていません。",0 : return "" objRS("Type") = 1 objRS->"Open" sHtml=objXMLHTTP("ResponseBody") objRS->"Write" sHtml objRS("Position") = 0 objRS("Type") = 2 objRS("Charset") = charcode ReturnHTML=objRS("ReadText") if CharSetCode=Char_Auto { charset=match(ReturnHTML,"<meta.*charset\\s*=.*?>") charset=replace(charset,"^.*charset\\s*=(.*)$","$1") charcode = "UTF-8" charset=getpath(charset,16) if instr(charset,0,"utf-8")!-1{ charcode = "UTF-8" }else :if instr(charset,0,"euc")!-1{ charcode = "EUC-JP" }else :if instr(charset,0,"shift_jis")!-1{ charcode = "Shift_JIS" } objRS("Position") = 0 objRS("Type") = 2 objRS("Charset") = charcode ReturnHTML=objRS("ReadText") } ;ファイルとして保存する場合 ;objRS->"Savetofile" sDest,adSaveCreateOverWrite objRS->"Close" }else{ dialog "接続に失敗致しました。",0,"エラー" } ;objprm objectID,ReturnHTML if vartype(objRS)==6 { if varuse(objRS)==1 : delcom objRS } delcom objXMLHTTP if crlf_flg = 1 : toCRLF ReturnHTML return ReturnHTML #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; 改行コードCRLF統一モジュール ; ; ;_______________________________________ #module "ReturnCode" ;******************************************************************************* ; 改行コードをCRLF(0x0D 0x0A)に置換 ; ; toCRLF p1 ; ; p1=変数 : 置換する文字列の入った変数 ; ;******************************************************************************* #deffunc toCRLF var sp1 ;改行コードLF(0x0A = \n)を作る lf="@" :poke lf,0,$A ;改行コードCR(0x0D = \r)を作る cr="@" :poke cr,0,$D repeat 3 switch cnt case 0 :a="\n" :b=lf :swbreak ;CR+LF → LF [HSPの\n = \r\n] case 1 :a=cr :b=lf :swbreak ;CR → LF case 2 :a=lf :b="\n" :swbreak ;LF → CR+LF swend i=0 repeat c=instr(sp1,i,a) ;置換え文字検索 if c=-1 :c=cnt :break ;検索されなくなったら終了、検索個数を記憶 i+=c+strlen(a) index(cnt+1)=i ;検索された文字の後ろのindexを記録 loop index(c+1)=strlen(sp1)+strlen(a) ;文字列の最終index+置換え文字サイズを入れる sdim temp,strlen(sp1) +(strlen(b)-strlen(a))*c +1 ;容量を確保(増分考慮) repeat temp+=strmid(sp1,index(cnt),index(cnt+1)-index(cnt)-strlen(a)) ;前の検索位置から次の検索位置までを切り取ってtempにつなげる if cnt=c :break temp+=b ;置き換える文字を置く loop sp1=temp loop return c #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; 曲ファイルから情報取得モジュール ; ; mp3infp_ExportFunc_HSP.hsp 使用 ;_______________________________________ #module GetMusicData #define global title_artist_get(%1="",%2=dummy,%3=dummy,%4=dummy,%5=dummy) _title_artist_get %1,%2,%3,%4,%5 ;******************************************************************************* ; ファイルからタグ情報を取得 ; ; GetMusicInfo p1, p2, p3, p4, p5 ; ; p1=文字列 : 音楽ファイルのファイルパス ; p2=変数 : タイトルが入る ; p3=変数 : アーティストが入る ; p4=変数 : アルバムが入る ; p5=変数 : 再生時間が入る ; ;******************************************************************************* #deffunc GetMusicInfo str f_name, var lm_title, var lm_artist, var lm_album, var lm_time lm_title="" lm_artist="" lm_album="" lm_time="" ;mp3infp title_artist_get f_name,lm_title,lm_artist,lm_album if lm_title="" :lm_title=getpath(f_name,1+8) f_name_=f_name lm_time="" mp3infp_Load hwnd, varptr(f_name_) if stat!-1 { mtime="TIME" mp3infp_GetValue varptr(mtime),varptr(prmm) prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 lm_time=prm_str if instr(lm_time,0," (")!-1 { lm_time = strmid( lm_time,0,instr(lm_time,0," (") ) } } if lm_time="" { mci "open \""+f_name+"\" alias flv type mpegvideo" mci "set flv time format milliseconds" mci "status flv length": sl=stat mci "close all" slm=sl/60/1000 sls=sl/1000-slm*60 lm_time = strf("%d:%02d",slm,sls) } return #deffunc sampling_get_wma str prm0 ,var prm1 prm0_=prm0 mp3infp_Load hwnd,varptr(prm0_) ;曲を読み込む if stat=-1 :return 0 afmt="AFMT" dim prmm mp3infp_GetValue varptr(afmt),varptr(prmm) ;フォーマット情報アドレスを取得 if stat=0 :return 0 prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 prm3=prm_str c=instr(prm3,0,"Hz") ;Hzまで見つけ、そこから逆検索し数値を得る k=0 :suti=0 repeat c,1 code=peek(prm3,c-cnt) if code=107 :k=1 ;k(キロ)を見つけたら覚えておく if code>=48 & code<=57 :suti=1 ;数値フラグ if code=32 & suti=1 :cn=cnt :break ;数値を既に見つけた後の空白で検索をやめる loop prm3=strmid(prm3,c-cn+1,cn-1) ;サンプリングレート(文字列)を取得 prm4="" repeat strlen(prm3) if peek(prm3,cnt)>=48 & peek(prm3,cnt)<=57 :prm4+=strmid(prm3,cnt,1) ;数値だけに直す if peek(prm3,cnt)=46 :dot=cnt loop dosu=0+(dot=1)*(strlen(prm4)-dot) prm1=int(prm4)*(1+(k=1)*999)/(1+(dosu=1)*9)/(1+(dosu=2)*99)/(1+(dosu=3)*999) return 1 #defcfunc syuseti int rate if rate > 46050 { return 9.6; }else { if rate > 38050 { return 9.702; }else { if rate > 28000 { return 9.92; }else { if rate > 23025 { return 9.84; }else { if rate > 19025 { return 9.9225; }else { if rate > 14000 { return 9.92; }else { if rate > 11512 { return 9.96; }else { if rate > 9512 { return 9.9225; }else { return 10.0; } } } } } } } } ; #deffunc _title_artist_get str prm0 ,var prm1 ,var prm2 ,var prm3_, var prm4_ prm0_=prm0 mp3infp_Load hwnd,varptr(prm0_) ;曲を読み込む if stat=-1 :return 0 sdim type,4,4 type(0)="" type(1)="_v1" type(2)="_v2" type(3)="_rmp" mp3infp_GetType if stat=1 { ;MP3 の場合 mp3infp_mp3_GetTagType st=stat repeat 1 if st&2 :st=2 :break ;ID3v2 if st&4 :st=3 :break ;RiffSIF if st&1 :st=1 :break ;ID3v1 st=-1 :break ;タグ用データ領域を持たないMP3 loop }else :st=0 if st=-1 :return 0 afmt="INAM"+type(st);タイトル dim prmm mp3infp_GetValue varptr(afmt),varptr(prmm) ;フォーマット情報アドレスを取得 if stat=0 :return 0 prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 prm1=prm_str afmt="IART"+type(st);アーティスト dim prmm mp3infp_GetValue varptr(afmt),varptr(prmm) ;フォーマット情報アドレスを取得 if stat=0 :return 1 prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 prm2=prm_str afmt="IPRD"+type(st);アルバム dim prmm mp3infp_GetValue varptr(afmt),varptr(prmm) ;フォーマット情報アドレスを取得 if stat=0 :return 1 prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 prm3_=prm_str afmt="TRACK"+type(st);トラック dim prmm mp3infp_GetValue varptr(afmt),varptr(prmm) ;フォーマット情報アドレスを取得 if stat=0 :return 1 prm_str="" dupptr prm_str,prmm,32,2 ;情報を文字列で取得 prm4_=prm_str return 3 #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; 歌詞URLから歌詞を抽出するモジュール ; ; lua-xl.hsp 使用 ; HTMLソース取得モジュール(GetHTMLSource) 使用 ;_______________________________________ #module ;******************************************************************************* ; LUAを利用して、URL指定で歌詞サイトから歌詞を取得・抽出 ; ; GetLyrics( p1, p2 ) ; ; p1=文字列 : URL ; p2=文字列 : 歌詞サイトのHTMLから歌詞を抽出するLUAスクリプト ; 詳細はhttp://w10.oroti.net/timetag/pukiwiki/index.php?LyricsGetScriptあたりを参照 ; ; 戻り値 : 歌詞 ; ;******************************************************************************* #defcfunc GetLyrics str lyricsURL, str _LuaScript LuaScript=_LuaScript //リンクURLからリンク先のHTMLソースを取得 → LuaスクリプトにHTMLをそのまま投げる LuaSendRawDate= GetHTMLSource( lyricsURL ) luaL_newstate // Lua初期化 L = stat luaL_openlibs L luaL_loadstring L, LuaScript //空実行して関数を認識させる(?) lua_pcall L, 0, 0, 0 if stat!0 { lua_close L // Lua開放 dialog "lua_pcall()=="+stat+"\nLuaスクリプトの読み込みに失敗しました(1)",1,"" return } //LyricsInfoGet関数をスタックに積む lua_getfield L, LUA_GLOBALSINDEX, "LyricsInfoGet" //引数をスタックに積む lua_pushstring L, LuaSendRawDate //スタック最下層を指定して関数を実行 lua_pcall L, 1, LUA_MULTRET, 0 if stat!0 { lua_close L // Lua開放 dialog "lua_pcall()=="+stat+"\nLuaスクリプトの読み込みに失敗しました(2)",1,"" return } lyrics="" //スタックの要素数(戻り値の数)を取得 lua_gettop L //要素の回数繰り返してスタックを全部読み取り除く repeat stat //引数を取得 lua_tostring L, -1 //ポインタ先の文字列を文字列変数で表せるようにする(クローン変数) dupptr luarefstr,stat,1,2 ;データタイプ getstr infotype, luarefstr, 0,'=' ;データ内容 infodata = strmid(luarefstr,strsize,strlen(luarefstr)) switch infotype case "LYRICS" lyrics = infodata swbreak case "TITLE" swbreak case "ARTIST" swbreak swend lua_pop L,1 loop lua_close L // Lua開放 return lyrics #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; LyricsMasterのテキストを取得・設定・解析 モジュール ; ; Lyrics Master @ http://www.kenichimaehashi.com/lyricsmaster/ ; RhythmicaLyricsから持ってきてそのまま ; user32.as 使用 ; mod_regexp.as 使用 ;_______________________________________ #module lyricsmastertxt ;******************************************************************************* ; LyricsMasterのリッチエディットの中身を取得 ; ; GetEdit_LyricsMster( p1 ) ; ; p1=数値 : LyricsMasterのウィンドウハンドル ; ; 戻り値 : LyricsMasterのリッチエディットの中身 ; ;******************************************************************************* #defcfunc GetEdit_LyricsMster int lm_hwnd sdim editbox, 64*1024 RE20Wclass="RICHEDIT50W" FindWindowEx lm_hwnd,0,varptr(RE20Wclass),0 RICHEDIT_hWnd = stat if RICHEDIT_hWnd=0 { RE20Wclass="RichEdit20W" FindWindowEx lm_hwnd,0,varptr(RE20Wclass),0 RICHEDIT_hWnd=stat } if RICHEDIT_hWnd!0 { sendmsg RICHEDIT_hWnd,WM_GETTEXT,64*1024,varptr(editbox) } return editbox ;******************************************************************************* ; LyricsMasterのリッチエディットの中身を設定 ; ; GetEdit_LyricsMster p1, p2 ; ; p1=数値 : LyricsMasterのウィンドウハンドル ; p2=文字列 : LyricsMasterのリッチエディットに書き込みたい文字列 ; ;******************************************************************************* #deffunc SetEdit_LyricsMster int lm_hwnd, str edittext editbox = edittext RE20Wclass="RICHEDIT50W" FindWindowEx lm_hwnd,0,varptr(RE20Wclass),0 RICHEDIT_hWnd = stat if RICHEDIT_hWnd=0 { RE20Wclass="RichEdit20W" FindWindowEx lm_hwnd,0,varptr(RE20Wclass),0 RICHEDIT_hWnd=stat } if RICHEDIT_hWnd!0 { sendmsg RICHEDIT_hWnd,WM_SETTEXT,,varptr(editbox) } return ;******************************************************************************* ; LyricsMasterのRichEditから検索した歌詞サイト名(+歌詞サイトからタイトル、アーティスト名)を取得 ; ; LMstringDivide ; ; p1=数値 : ; ;******************************************************************************* #deffunc LMstringDivide var vp1, str sp2, var vp3, var vp4, var vp5, int ip6 i=0 getstr temp,vp1,i :i+=strsize ;1行目 vp3=temp ;タイトル getstr temp,vp1,i :i+=strsize ;2行目 getstr temp,vp1,i :i+=strsize ;3行目 ;// 判断開始 a=strmid(temp,0,4) ;最初の4バイトを取得 if a="Arti" { ;SING365.COM / Absolute Lyrics / Lyrics Search Engine getstr a,temp,0,':' ;頭から':'までを取得 if a="Artist" { vp4=strmid(temp,8,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;4行目 if strmid(temp,0,6)="Album:" { vp5="Lyrics Search Engine" getstr temp,vp1,i :i+=strsize ;5行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if temp="" { vp5="SING365.COM" if ip6=2 && sp2="absolutelyrics" :vp5="Absolute Lyrics" if ip6=2 && sp2="metrolyrics" :vp5="MetroLyrics" vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } } }else :if a="アー" { ;歌詞GET!! / アニカシ vp4=strmid(temp,14,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;4行目 if strmid(temp,0,4)="作詞" { vp5="歌詞GET!!" getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if strmid(temp,0,4)="番組" { vp5="アニカシ" getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 getstr temp,vp1,i :i+=strsize ;7行目 getstr temp,vp1,i :i+=strsize ;8行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } }else :if a="タイ" { ;歌詞GET!! vp5="歌詞GET!!" getstr temp,vp1,i :i+=strsize ;4行目 vp4=strmid(temp,14,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 getstr temp,vp1,i :i+=strsize ;7行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if a="作詞" { getstr temp,vp1,i :i+=strsize ;4行目 if strmid(temp,0,4)!"作曲" :return 0 getstr temp,vp1,i :i+=strsize ;5行目 if strmid(temp,0,4)="編曲" { ;アニメソングの歌詞ならここにおまかせ? getstr temp,vp1,i :i+=strsize ;6行目 if strmid(temp,0,4)!"歌 " :return 0 vp4=strmid(temp,4,1024) ;アーティスト vp5="アニメソングの歌詞ならここにおまかせ?" getstr temp,vp1,i :i+=strsize ;7行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if strmid(temp,0,4)="アー" { ;UtaTen vp4=strmid(temp,14,1024) ;アーティスト vp5="UtaTen" getstr temp,vp1,i :i+=strsize ;6行目 getstr temp,vp1,i :i+=strsize ;7行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if strmid(temp,0,4)="唄 " { vp4=strmid(temp,4,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 if sp2="yahoo" { vp5="Yahoo!ミュージック" return 1 }else :if sp2="kashinavi" { vp5="歌詞ナビ" return 1 } }else :if strmid(temp,0,4)="歌 " { ;USEN総合チャート vp4=strmid(temp,4,1024) ;アーティスト vp5="USEN総合チャート" getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } }else :if a="歌手" { ;歌ネット / 歌詞タイム vp4=strmid(temp,6,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;4行目 getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 if strmid(temp,0,4)="編曲" { vp5="歌詞タイム" getstr temp,vp1,i :i+=strsize ;7行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if temp="" { vp5="歌ネット" vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } }else :if a="唄 " { ;うたまっぷ か Yahoo!ミュージック vp4=strmid(temp,4,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;4行目 getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 if ip6=2 { ;バージョン2は必ず vp5="うたまっぷ" return 1 }else { ;バージョン1 vp5="うたまっぷ" ;1ではとりあえずうたまっぷ if sp2="yahoo" :vp5="Yahoo!ミュージック" return 1 } return 0 }else :if a="歌 " { ;イベスタ歌詞とる / Listen Japan / カラオケ用「歌詞」のページ vp4=strmid(temp,4,1024) ;アーティスト getstr temp,vp1,i :i+=strsize ;4行目 if strmid(temp,0,4)="作詞" { ;イベスタ歌詞とる if sp2="evesta" { vp5="イベスタ" getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if sp2="listenjapan" { vp5="Listen Japan" getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } }else :if strmid(temp,0,4)="詞 " { vp5="J-Total Music" getstr temp,vp1,i :i+=strsize ;5行目 getstr temp,vp1,i :i+=strsize ;6行目 getstr temp,vp1,i :i+=strsize ;7行目 vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 }else :if strmid(temp,0,4)="" { ;カラオケ用「歌詞」のページ vp5="カラオケ用「歌詞」のページ" vp1=strmid(vp1,i,strlen.vp1) ;歌詞のみ化 return 1 } } return 0 ;******************************************************************************* ; LyricsMasterの設定ファイル内容を取得 ; ; LoadLMpreferences p1 ; ; p1=数値 : オプション ; p1 = 1 : 連続取得に最適化する ; ; 戻り値 : LyricsMasterの設定ファイル内容 ; ;******************************************************************************* #defcfunc LoadLMpreferences int opt //LyricsMasterの設定ファイルをロード preferences_lyricsmaster = "" exist dirinfo($1001A)+"\\preferences.lyricsmaster" if strsize = -1 :return "" notesel preferences_lyricsmaster noteload dirinfo($1001A)+"\\preferences.lyricsmaster" noteunsel preferences_lyricsmaster_b = preferences_lyricsmaster if opt=1 { ;連続取得に最適化するように設定変更 preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_autoDetect\tFalse", "search_autoDetect\tTrue") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_autoSelectMaxRank\tFalse", "search_autoSelectMaxRank\tTrue") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useUtamap\tTrue", "search_useUtamap\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useKashiGet\tTrue", "search_useKashiGet\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useUtanet\tTrue", "search_useUtanet\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useLyricsSearchEngine\tTrue", "search_useLyricsSearchEngine\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useSing365com\tTrue", "search_useSing365com\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useAslse\tTrue", "search_useAslse\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useExtraEngine\tTrue", "search_useExtraEngine\tFalse") preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useJoysound\tTrue", "search_useJoysound\tFalse") } return preferences_lyricsmaster ;******************************************************************************* ; LyricsMasterの設定ファイルを保存 ; ; SaveLMpreferences p1 ; ; p1=文字列 : オプション ; p1 = "" : 連続取得に最適化する ; ; 戻り値 : LyricsMasterの設定ファイル内容 ; ;******************************************************************************* #deffunc SaveLMpreferences str savetxt preferences_lyricsmaster = savetxt ;savetxt=""のとき、最後にロードしたものがあればそれで保存してもとに戻す if savetxt = "" { if vartype(preferences_lyricsmaster_b)=2 { ;最後にロードした設定 preferences_lyricsmaster = preferences_lyricsmaster_b }else { ;ロードしたものがなくて文字列が空なら何もしない return 0 } } //LyricsMasterの設定ファイルを保存 notesel preferences_lyricsmaster notesave dirinfo($1001A)+"\\preferences.lyricsmaster" noteunsel return 1 ;******************************************************************************* ; LyricsMasterの設定ファイルを最後にロードしたときの状態に戻して保存するマクロ ; ; SaveLMpreferences_LastLoad ; ;******************************************************************************* #define global SaveLMpreferences_LastLoad SaveLMpreferences "" ;******************************************************************************* ; LyricsMasterの設定ファイルテキストを特定の歌詞サイトから検索するように変更する ; ; ReplaceSearchSiteLMpreferences p1 ; ; p1=文字列 : LyricsMaster設定ファイルテキスト ; p2=文字列 : 歌詞サイト名 ; ; 戻り値 : 変更されたLyricsMasterの設定ファイル内容 ; ;******************************************************************************* #defcfunc ReplaceSearchSiteLMpreferences str savetxt, str sitetxt preferences_lyricsmaster = savetxt ;savetxt=""のとき、最後にロードしたものがあればそれで保存してもとに戻す if savetxt = "" { if vartype(preferences_lyricsmaster_b)=2 { ;最後にロードした設定 preferences_lyricsmaster = preferences_lyricsmaster_b }else { ;ロードしたものがなくて文字列が空なら何もしない return 0 } } if sitetxt= "うたまっぷ" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useUtamap\tFalse", "search_useUtamap\tTrue") }else : if sitetxt="歌詞GET!!" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useKashiGet\tFalse", "search_useKashiGet\tTrue") }else : if sitetxt="歌ネット" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useUtanet\tFalse", "search_useUtanet\tTrue") }else : if sitetxt="アニメソングの歌詞ならここにおまかせ?" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useAslse\tFalse", "search_useAslse\tTrue") }else : if sitetxt="SING365.COM" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useSing365com\tFalse", "search_useSing365com\tTrue") }else : if sitetxt="Lyrics Search Engine" { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useLyricsSearchEngine\tFalse", "search_useLyricsSearchEngine\tTrue") }else { preferences_lyricsmaster = replace(preferences_lyricsmaster, "search_useExtraEngine\tFalse", "search_useExtraEngine\tTrue") } return preferences_lyricsmaster #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; タイムタグ付き歌詞生成 モジュール ; ; タイムタグ情報について @ http://w10.oroti.net/timetag/infoofdb.html ; RhythmicaLyricsから持ってきてそのまま ;_______________________________________ #module TimetagLyrics ;//2バイト文字判定 #define ctype wbyte(%1) ( (( (129<=%1)&(%1<=159) )||( (224<=%1)&(%1<=252) )) ) ;******************************************************************************* ; 歌詞とタイムタグ情報からタイムタグ付き歌詞を生成 ; ; ApplyTimetagData( p1, p2 ) ; ; p1=文字列 : 歌詞 ; p2=文字列 : タイムタグ情報 ; ; 戻り値 : タイムタグ付き歌詞 ; ;******************************************************************************* #defcfunc ApplyTimetagData str kasi_, var data kasi=kasi_ tekiyo="" di=0 :ki=0 repeat getstr temp_data, data, di :di+=strsize if strsize=0 { ;歌詞が残ってたら if ki<strlen(kasi) :tekiyo+="\n"+strmid(kasi,ki,strlen(kasi)) break } if cnt>0 :tekiyo+="\n" if peek(temp_data,0)='@' :tekiyo+=temp_data :continue getstr temp_kasi, kasi, ki :ki+=strsize t_data_index=0 t_kasi_index=0 mojisu="" repeat strlen(temp_data) if 48<=peek(temp_data,cnt) && peek(temp_data,cnt)<=57 { ;0〜9なら文字数として積んでいく mojisu+=strmid(temp_data,cnt,1) continue }else { ;数字じゃない if mojisu!"" { ;既にmojisuに格納されていたら、文字数ぶん歌詞を拾っていく repeat int(mojisu) if t_kasi_index>=strlen(temp_kasi) :break i=wbyte(peek(temp_kasi,t_kasi_index))+1 tekiyo+=strmid(temp_kasi,t_kasi_index,i) t_kasi_index+=i loop mojisu="" } ;この先タイムタグかどうか i=tagkana(temp_data,cnt) if i>0 { tekiyo+=strmid(temp_data,cnt,i+1) continue cnt+i+1 } ;それ以外。ホントはここまで来ないんだけど一応。そのまま格納していく i=wbyte(peek(temp_data,cnt))+1 tekiyo+=strmid(temp_data,cnt,i) continue cnt+i } loop ;もし歌詞が1行分消費してなかったら残りを末尾にくっつける if t_kasi_index<strlen(temp_kasi) :tekiyo+=strmid(temp_kasi,t_kasi_index,strlen(temp_kasi)) loop return tekiyo ;タイムタグか確認 #defcfunc tagkana var sp1, int index temp=strmid(sp1,index+0,1) :if temp="" :return 0 :else :if peek(temp,0)!'[' :return 0 temp=strmid(sp1,index+1,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+2,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+3,1) :if temp="" :return 0 :else :if peek(temp,0)!':' :return 0 temp=strmid(sp1,index+4,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+5,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+6,1) :if temp="" :return 0 if peek(temp,0)=']' :return 6 if peek(temp,0)!':' && peek(temp,0)!'.' :return 0 flametime=(peek(temp,0)='.') temp=strmid(sp1,index+7,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+8,1) :if temp="" :return 0 :else :if peek(temp,0)<48|57<peek(temp,0) :return 0 temp=strmid(sp1,index+9,1) :if temp="" :return 0 :else :if peek(temp,0)!']' :return 0 if flametime { poke sp1, index+6, ':' if op_save_dot@=0 { op_save_dot@=2 :op_save_dot2@=2 if is_gsel_create(5) { selg=ginfo_sel gsel 5 objprm id_op_save_dot@,1 gsel selg } } }else { } return 9 #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; ツールチップ モジュール ; ; ;_______________________________________ #module "tooltip" ;// ツールチップ初期化 #deffunc tipset_init winobj "tooltips_class32","",0,3 ;,400,400,0,0 htooltip(tip_id)=objinfo(stat,2) dim RECT,4 ;▼comctl32.dllのバージョンが4.70以降で有効 ; ↓ RECT=3,3,3,3 SendMsg htooltip,TTM_SETMARGIN,0,varptr(RECT) ;マージン SendMsg htooltip,TTM_SETMAXTIPWIDTH,0,500 ;tipwidth SendMsg htooltip,TTM_SETDELAYTIME,2,30000 ;表示時間 return ;// ツールチップセット #deffunc tipset int _ObjID, str _temp Objh=objinfo_hwnd(_ObjID) temp=_temp GetClientRect Objh, varptr(RECT) dim TOOLINFO,11 ;TOOLINFO構造体 TOOLINFO(0) = 40, $10, Objh, 0, RECT.0, RECT.1, RECT.2, RECT.3, 0, varptr(temp) SendMsg htooltip,TTM_ADDTOOL,0,varptr(TOOLINFO) return #global ; ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ; ダイアログボックス関連 モジュール ; ; HSP module & macro Library(stdlib)exdialog.as (HSP-NEXT さくら様作) から抜粋、モジュール化 ;_______________________________________ #module exdlg ;******************************************************************************* ; フォルダ選択ダイアログ (foldlg) ; ; 戻り値 : 成功 stat=0, refstr=選択フォルダ名,失敗, stat=1 ; ; ・書式 foldlg dlgtitle,deffolder,nOption ; ・引数 dlgtitle (str) : ダイアログタイトル名 (省略可) ; deffolder (str) : 初期フォルダ名 ; nOption (int) : 0,1,$400(0) スタイルオプション値 ; ・タイプ モジュール命令 ; ;-- (NOTE) --------------------------------------------------------------------- ; ; (使用例) ; foldlg "",exedir,0 ; dialog refstr,0 ;******************************************************************************* #deffunc foldlg str prm1,str prm2,int prm3 mref ref,65 ls=strlen(prm1) dlgtitle = prm1 if ls==0 : dlgtitle="フォルダを選択して下さい" sdim deffolder,MAX_PATH deffolder = prm2 if strlen(deffolder)==0 : deffolder=exedir nOption = prm3 ;(0,1,$4000) if (nOption!0)|(nOption!1)|(nOption!$4000) : nOption=0 dim browsinfo,64 : sdim retbuf,MAX_PATH browsinfo(0) = hwnd browsinfo(3) = varptr(dlgtitle) browsinfo(4) = nOption ;BrowseCallback ;初期フォルダ指定可能 ; if deffolder!="" { dim brproc, 9 browsinfo(5)=varptr(brproc) : browsinfo(6)=varptr(deffolder) p=varptr(SendMessage) brproc = $08247C83, $90177501, $102474FF, $6668016A, $FF000004 brproc(5) = $B8102474, p, $C031D0FF, $000010C2 } SHBrowseForFolder varptr(browsinfo) : pidl=stat SHGetPathFromIDList pidl,varptr(retbuf) ;: pidl=stat CoTaskMemFree pidl ref=retbuf : ls=strlen(retbuf) if ls==0 : ret=1 : else : ret=0 dim browsinfo,0 : sdim retbuf,0 : sdim deffolder,0 return ret #global