--- Title: Pytube とwxでダウンローダーを作る 190530 Author: yamasyuh68 Web: 'https://mimemo.io/m/8agmD4pk70lRjYz' --- ## Pytube とwxでダウンローダーを作る - ずっとやってみたかった。調べたら簡単そうだったので早速作ってみた https://live.staticflickr.com/65535/47964993051_37450d433e_z.jpg ``` import wx ,io ,sys ,re from pytube import YouTube import YouTube_ui class MyFrame( YouTube_ui.MyFrame1 ): def __init__( self, parent ): YouTube_ui.MyFrame1.__init__( self, parent ) # self.m_textCtrl1.SetValue(<< url >>) # self.m_textCtrl2.SetValue(<< pass >>) def btn_go( self, event ): url=self.m_textCtrl1.GetValue() yt=YouTube(url) for list in yt.streams.all(): with io.StringIO() as f: sys.stdout = f print(list) text = f.getvalue() self.m_listBox1.Append(text) sys.stdout = sys.__stdout__ def listbox_select(self,e): str=e.GetEventObject().GetStringSelection() # get text num=re.search('[0-9]+' , str) self.m_textCtrl3.SetValue(num.group(0)) def btn_bye( self, event ): quit() def btn_download( self, event ): YouTube( self.m_textCtrl1.GetValue() ).streams.get_by_itag( \ self.m_textCtrl3.GetValue() ).download( self.m_textCtrl2.GetValue() ) if __name__ == '__main__': app = wx.App(False) frame = MyFrame(None) frame.Show(True) app.MainLoop() ``` - `pytube` は `pip`で落とした。すぐだった、軽そう。 - UIは`wxFormBuilder`で作る。簡単で良いです - コードは解説サイト見ながらだけどすごく簡単 **しかし、大きな落とし穴が・・・・** `yt.streams.all()` をforで回せば落とせるタイプのリストが一行ずつ取得できるんだけど、これは`Stream`になっていて、GUIでは表示できない **というか、表示の方法がわからない┐('д')┌** - `print`するのは簡単なんだけど、GUIで表示するには`text`にしなければならず、その方法がわからない いろいろやってみたけど昨日は出来なくて、とりあえずで、`print`の出力を`text`に変換して表示したのがこのコードです `print`は指定しなければ標準出力に出力される、コンソールね。あらかじめ出力先をテキストストリームにしておいて、そこから`getvalue`すればテキストで取得できるって事です 普段デバッグを含めて多用している`print`だけど、ものすごい実力を持ってるんだなあといつも思います - `ListBox`のアイテムをクリックしたら文字列からIDを取得して下の`textctrl`に表示する。`download`で指定したフォルダにダウンロードします # 課題など - 実際に使ってみたら、**ダウンロード中はGUIが固まってました** pytubeはダウンロード完了まで制御を戻してくれないんだね 別スレッドにしたら制御自体は戻ると思うけど、逆にそうなるといつダウンロードが完了したのかわかりづらくなりますな - 普通はダウンロードの進捗状況を何らかの形で表示すべきだよな 複数ダウンロードも可能にすべき 私は興味があっていじってみたけど多分このツールは使わないと思うのでそこまではやる予定は無し( ´∀`) prog