summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJeffrey C. Ollie <jeff@ocjtech.us>2008-08-19 19:34:21 -0500
committerJeffrey C. Ollie <jeff@ocjtech.us>2008-08-19 19:34:21 -0500
commitcfc058e6ecd9d7e132d5ccf4600ead1f0641ddc9 (patch)
tree5d9d4756703d8e640a60188abd818b74d5e0cca9
parentad0fe53806ab5da2ead4a790af22f47e4ea2e713 (diff)
downloadnohgooee-cfc058e6ecd9d7e132d5ccf4600ead1f0641ddc9.tar.gz
nohgooee-cfc058e6ecd9d7e132d5ccf4600ead1f0641ddc9.tar.xz
nohgooee-cfc058e6ecd9d7e132d5ccf4600ead1f0641ddc9.zip
Some renames.
-rw-r--r--NohGooee/BeautifulSupe.py (renamed from BitTorrent/BeautifulSupe.py)0
-rw-r--r--NohGooee/Choker.py (renamed from BitTorrent/Choker.py)0
-rw-r--r--NohGooee/ClientIdentifier.py (renamed from BitTorrent/ClientIdentifier.py)0
-rw-r--r--NohGooee/Connecter.py (renamed from BitTorrent/Connecter.py)4
-rw-r--r--NohGooee/ConvertedMetainfo.py (renamed from BitTorrent/ConvertedMetainfo.py)6
-rw-r--r--NohGooee/CurrentRateMeasure.py (renamed from BitTorrent/CurrentRateMeasure.py)2
-rw-r--r--NohGooee/Desktop.py (renamed from BitTorrent/Desktop.py)2
-rw-r--r--NohGooee/Downloader.py (renamed from BitTorrent/Downloader.py)6
-rw-r--r--NohGooee/DownloaderFeedback.py (renamed from BitTorrent/DownloaderFeedback.py)0
-rw-r--r--NohGooee/Encoder.py (renamed from BitTorrent/Encoder.py)12
-rw-r--r--NohGooee/GUI.py (renamed from BitTorrent/GUI.py)6
-rw-r--r--NohGooee/GetTorrent.py (renamed from BitTorrent/GetTorrent.py)2
-rw-r--r--NohGooee/IPC.py (renamed from BitTorrent/IPC.py)6
-rw-r--r--NohGooee/LaunchPath.py (renamed from BitTorrent/LaunchPath.py)0
-rw-r--r--NohGooee/NatCheck.py (renamed from BitTorrent/NatCheck.py)0
-rw-r--r--NohGooee/NatTraversal.py (renamed from BitTorrent/NatTraversal.py)10
-rw-r--r--NohGooee/NewVersion.py (renamed from BitTorrent/NewVersion.py)10
-rw-r--r--NohGooee/PeerID.py (renamed from BitTorrent/PeerID.py)2
-rw-r--r--NohGooee/PiecePicker.py (renamed from BitTorrent/PiecePicker.py)0
-rw-r--r--NohGooee/RateLimiter.py (renamed from BitTorrent/RateLimiter.py)2
-rw-r--r--NohGooee/RateMeasure.py (renamed from BitTorrent/RateMeasure.py)2
-rw-r--r--NohGooee/Rerequester.py (renamed from BitTorrent/Rerequester.py)12
-rw-r--r--NohGooee/StatusLight.py (renamed from BitTorrent/StatusLight.py)2
-rw-r--r--NohGooee/Storage.py (renamed from BitTorrent/Storage.py)2
-rw-r--r--NohGooee/StorageWrapper.py (renamed from BitTorrent/StorageWrapper.py)4
-rw-r--r--NohGooee/TorrentQueue.py (renamed from BitTorrent/TorrentQueue.py)18
-rw-r--r--NohGooee/TrayIcon.py (renamed from BitTorrent/TrayIcon.py)8
-rw-r--r--NohGooee/Uploader.py (renamed from BitTorrent/Uploader.py)2
-rw-r--r--NohGooee/__init__.py (renamed from BitTorrent/__init__.py)6
-rw-r--r--NohGooee/bencode.py (renamed from BitTorrent/bencode.py)2
-rw-r--r--NohGooee/bitfield.py (renamed from BitTorrent/bitfield.py)0
-rw-r--r--NohGooee/btformats.py (renamed from BitTorrent/btformats.py)2
-rw-r--r--NohGooee/configfile.py (renamed from BitTorrent/configfile.py)10
-rw-r--r--NohGooee/defaultargs.py (renamed from BitTorrent/defaultargs.py)4
-rw-r--r--NohGooee/defer.py (renamed from BitTorrent/defer.py)0
-rw-r--r--NohGooee/download.py (renamed from BitTorrent/download.py)46
-rw-r--r--NohGooee/language.py (renamed from BitTorrent/language.py)0
-rw-r--r--NohGooee/launchmanycore.py (renamed from BitTorrent/launchmanycore.py)10
-rw-r--r--NohGooee/makemetafile.py (renamed from BitTorrent/makemetafile.py)8
-rw-r--r--NohGooee/parseargs.py (renamed from BitTorrent/parseargs.py)10
-rw-r--r--NohGooee/parsedir.py (renamed from BitTorrent/parsedir.py)4
-rw-r--r--NohGooee/platform.py (renamed from BitTorrent/platform.py)4
-rw-r--r--NohGooee/prefs.py (renamed from BitTorrent/prefs.py)0
-rw-r--r--NohGooee/selectpoll.py (renamed from BitTorrent/selectpoll.py)0
-rw-r--r--NohGooee/track.py (renamed from BitTorrent/track.py)12
-rw-r--r--NohGooee/zurllib.py (renamed from BitTorrent/zurllib.py)2
l---------bittorrent1
l---------bittorrent-console1
-rwxr-xr-xbittorrent-console.py308
l---------bittorrent-curses1
-rwxr-xr-xbittorrent-curses.py449
l---------bittorrent-tracker1
-rw-r--r--bittorrent.desktop11
-rw-r--r--bittorrent.pngbin1729 -> 0 bytes
-rwxr-xr-xbittorrent.py3834
l---------changetracker-console1
-rw-r--r--images/bittorrent.icobin13902 -> 0 bytes
-rw-r--r--images/icons/default/abort.pngbin3856 -> 0 bytes
-rw-r--r--images/icons/default/broken.pngbin3827 -> 0 bytes
-rw-r--r--images/icons/default/finished.pngbin3885 -> 0 bytes
-rw-r--r--images/icons/default/info.pngbin3824 -> 0 bytes
-rw-r--r--images/icons/default/pause.pngbin3137 -> 0 bytes
-rw-r--r--images/icons/default/paused.pngbin3230 -> 0 bytes
-rw-r--r--images/icons/default/play.pngbin3465 -> 0 bytes
-rw-r--r--images/icons/default/queued.pngbin4285 -> 0 bytes
-rw-r--r--images/icons/default/remove.pngbin3916 -> 0 bytes
-rw-r--r--images/icons/default/running.pngbin3472 -> 0 bytes
-rw-r--r--images/icons/default/status-broken.pngbin3179 -> 0 bytes
-rw-r--r--images/icons/default/status-natted.pngbin3286 -> 0 bytes
-rw-r--r--images/icons/default/status-pre-natted.pngbin3316 -> 0 bytes
-rw-r--r--images/icons/default/status-running.pngbin3433 -> 0 bytes
-rw-r--r--images/icons/default/status-starting.pngbin3226 -> 0 bytes
-rw-r--r--images/icons/default/status-stopped.pngbin3101 -> 0 bytes
-rw-r--r--images/icons/default/trashcan.pngbin3321 -> 0 bytes
-rw-r--r--images/icons/old/broken.pngbin1046 -> 0 bytes
-rw-r--r--images/icons/old/finished.pngbin1076 -> 0 bytes
-rw-r--r--images/icons/old/info.pngbin1162 -> 0 bytes
-rw-r--r--images/icons/old/pause.pngbin450 -> 0 bytes
-rw-r--r--images/icons/old/paused.pngbin1668 -> 0 bytes
-rw-r--r--images/icons/old/play.pngbin759 -> 0 bytes
-rw-r--r--images/icons/old/queued.pngbin1650 -> 0 bytes
-rw-r--r--images/icons/old/remove.pngbin315 -> 0 bytes
-rw-r--r--images/icons/old/running.pngbin799 -> 0 bytes
-rw-r--r--images/icons/old/status-broken.pngbin821 -> 0 bytes
-rw-r--r--images/icons/old/status-natted.pngbin762 -> 0 bytes
-rw-r--r--images/icons/old/status-pre-natted.pngbin767 -> 0 bytes
-rw-r--r--images/icons/old/status-running.pngbin653 -> 0 bytes
-rw-r--r--images/icons/old/status-starting.pngbin811 -> 0 bytes
-rw-r--r--images/icons/old/status-stopped.pngbin821 -> 0 bytes
-rw-r--r--images/logo/bittorrent_32.pngbin4326 -> 0 bytes
-rw-r--r--images/logo/bittorrent_96.pngbin19020 -> 0 bytes
-rw-r--r--khashmir/KRateLimiter.py4
-rw-r--r--khashmir/actions.py2
-rw-r--r--khashmir/cache.py2
-rw-r--r--khashmir/inserter.py4
-rw-r--r--khashmir/khashmir.py10
-rw-r--r--khashmir/knode.py2
-rw-r--r--khashmir/krpc.py8
-rw-r--r--khashmir/kstore.py2
-rw-r--r--khashmir/ktable.py2
-rw-r--r--khashmir/node.py2
-rw-r--r--khashmir/test_khashmir.py2
-rw-r--r--khashmir/test_krpc.py2
-rw-r--r--khashmir/test_kstore.py2
-rw-r--r--khashmir/unet.py4
-rw-r--r--language_codes.py4
l---------launchmany-console1
l---------launchmany-curses1
-rwxr-xr-xlaunchmany-curses.py301
l---------maketorrent1
l---------maketorrent-console1
-rwxr-xr-xmaketorrent.py577
-rwxr-xr-xnohgooee-changetracker (renamed from changetracker-console.py)4
-rwxr-xr-xnohgooee-maketorrent (renamed from maketorrent-console.py)12
-rwxr-xr-xnohgooee-seed (renamed from launchmany-console.py)14
-rwxr-xr-xnohgooee-seed.init (renamed from btseed.init)0
-rwxr-xr-xnohgooee-torrentinfo (renamed from torrentinfo-console.py)6
-rwxr-xr-xnohgooee-tracker.init (renamed from bttrack.init)0
-rwxr-xr-xnohgooee-tracker.tac (renamed from bittorrent-tracker.py)4
-rw-r--r--redirdonate.html1
-rw-r--r--setup.py6
-rw-r--r--test/test_ClientIdentifier.py2
l---------torrentinfo-console1
123 files changed, 170 insertions, 5661 deletions
diff --git a/BitTorrent/BeautifulSupe.py b/NohGooee/BeautifulSupe.py
index 79072d4..79072d4 100644
--- a/BitTorrent/BeautifulSupe.py
+++ b/NohGooee/BeautifulSupe.py
diff --git a/BitTorrent/Choker.py b/NohGooee/Choker.py
index ed3d500..ed3d500 100644
--- a/BitTorrent/Choker.py
+++ b/NohGooee/Choker.py
diff --git a/BitTorrent/ClientIdentifier.py b/NohGooee/ClientIdentifier.py
index cec2fa5..cec2fa5 100644
--- a/BitTorrent/ClientIdentifier.py
+++ b/NohGooee/ClientIdentifier.py
diff --git a/BitTorrent/Connecter.py b/NohGooee/Connecter.py
index 5fc3add..830fd82 100644
--- a/BitTorrent/Connecter.py
+++ b/NohGooee/Connecter.py
@@ -13,8 +13,8 @@
from binascii import b2a_hex
from struct import pack, unpack
-from BitTorrent.RawServer_magic import Handler
-from BitTorrent.bitfield import Bitfield
+from NohGooee.RawServer_magic import Handler
+from NohGooee.bitfield import Bitfield
def toint(s):
return unpack("!i", s)[0]
diff --git a/BitTorrent/ConvertedMetainfo.py b/NohGooee/ConvertedMetainfo.py
index 0e22205..9b2459f 100644
--- a/BitTorrent/ConvertedMetainfo.py
+++ b/NohGooee/ConvertedMetainfo.py
@@ -14,9 +14,9 @@ import os
import sys
from sha import sha
-from BitTorrent.bencode import bencode
-from BitTorrent import btformats
-from BitTorrent import BTFailure, WARNING, ERROR
+from NohGooee.bencode import bencode
+from NohGooee import btformats
+from NohGooee import BTFailure, WARNING, ERROR
WINDOWS_UNSUPPORTED_CHARS ='"*/:<>?\|'
diff --git a/BitTorrent/CurrentRateMeasure.py b/NohGooee/CurrentRateMeasure.py
index 3dd940f..86e16da 100644
--- a/BitTorrent/CurrentRateMeasure.py
+++ b/NohGooee/CurrentRateMeasure.py
@@ -10,7 +10,7 @@
# Written by Bram Cohen
-from BitTorrent.platform import bttime
+from NohGooee.platform import bttime
class Measure(object):
diff --git a/BitTorrent/Desktop.py b/NohGooee/Desktop.py
index b724811..e8955c3 100644
--- a/BitTorrent/Desktop.py
+++ b/NohGooee/Desktop.py
@@ -13,7 +13,7 @@
import os
import sys
-from BitTorrent.platform import get_home_dir, get_shell_dir
+from NohGooee.platform import get_home_dir, get_shell_dir
if os.name == 'nt':
from win32com.shell import shellcon
diff --git a/BitTorrent/Downloader.py b/NohGooee/Downloader.py
index accb332..ca5f973 100644
--- a/BitTorrent/Downloader.py
+++ b/NohGooee/Downloader.py
@@ -12,9 +12,9 @@
from random import shuffle
-from BitTorrent.platform import bttime
-from BitTorrent.CurrentRateMeasure import Measure
-from BitTorrent.bitfield import Bitfield
+from NohGooee.platform import bttime
+from NohGooee.CurrentRateMeasure import Measure
+from NohGooee.bitfield import Bitfield
class PerIPStats(object):
diff --git a/BitTorrent/DownloaderFeedback.py b/NohGooee/DownloaderFeedback.py
index 6c16c90..6c16c90 100644
--- a/BitTorrent/DownloaderFeedback.py
+++ b/NohGooee/DownloaderFeedback.py
diff --git a/BitTorrent/Encoder.py b/NohGooee/Encoder.py
index a5bd6dc..8675823 100644
--- a/BitTorrent/Encoder.py
+++ b/NohGooee/Encoder.py
@@ -12,12 +12,12 @@
from socket import error as socketerror
-from BitTorrent import BTFailure
-from BitTorrent.RawServer_magic import Handler
-from BitTorrent.NatTraversal import UPNPError
-from BitTorrent.Connecter import Connection
-from BitTorrent.platform import is_frozen_exe
-from BitTorrent.ClientIdentifier import identify_client
+from NohGooee import BTFailure
+from NohGooee.RawServer_magic import Handler
+from NohGooee.NatTraversal import UPNPError
+from NohGooee.Connecter import Connection
+from NohGooee.platform import is_frozen_exe
+from NohGooee.ClientIdentifier import identify_client
# header, reserved, download id, my id, [length, message]
diff --git a/BitTorrent/GUI.py b/NohGooee/GUI.py
index 0497367..a4a677c 100644
--- a/BitTorrent/GUI.py
+++ b/NohGooee/GUI.py
@@ -21,8 +21,8 @@ import threading
assert gtk.gtk_version >= (2, 6), _( "GTK %s or newer required") % '2.6'
assert gtk.pygtk_version >= (2, 6), _("PyGTK %s or newer required") % '2.6'
-from BitTorrent import app_name, FAQ_URL, languages, language_names
-from BitTorrent.platform import image_root, read_language_file, write_language_file
+from NohGooee import app_name, FAQ_URL, languages, language_names
+from NohGooee.platform import image_root, read_language_file, write_language_file
def lock_wrap(function, *args):
gtk.gdk.threads_enter()
@@ -451,7 +451,7 @@ class FileSelection(IconMixin, gtk.FileChooserDialog):
buttons=(gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
gtk.STOCK_OK, gtk.RESPONSE_OK))
IconMixin.__init__(self)
- from BitTorrent.ConvertedMetainfo import filesystem_encoding
+ from NohGooee.ConvertedMetainfo import filesystem_encoding
self.fsenc = filesystem_encoding
try:
fullname.decode('utf8')
diff --git a/BitTorrent/GetTorrent.py b/NohGooee/GetTorrent.py
index a69651c..dcbcb50 100644
--- a/BitTorrent/GetTorrent.py
+++ b/NohGooee/GetTorrent.py
@@ -17,7 +17,7 @@ import os
import re
import zurllib
from bencode import bdecode
-from BitTorrent.platform import get_cache_dir
+from NohGooee.platform import get_cache_dir
urlpat = re.compile('^\w+://')
urlpat_torrent = re.compile('^torrent://')
diff --git a/BitTorrent/IPC.py b/NohGooee/IPC.py
index de50434..11d910b 100644
--- a/BitTorrent/IPC.py
+++ b/NohGooee/IPC.py
@@ -25,9 +25,9 @@ if os.name == 'nt':
from binascii import b2a_hex
-from BitTorrent.RawServer_magic import RawServer, Handler
-from BitTorrent.platform import get_home_dir, get_config_dir
-from BitTorrent import INFO, WARNING, ERROR, CRITICAL, BTFailure, app_name
+from NohGooee.RawServer_magic import RawServer, Handler
+from NohGooee.platform import get_home_dir, get_config_dir
+from NohGooee import INFO, WARNING, ERROR, CRITICAL, BTFailure, app_name
def toint(s):
return int(b2a_hex(s), 16)
diff --git a/BitTorrent/LaunchPath.py b/NohGooee/LaunchPath.py
index 3c78845..3c78845 100644
--- a/BitTorrent/LaunchPath.py
+++ b/NohGooee/LaunchPath.py
diff --git a/BitTorrent/NatCheck.py b/NohGooee/NatCheck.py
index fe59a15..fe59a15 100644
--- a/BitTorrent/NatCheck.py
+++ b/NohGooee/NatCheck.py
diff --git a/BitTorrent/NatTraversal.py b/NohGooee/NatTraversal.py
index 30eb377..a6c96e3 100644
--- a/BitTorrent/NatTraversal.py
+++ b/NohGooee/NatTraversal.py
@@ -26,11 +26,11 @@ except NameError:
# python 2.2
pass
-from BitTorrent import app_name, defer
-from BitTorrent import INFO, WARNING, ERROR
-from BitTorrent.platform import os_version
-from BitTorrent.RawServer_magic import RawServer, Handler
-from BitTorrent.BeautifulSupe import BeautifulSupe, Tag
+from NohGooee import app_name, defer
+from NohGooee import INFO, WARNING, ERROR
+from NohGooee.platform import os_version
+from NohGooee.RawServer_magic import RawServer, Handler
+from NohGooee.BeautifulSupe import BeautifulSupe, Tag
from urllib2 import URLError, HTTPError, Request
#bleh
diff --git a/BitTorrent/NewVersion.py b/NohGooee/NewVersion.py
index 25445ae..96ed2f5 100644
--- a/BitTorrent/NewVersion.py
+++ b/NohGooee/NewVersion.py
@@ -19,11 +19,11 @@ from sha import sha
DEBUG = False
-from BitTorrent import ERROR, WARNING, BTFailure, version, app_name
-from BitTorrent import GetTorrent
-from BitTorrent.bencode import bdecode, bencode
-from BitTorrent.platform import os_version, spawn, get_temp_dir, doc_root, is_frozen_exe, osx
-from BitTorrent.ConvertedMetainfo import ConvertedMetainfo
+from NohGooee import ERROR, WARNING, BTFailure, version, app_name
+from NohGooee import GetTorrent
+from NohGooee.bencode import bdecode, bencode
+from NohGooee.platform import os_version, spawn, get_temp_dir, doc_root, is_frozen_exe, osx
+from NohGooee.ConvertedMetainfo import ConvertedMetainfo
if osx:
from Foundation import NSAutoreleasePool
diff --git a/BitTorrent/PeerID.py b/NohGooee/PeerID.py
index 9dc9285..d116abe 100644
--- a/BitTorrent/PeerID.py
+++ b/NohGooee/PeerID.py
@@ -19,7 +19,7 @@ except AttributeError:
def getpid():
return 1
-from BitTorrent import version
+from NohGooee import version
def make_id():
myid = 'M' + version.split()[0].replace('.', '-')
diff --git a/BitTorrent/PiecePicker.py b/NohGooee/PiecePicker.py
index e22b13a..e22b13a 100644
--- a/BitTorrent/PiecePicker.py
+++ b/NohGooee/PiecePicker.py
diff --git a/BitTorrent/RateLimiter.py b/NohGooee/RateLimiter.py
index d58f2c4..12d3205 100644
--- a/BitTorrent/RateLimiter.py
+++ b/NohGooee/RateLimiter.py
@@ -10,7 +10,7 @@
# Written by Uoti Urpala and Andrew Loewenstern
-from BitTorrent.platform import bttime
+from NohGooee.platform import bttime
def minctx(a,b):
A = B = 0
diff --git a/BitTorrent/RateMeasure.py b/NohGooee/RateMeasure.py
index b609330..e5101ff 100644
--- a/BitTorrent/RateMeasure.py
+++ b/NohGooee/RateMeasure.py
@@ -10,7 +10,7 @@
# Written by Bram Cohen
-from BitTorrent.platform import bttime
+from NohGooee.platform import bttime
class RateMeasure(object):
diff --git a/BitTorrent/Rerequester.py b/NohGooee/Rerequester.py
index 93d9472..b899ca9 100644
--- a/BitTorrent/Rerequester.py
+++ b/NohGooee/Rerequester.py
@@ -15,12 +15,12 @@ from socket import error, gethostbyname
from random import random, randrange
from binascii import b2a_hex
-from BitTorrent import version
-from BitTorrent.platform import bttime
-from BitTorrent.zurllib import urlopen, quote, Request
-from BitTorrent.btformats import check_peers
-from BitTorrent.bencode import bencode, bdecode
-from BitTorrent import BTFailure, INFO, WARNING, ERROR, CRITICAL
+from NohGooee import version
+from NohGooee.platform import bttime
+from NohGooee.zurllib import urlopen, quote, Request
+from NohGooee.btformats import check_peers
+from NohGooee.bencode import bencode, bdecode
+from NohGooee import BTFailure, INFO, WARNING, ERROR, CRITICAL
class Rerequester(object):
diff --git a/BitTorrent/StatusLight.py b/NohGooee/StatusLight.py
index 11cbf14..e1668e4 100644
--- a/BitTorrent/StatusLight.py
+++ b/NohGooee/StatusLight.py
@@ -1,4 +1,4 @@
-from BitTorrent.platform import bttime
+from NohGooee.platform import bttime
class StatusLight(object):
diff --git a/BitTorrent/Storage.py b/NohGooee/Storage.py
index 8f1d6fb..7a766bd 100644
--- a/BitTorrent/Storage.py
+++ b/NohGooee/Storage.py
@@ -14,7 +14,7 @@ import os
from bisect import bisect_right
from array import array
-from BitTorrent import BTFailure, app_name
+from NohGooee import BTFailure, app_name
class FilePool(object):
diff --git a/BitTorrent/StorageWrapper.py b/NohGooee/StorageWrapper.py
index ac14fdd..7955f95 100644
--- a/BitTorrent/StorageWrapper.py
+++ b/NohGooee/StorageWrapper.py
@@ -16,8 +16,8 @@ from sha import sha
from array import array
from binascii import b2a_hex
-from BitTorrent.bitfield import Bitfield
-from BitTorrent import BTFailure, INFO, WARNING, ERROR, CRITICAL
+from NohGooee.bitfield import Bitfield
+from NohGooee import BTFailure, INFO, WARNING, ERROR, CRITICAL
def toint(s):
return int(b2a_hex(s), 16)
diff --git a/BitTorrent/TorrentQueue.py b/NohGooee/TorrentQueue.py
index 4187a80..bf369be 100644
--- a/BitTorrent/TorrentQueue.py
+++ b/NohGooee/TorrentQueue.py
@@ -18,15 +18,15 @@ import threading
import traceback
-from BitTorrent import GetTorrent
-from BitTorrent.platform import bttime
-from BitTorrent.download import Feedback, Multitorrent
-from BitTorrent.bencode import bdecode
-from BitTorrent.ConvertedMetainfo import ConvertedMetainfo
-from BitTorrent.prefs import Preferences
-from BitTorrent import BTFailure, BTShutdown, INFO, WARNING, ERROR, CRITICAL
-from BitTorrent import configfile
-from BitTorrent import FAQ_URL
+from NohGooee import GetTorrent
+from NohGooee.platform import bttime
+from NohGooee.download import Feedback, Multitorrent
+from NohGooee.bencode import bdecode
+from NohGooee.ConvertedMetainfo import ConvertedMetainfo
+from NohGooee.prefs import Preferences
+from NohGooee import BTFailure, BTShutdown, INFO, WARNING, ERROR, CRITICAL
+from NohGooee import configfile
+from NohGooee import FAQ_URL
import BitTorrent
diff --git a/BitTorrent/TrayIcon.py b/NohGooee/TrayIcon.py
index ac7620d..d48dd2e 100644
--- a/BitTorrent/TrayIcon.py
+++ b/NohGooee/TrayIcon.py
@@ -1,8 +1,8 @@
import os
-from BitTorrent import app_name
-from BitTorrent.GUI import gtk_wrap
-from BitTorrent.platform import image_root
+from NohGooee import app_name
+from NohGooee.GUI import gtk_wrap
+from NohGooee.platform import image_root
if os.name == 'nt':
from systray import systray
@@ -86,7 +86,7 @@ else:
if __name__ == '__main__':
import threading
- from BitTorrent.platform import install_translation
+ from NohGooee.platform import install_translation
install_translation()
ti = TrayIcon(True)
th = threading.Thread(target=ti.enable, args=())
diff --git a/BitTorrent/Uploader.py b/NohGooee/Uploader.py
index d02bfa8..ce98949 100644
--- a/BitTorrent/Uploader.py
+++ b/NohGooee/Uploader.py
@@ -10,7 +10,7 @@
# Written by Bram Cohen
-from BitTorrent.CurrentRateMeasure import Measure
+from NohGooee.CurrentRateMeasure import Measure
class Upload(object):
diff --git a/BitTorrent/__init__.py b/NohGooee/__init__.py
index cae9c77..5dc8996 100644
--- a/BitTorrent/__init__.py
+++ b/NohGooee/__init__.py
@@ -21,12 +21,12 @@ branch = None
if os.access('.cdv', os.F_OK):
branch = os.path.split(os.path.realpath(os.path.split(sys.argv[0])[0]))[1]
-from BitTorrent.language import languages, language_names
-from BitTorrent.platform import get_home_dir, is_frozen_exe
+from NohGooee.language import languages, language_names
+from NohGooee.platform import get_home_dir, is_frozen_exe
if os.name == 'posix':
if os.uname()[0] == "Darwin":
- from BitTorrent.platform import install_translation
+ from NohGooee.platform import install_translation
install_translation()
del sys, get_home_dir, is_frozen_exe
diff --git a/BitTorrent/bencode.py b/NohGooee/bencode.py
index 2fcdeb8..f544286 100644
--- a/BitTorrent/bencode.py
+++ b/NohGooee/bencode.py
@@ -10,7 +10,7 @@
# Written by Petru Paler
-from BitTorrent import BTFailure
+from NohGooee import BTFailure
def decode_int(x, f):
f += 1
diff --git a/BitTorrent/bitfield.py b/NohGooee/bitfield.py
index bede74f..bede74f 100644
--- a/BitTorrent/bitfield.py
+++ b/NohGooee/bitfield.py
diff --git a/BitTorrent/btformats.py b/NohGooee/btformats.py
index 97e62df..632fe27 100644
--- a/BitTorrent/btformats.py
+++ b/NohGooee/btformats.py
@@ -12,7 +12,7 @@
import re
-from BitTorrent import BTFailure
+from NohGooee import BTFailure
allowed_path_re = re.compile(r'^[^/\\.~][^/\\]*$')
diff --git a/BitTorrent/configfile.py b/NohGooee/configfile.py
index 6f4a1e3..49c4e4f 100644
--- a/BitTorrent/configfile.py
+++ b/NohGooee/configfile.py
@@ -22,11 +22,11 @@ except ImportError:
from ConfigParser import ConfigParser as RawConfigParser
from ConfigParser import MissingSectionHeaderError, ParsingError
-from BitTorrent import parseargs
-from BitTorrent import app_name, version, ERROR, BTFailure
-from BitTorrent.platform import get_config_dir, locale_root, is_frozen_exe
-from BitTorrent.defaultargs import MYTRUE
-from BitTorrent.zurllib import bind_tracker_connection, set_zurllib_rawserver
+from NohGooee import parseargs
+from NohGooee import app_name, version, ERROR, BTFailure
+from NohGooee.platform import get_config_dir, locale_root, is_frozen_exe
+from NohGooee.defaultargs import MYTRUE
+from NohGooee.zurllib import bind_tracker_connection, set_zurllib_rawserver
MAIN_CONFIG_FILE = 'ui_config'
TORRENT_CONFIG_FILE = 'torrent_config'
diff --git a/BitTorrent/defaultargs.py b/NohGooee/defaultargs.py
index 2c7af5c..dc9583a 100644
--- a/BitTorrent/defaultargs.py
+++ b/NohGooee/defaultargs.py
@@ -36,12 +36,12 @@ if os.name == 'posix':
MIN_INCOMPLETE = 100
if os.name == 'nt':
- from BitTorrent.platform import win_version_num
+ from NohGooee.platform import win_version_num
# starting in XP SP2 the incomplete outgoing connection limit was set to 10
if win_version_num >= (2, 5, 1, 2, 0):
MIN_INCOMPLETE = 10
-from BitTorrent import languages
+from NohGooee import languages
basic_options = [
('data_dir', '',
diff --git a/BitTorrent/defer.py b/NohGooee/defer.py
index 4531271..4531271 100644
--- a/BitTorrent/defer.py
+++ b/NohGooee/defer.py
diff --git a/BitTorrent/download.py b/NohGooee/download.py
index d17b685..e3248c4 100644
--- a/BitTorrent/download.py
+++ b/NohGooee/download.py
@@ -25,29 +25,29 @@ from cStringIO import StringIO
from traceback import print_exc
from math import sqrt
-from BitTorrent.btformats import check_message
-from BitTorrent.Choker import Choker
-from BitTorrent.Storage import Storage, FilePool
-from BitTorrent.StorageWrapper import StorageWrapper
-from BitTorrent.Uploader import Upload
-from BitTorrent.Downloader import Downloader
-from BitTorrent.Encoder import Encoder, SingleportListener
-from BitTorrent.zurllib import set_zurllib_rawserver, add_unsafe_thread
-from BitTorrent import PeerID
-
-from BitTorrent.RateLimiter import MultiRateLimiter as RateLimiter
-from BitTorrent.RateLimiter import RateLimitedGroup
-
-from BitTorrent.RawServer_magic import RawServer
-from BitTorrent.NatTraversal import NatTraverser
-from BitTorrent.Rerequester import Rerequester, DHTRerequester
-from BitTorrent.DownloaderFeedback import DownloaderFeedback
-from BitTorrent.RateMeasure import RateMeasure
-from BitTorrent.CurrentRateMeasure import Measure
-from BitTorrent.PiecePicker import PiecePicker
-from BitTorrent.ConvertedMetainfo import set_filesystem_encoding
-from BitTorrent import version
-from BitTorrent import BTFailure, BTShutdown, INFO, WARNING, ERROR, CRITICAL
+from NohGooee.btformats import check_message
+from NohGooee.Choker import Choker
+from NohGooee.Storage import Storage, FilePool
+from NohGooee.StorageWrapper import StorageWrapper
+from NohGooee.Uploader import Upload
+from NohGooee.Downloader import Downloader
+from NohGooee.Encoder import Encoder, SingleportListener
+from NohGooee.zurllib import set_zurllib_rawserver, add_unsafe_thread
+from NohGooee import PeerID
+
+from NohGooee.RateLimiter import MultiRateLimiter as RateLimiter
+from NohGooee.RateLimiter import RateLimitedGroup
+
+from NohGooee.RawServer_magic import RawServer
+from NohGooee.NatTraversal import NatTraverser
+from NohGooee.Rerequester import Rerequester, DHTRerequester
+from NohGooee.DownloaderFeedback import DownloaderFeedback
+from NohGooee.RateMeasure import RateMeasure
+from NohGooee.CurrentRateMeasure import Measure
+from NohGooee.PiecePicker import PiecePicker
+from NohGooee.ConvertedMetainfo import set_filesystem_encoding
+from NohGooee import version
+from NohGooee import BTFailure, BTShutdown, INFO, WARNING, ERROR, CRITICAL
from khashmir.utkhashmir import UTKhashmir
from khashmir import const
diff --git a/BitTorrent/language.py b/NohGooee/language.py
index f7f72ef..f7f72ef 100644
--- a/BitTorrent/language.py
+++ b/NohGooee/language.py
diff --git a/BitTorrent/launchmanycore.py b/NohGooee/launchmanycore.py
index 955f88a..bf83fea 100644
--- a/BitTorrent/launchmanycore.py
+++ b/NohGooee/launchmanycore.py
@@ -15,11 +15,11 @@ import os
from cStringIO import StringIO
from traceback import print_exc
-from BitTorrent import configfile
-from BitTorrent.parsedir import parsedir
-from BitTorrent.download import Multitorrent, Feedback
-from BitTorrent.ConvertedMetainfo import ConvertedMetainfo
-from BitTorrent import BTFailure
+from NohGooee import configfile
+from NohGooee.parsedir import parsedir
+from NohGooee.download import Multitorrent, Feedback
+from NohGooee.ConvertedMetainfo import ConvertedMetainfo
+from NohGooee import BTFailure
from threading import Event
from time import time
diff --git a/BitTorrent/makemetafile.py b/NohGooee/makemetafile.py
index 798f325..ccd721d 100644
--- a/BitTorrent/makemetafile.py
+++ b/NohGooee/makemetafile.py
@@ -18,10 +18,10 @@ from sha import sha
from time import time
from threading import Event
-from BitTorrent.bencode import bencode, bdecode
-from BitTorrent.btformats import check_info
-from BitTorrent.parseargs import parseargs, printHelp
-from BitTorrent import BTFailure
+from NohGooee.bencode import bencode, bdecode
+from NohGooee.btformats import check_info
+from NohGooee.parseargs import parseargs, printHelp
+from NohGooee import BTFailure
from khashmir.node import Node
from khashmir.ktable import KTable
diff --git a/BitTorrent/parseargs.py b/NohGooee/parseargs.py
index bd38558..e2f773a 100644
--- a/BitTorrent/parseargs.py
+++ b/NohGooee/parseargs.py
@@ -13,10 +13,10 @@
from types import *
from cStringIO import StringIO
-from BitTorrent.defaultargs import MyBool, MYTRUE
-from BitTorrent import BTFailure
-from BitTorrent.bencode import bdecode
-from BitTorrent.platform import is_frozen_exe
+from NohGooee.defaultargs import MyBool, MYTRUE
+from NohGooee import BTFailure
+from NohGooee.bencode import bdecode
+from NohGooee.platform import is_frozen_exe
def makeHelp(uiname, defaults):
ret = ''
@@ -37,7 +37,7 @@ def makeHelp(uiname, defaults):
def printHelp(uiname, defaults):
if uiname in ('bittorrent','maketorrent') and is_frozen_exe:
- from BitTorrent.GUI import HelpWindow
+ from NohGooee.GUI import HelpWindow
HelpWindow(None, makeHelp(uiname, defaults))
else:
print makeHelp(uiname, defaults)
diff --git a/BitTorrent/parsedir.py b/NohGooee/parsedir.py
index 3b86a03..2ffe1c2 100644
--- a/BitTorrent/parsedir.py
+++ b/NohGooee/parsedir.py
@@ -13,8 +13,8 @@
import os
from sha import sha
-from BitTorrent.bencode import bencode, bdecode
-from BitTorrent.btformats import check_message
+from NohGooee.bencode import bencode, bdecode
+from NohGooee.btformats import check_message
NOISY = False
diff --git a/BitTorrent/platform.py b/NohGooee/platform.py
index 8435397..4749fd3 100644
--- a/BitTorrent/platform.py
+++ b/NohGooee/platform.py
@@ -33,8 +33,8 @@ elif os.name == 'posix' and os.uname()[0] == 'Darwin':
except ImportError:
pass
-from BitTorrent import app_name, version
-from BitTorrent.language import locale_sucks
+from NohGooee import app_name, version
+from NohGooee.language import locale_sucks
if sys.platform.startswith('win'):
bttime = time.clock
diff --git a/BitTorrent/prefs.py b/NohGooee/prefs.py
index 37177c2..37177c2 100644
--- a/BitTorrent/prefs.py
+++ b/NohGooee/prefs.py
diff --git a/BitTorrent/selectpoll.py b/NohGooee/selectpoll.py
index d01f1ef..d01f1ef 100644
--- a/BitTorrent/selectpoll.py
+++ b/NohGooee/selectpoll.py
diff --git a/BitTorrent/track.py b/NohGooee/track.py
index fe4788f..ee1fe5e 100644
--- a/BitTorrent/track.py
+++ b/NohGooee/track.py
@@ -22,12 +22,12 @@ from twisted.web.resource import Resource
from twisted.internet import reactor
from twisted.python import log
-from BitTorrent.parseargs import parseargs, formatDefinitions
-from BitTorrent.parsedir import parsedir
-from BitTorrent.NatCheck import NatCheck
-from BitTorrent.bencode import bencode, bdecode, Bencached
-from BitTorrent.zurllib import quote, unquote
-from BitTorrent import version
+from NohGooee.parseargs import parseargs, formatDefinitions
+from NohGooee.parsedir import parsedir
+from NohGooee.NatCheck import NatCheck
+from NohGooee.bencode import bencode, bdecode, Bencached
+from NohGooee.zurllib import quote, unquote
+from NohGooee import version
defaults = [
diff --git a/BitTorrent/zurllib.py b/NohGooee/zurllib.py
index 8bbe5ba..399118f 100644
--- a/BitTorrent/zurllib.py
+++ b/NohGooee/zurllib.py
@@ -13,7 +13,7 @@ import sys
import threading
import thread
-from BitTorrent import PeerID
+from NohGooee import PeerID
user_agent = PeerID.make_id()
del PeerID
diff --git a/bittorrent b/bittorrent
deleted file mode 120000
index 7ca3c4e..0000000
--- a/bittorrent
+++ /dev/null
@@ -1 +0,0 @@
-bittorrent.py \ No newline at end of file
diff --git a/bittorrent-console b/bittorrent-console
deleted file mode 120000
index 054110d..0000000
--- a/bittorrent-console
+++ /dev/null
@@ -1 +0,0 @@
-bittorrent-console.py \ No newline at end of file
diff --git a/bittorrent-console.py b/bittorrent-console.py
deleted file mode 100755
index e5ec115..0000000
--- a/bittorrent-console.py
+++ /dev/null
@@ -1,308 +0,0 @@
-#!/usr/bin/env python
-
-# The contents of this file are subject to the BitTorrent Open Source License
-# Version 1.1 (the License). You may not copy or use this file, in either
-# source code or executable form, except in compliance with the License. You
-# may obtain a copy of the License at http://www.bittorrent.com/license/.
-#
-# Software distributed under the License is distributed on an AS IS basis,
-# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
-# for the specific language governing rights and limitations under the
-# License.
-
-# Written by Bram Cohen, Uoti Urpala and John Hoffman
-
-from __future__ import division
-
-from BitTorrent.platform import install_translation
-install_translation()
-
-import sys
-import os
-import threading
-from time import time, strftime
-from cStringIO import StringIO
-
-from BitTorrent.download import Feedback, Multitorrent
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.parseargs import printHelp
-from BitTorrent.zurllib import urlopen
-from BitTorrent.bencode import bdecode
-from BitTorrent.ConvertedMetainfo import ConvertedMetainfo
-from BitTorrent.prefs import Preferences
-from BitTorrent import configfile
-from BitTorrent import BTFailure
-from BitTorrent import version
-from BitTorrent import GetTorrent
-
-
-def fmttime(n):
- if n == 0:
- return _("download complete!")
- try:
- n = int(n)
- assert n >= 0 and n < 5184000 # 60 days
- except:
- return _("<unknown>")
- m, s = divmod(n, 60)
- h, m = divmod(m, 60)
- return _("finishing in %d:%02d:%02d") % (h, m, s)
-
-def fmtsize(n):
- s = str(n)
- size = s[-3:]
- while len(s) > 3:
- s = s[:-3]
- size = '%s,%s' % (s[-3:], size)
- if n > 999:
- unit = ['B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB', 'EiB', 'ZiB', 'YiB']
- i = 1
- while i + 1 < len(unit) and (n >> 10) >= 999:
- i += 1
- n >>= 10
- n /= (1 << 10)
- size = '%s (%.0f %s)' % (size, n, unit[i])
- return size
-
-
-class HeadlessDisplayer(object):
-
- def __init__(self, doneflag):
- self.doneflag = doneflag
-
- self.done = False
- self.percentDone = ''
- self.timeEst = ''
- self.downRate = '---'
- self.upRate = '---'
- self.shareRating = ''
- self.seedStatus = ''
- self.peerStatus = ''
- self.errors = []
- self.file = ''
- self.downloadTo = ''
- self.fileSize = ''
- self.numpieces = 0
-
- def set_torrent_values(self, name, path, size, numpieces):
- self.file = name
- self.downloadTo = path
- self.fileSize = fmtsize(size)
- self.numpieces = numpieces
-
- def finished(self):
- self.done = True
- self.downRate = '---'
- self.display({'activity':_("download succeeded"), 'fractionDone':1})
-
- def error(self, errormsg):
- newerrmsg = strftime('[%H:%M:%S] ') + errormsg
- self.errors.append(newerrmsg)
- self.display({})
-
- def display(self, statistics):
- fractionDone = statistics.get('fractionDone')
- activity = statistics.get('activity')
- timeEst = statistics.get('timeEst')
- downRate = statistics.get('downRate')
- upRate = statistics.get('upRate')
- spew = statistics.get('spew')
-
- print '\n\n\n\n'
- if spew is not None:
- self.print_spew(spew)
-
- if timeEst is not None:
- self.timeEst = fmttime(timeEst)
- elif activity is not None:
- self.timeEst = activity
-
- if fractionDone is not None:
- self.percentDone = str(int(fractionDone * 1000) / 10)
- if downRate is not None:
- self.downRate = '%.1f KB/s' % (downRate / (1 << 10))
- if upRate is not None:
- self.upRate = '%.1f KB/s' % (upRate / (1 << 10))
- downTotal = statistics.get('downTotal')
- if downTotal is not None:
- upTotal = statistics['upTotal']
- if downTotal <= upTotal / 100:
- self.shareRating = _("oo (%.1f MB up / %.1f MB down)") % (
- upTotal / (1<<20), downTotal / (1<<20))
- else:
- self.shareRating = _("%.3f (%.1f MB up / %.1f MB down)") % (
- upTotal / downTotal, upTotal / (1<<20), downTotal / (1<<20))
- numCopies = statistics['numCopies']
- nextCopies = ', '.join(["%d:%.1f%%" % (a,int(b*1000)/10) for a,b in
- zip(xrange(numCopies+1, 1000), statistics['numCopyList'])])
- if not self.done:
- self.seedStatus = _("%d seen now, plus %d distributed copies "
- "(%s)") % (statistics['numSeeds' ],
- statistics['numCopies'],
- nextCopies)
- else:
- self.seedStatus = _("%d distributed copies (next: %s)") % (
- statistics['numCopies'], nextCopies)
- self.peerStatus = _("%d seen now") % statistics['numPeers']
-
- for err in self.errors[-4:]:
- print _("ERROR:\n") + err + '\n'
- print _("saving: "), self.file
- print _("file size: "), self.fileSize
- print _("percent done: "), self.percentDone
- print _("time left: "), self.timeEst
- print _("download to: "), self.downloadTo
- print _("download rate: "), self.downRate
- print _("upload rate: "), self.upRate
- print _("share rating: "), self.shareRating
- print _("seed status: "), self.seedStatus
- print _("peer status: "), self.peerStatus
-
- def print_spew(self, spew):
- s = StringIO()
- s.write('\n\n\n')
- for c in spew:
- s.write('%20s ' % c['ip'])
- if c['initiation'] == 'L':
- s.write('l')
- else:
- s.write('r')
- total, rate, interested, choked = c['upload']
- s.write(' %10s %10s ' % (str(int(total/10485.76)/100),
- str(int(rate))))
- if c['is_optimistic_unchoke']:
- s.write('*')
- else:
- s.write(' ')
- if interested:
- s.write('i')
- else:
- s.write(' ')
- if choked:
- s.write('c')
- else:
- s.write(' ')
-
- total, rate, interested, choked, snubbed = c['download']
- s.write(' %10s %10s ' % (str(int(total/10485.76)/100),
- str(int(rate))))
- if interested:
- s.write('i')
- else:
- s.write(' ')
- if choked:
- s.write('c')
- else:
- s.write(' ')
- if snubbed:
- s.write('s')
- else:
- s.write(' ')
- s.write('\n')
- print s.getvalue()
-
-
-class DL(Feedback):
-
- def __init__(self, metainfo, config):
- self.doneflag = threading.Event()
- self.metainfo = metainfo
- self.config = Preferences().initWithDict(config)
-
- def run(self):
- self.d = HeadlessDisplayer(self.doneflag)
- try:
- self.multitorrent = Multitorrent(self.config, self.doneflag,
- self.global_error)
- # raises BTFailure if bad
- metainfo = ConvertedMetainfo(bdecode(self.metainfo))
- torrent_name = metainfo.name_fs
- if config['save_as']:
- if config['save_in']:
- raise BTFailure(_("You cannot specify both --save_as and "
- "--save_in"))
- saveas = config['save_as']
- elif config['save_in']:
- saveas = os.path.join(config['save_in'], torrent_name)
- else:
- saveas = torrent_name
-
- self.d.set_torrent_values(metainfo.name, os.path.abspath(saveas),
- metainfo.total_bytes, len(metainfo.hashes))
- self.torrent = self.multitorrent.start_torrent(metainfo,
- Preferences(self.config), self, saveas)
- except BTFailure, e:
- print str(e)
- return
- self.get_status()
- self.multitorrent.rawserver.install_sigint_handler()
- self.multitorrent.rawserver.listen_forever()
- self.d.display({'activity':_("shutting down"), 'fractionDone':0})
- self.torrent.shutdown()
-
- def reread_config(self):
- try:
- newvalues = configfile.get_config(self.config, 'bittorrent-console')
- except Exception, e:
- self.d.error(_("Error reading config: ") + str(e))
- return
- self.config.update(newvalues)
- # The set_option call can potentially trigger something that kills
- # the torrent (when writing this the only possibility is a change in
- # max_files_open causing an IOError while closing files), and so
- # the self.failed() callback can run during this loop.
- for option, value in newvalues.iteritems():
- self.multitorrent.set_option(option, value)
- for option, value in newvalues.iteritems():
- self.torrent.set_option(option, value)
-
- def get_status(self):
- self.multitorrent.rawserver.add_task(self.get_status,
- self.config['display_interval'])
- status = self.torrent.get_status(self.config['spew'])
- self.d.display(status)
-
- def global_error(self, level, text):
- self.d.error(text)
-
- def error(self, torrent, level, text):
- self.d.error(text)
-
- def failed(self, torrent, is_external):
- self.doneflag.set()
-
- def finished(self, torrent):
- self.d.finished()
-
-
-if __name__ == '__main__':
- uiname = 'bittorrent-console'
- defaults = get_defaults(uiname)
-
- metainfo = None
- if len(sys.argv) <= 1:
- printHelp(uiname, defaults)
- sys.exit(1)
- try:
- config, args = configfile.parse_configuration_and_args(defaults,
- uiname, sys.argv[1:], 0, 1)
-
- torrentfile = None
- if len(args):
- torrentfile = args[0]
- for opt in ('responsefile', 'url'):
- if config[opt]:
- print '"--%s"' % opt, _("deprecated, do not use")
- torrentfile = config[opt]
- if torrentfile is not None:
- metainfo, errors = GetTorrent.get(torrentfile)
- if errors:
- raise BTFailure(_("Error reading .torrent file: ") + '\n'.join(errors))
- else:
- raise BTFailure(_("you must specify a .torrent file"))
- except BTFailure, e:
- print str(e)
- sys.exit(1)
-
- dl = DL(metainfo, config)
- dl.run()
diff --git a/bittorrent-curses b/bittorrent-curses
deleted file mode 120000
index e6ea9be..0000000
--- a/bittorrent-curses
+++ /dev/null
@@ -1 +0,0 @@
-bittorrent-curses.py \ No newline at end of file
diff --git a/bittorrent-curses.py b/bittorrent-curses.py
deleted file mode 100755
index f5d906f..0000000
--- a/bittorrent-curses.py
+++ /dev/null
@@ -1,449 +0,0 @@
-#!/usr/bin/env python
-
-# The contents of this file are subject to the BitTorrent Open Source License
-# Version 1.1 (the License). You may not copy or use this file, in either
-# source code or executable form, except in compliance with the License. You
-# may obtain a copy of the License at http://www.bittorrent.com/license/.
-#
-# Software distributed under the License is distributed on an AS IS basis,
-# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
-# for the specific language governing rights and limitations under the
-# License.
-
-# Original version written by Henry 'Pi' James, modified by (at least)
-# John Hoffman and Uoti Urpala
-
-from __future__ import division
-
-from BitTorrent.platform import install_translation
-install_translation()
-
-SPEW_SCROLL_RATE = 1
-
-import sys
-import os
-import threading
-from time import time, strftime
-
-from BitTorrent.download import Feedback, Multitorrent
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.parseargs import printHelp
-from BitTorrent.zurllib import urlopen
-from BitTorrent.bencode import bdecode
-from BitTorrent.ConvertedMetainfo import ConvertedMetainfo
-from BitTorrent.prefs import Preferences
-from BitTorrent import configfile
-from BitTorrent import BTFailure
-from BitTorrent import version
-from BitTorrent import GetTorrent
-
-
-try:
- curses = import_curses()
- import curses.panel
- from curses.wrapper import wrapper as curses_wrapper
- from signal import signal, SIGWINCH
-except:
- print _("Textmode GUI initialization failed, cannot proceed.")
- print
- print _("This download interface requires the standard Python module "
- "\"curses\", which is unfortunately not available for the native "
- "Windows port of Python. It is however available for the Cygwin "
- "port of Python, running on all Win32 systems (www.cygwin.com).")
- print
- print _('You may still use "bittorrent-console" to download.')
- sys.exit(1)
-
-def fmttime(n):
- if n == 0:
- return _("download complete!")
- try:
- n = int(n)
- assert n >= 0 and n < 5184000 # 60 days
- except:
- return _("<unknown>")
- m, s = divmod(n, 60)
- h, m = divmod(m, 60)
- return _("finishing in %d:%02d:%02d") % (h, m, s)
-
-def fmtsize(n):
- s = str(n)
- size = s[-3:]
- while len(s) > 3:
- s = s[:-3]
- size = '%s,%s' % (s[-3:], size)
- if n > 999:
- unit = ['B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB', 'EiB', 'ZiB', 'YiB']
- i = 1
- while i + 1 < len(unit) and (n >> 10) >= 999:
- i += 1
- n >>= 10
- n /= (1 << 10)
- size = '%s (%.0f %s)' % (size, n, unit[i])
- return size
-
-
-class CursesDisplayer(object):
-
- def __init__(self, scrwin, errlist, doneflag, reread_config, ulrate):
- self.scrwin = scrwin
- self.errlist = errlist
- self.doneflag = doneflag
-
- signal(SIGWINCH, self.winch_handler)
- self.changeflag = threading.Event()
-
- self.done = False
- self.reread_config = reread_config
- self.ulrate = ulrate
- self.activity = ''
- self.status = ''
- self.progress = ''
- self.downRate = '---'
- self.upRate = '---'
- self.shareRating = ''
- self.seedStatus = ''
- self.peerStatus = ''
- self.errors = []
- self.file = ''
- self.downloadTo = ''
- self.fileSize = ''
- self.numpieces = 0
- self.spew_scroll_time = 0
- self.spew_scroll_pos = 0
-
- self._remake_window()
- curses.use_default_colors()
-
- def set_torrent_values(self, name, path, size, numpieces):
- self.file = name
- self.downloadTo = path
- self.fileSize = fmtsize(size)
- self.numpieces = numpieces
- self._remake_window()
-
- def winch_handler(self, signum, stackframe):
- self.changeflag.set()
- curses.endwin()
- self.scrwin.refresh()
- self.scrwin = curses.newwin(0, 0, 0, 0)
- self._remake_window()
-
- def _remake_window(self):
- self.scrh, self.scrw = self.scrwin.getmaxyx()
- self.scrpan = curses.panel.new_panel(self.scrwin)
- self.labelh, self.labelw, self.labely, self.labelx = 11, 9, 1, 2
- self.labelwin = curses.newwin(self.labelh, self.labelw,
- self.labely, self.labelx)
- self.labelpan = curses.panel.new_panel(self.labelwin)
- self.fieldh, self.fieldw, self.fieldy, self.fieldx = (
- self.labelh, self.scrw-2 - self.labelw-3,
- 1, self.labelw+3)
- self.fieldwin = curses.newwin(self.fieldh, self.fieldw,
- self.fieldy, self.fieldx)
- self.fieldwin.nodelay(1)
- self.fieldpan = curses.panel.new_panel(self.fieldwin)
- self.spewh, self.speww, self.spewy, self.spewx = (
- self.scrh - self.labelh - 2, self.scrw - 3, 1 + self.labelh, 2)
- self.spewwin = curses.newwin(self.spewh, self.speww,
- self.spewy, self.spewx)
- self.spewpan = curses.panel.new_panel(self.spewwin)
- try:
- self.scrwin.border(ord('|'),ord('|'),ord('-'),ord('-'),ord(' '),ord(' '),ord(' '),ord(' '))
- except:
- pass
- self.labelwin.addstr(0, 0, _("file:"))
- self.labelwin.addstr(1, 0, _("size:"))
- self.labelwin.addstr(2, 0, _("dest:"))
- self.labelwin.addstr(3, 0, _("progress:"))
- self.labelwin.addstr(4, 0, _("status:"))
- self.labelwin.addstr(5, 0, _("dl speed:"))
- self.labelwin.addstr(6, 0, _("ul speed:"))
- self.labelwin.addstr(7, 0, _("sharing:"))
- self.labelwin.addstr(8, 0, _("seeds:"))
- self.labelwin.addstr(9, 0, _("peers:"))
- curses.panel.update_panels()
- curses.doupdate()
- self.changeflag.clear()
-
-
- def finished(self):
- self.done = True
- self.downRate = '---'
- self.display({'activity':_("download succeeded"), 'fractionDone':1})
-
- def error(self, errormsg):
- newerrmsg = strftime('[%H:%M:%S] ') + errormsg
- self.errors.append(newerrmsg.split('\n')[0])
- self.errlist.append(newerrmsg)
- self.display({})
-
- def display(self, statistics):
- fractionDone = statistics.get('fractionDone')
- activity = statistics.get('activity')
- timeEst = statistics.get('timeEst')
- downRate = statistics.get('downRate')
- upRate = statistics.get('upRate')
- spew = statistics.get('spew')
-
- inchar = self.fieldwin.getch()
- if inchar == 12: # ^L
- self._remake_window()
- elif inchar in (ord('q'),ord('Q')):
- self.doneflag.set()
- elif inchar in (ord('r'),ord('R')):
- self.reread_config()
- elif inchar in (ord('u'),ord('U')):
- curses.echo()
- self.fieldwin.nodelay(0)
- s = self.fieldwin.getstr(6,10)
- curses.noecho()
- self.fieldwin.nodelay(1)
- r = None
- try:
- r = int(s)
- except ValueError:
- pass
- if r is not None:
- self.ulrate(r)
-
- if timeEst is not None:
- self.activity = fmttime(timeEst)
- elif activity is not None:
- self.activity = activity
- if self.changeflag.isSet():
- return
-
- if fractionDone is not None:
- blocknum = int(self.fieldw * fractionDone)
- self.progress = blocknum * '#' + (self.fieldw - blocknum) * '_'
- self.status = '%s (%.1f%%)' % (self.activity, fractionDone * 100)
-
- if downRate is not None:
- self.downRate = '%.1f KB/s' % (downRate / (1 << 10))
- if upRate is not None:
- self.upRate = '%.1f KB/s' % (upRate / (1 << 10))
- downTotal = statistics.get('downTotal')
- if downTotal is not None:
- upTotal = statistics['upTotal']
- if downTotal <= upTotal / 100:
- self.shareRating = _("oo (%.1f MB up / %.1f MB down)") % (
- upTotal / (1<<20), downTotal / (1<<20))
- else:
- self.shareRating = _("%.3f (%.1f MB up / %.1f MB down)") % (
- upTotal / downTotal, upTotal / (1<<20), downTotal / (1<<20))
- numCopies = statistics['numCopies']
- nextCopies = ', '.join(["%d:%.1f%%" % (a,int(b*1000)/10) for a,b in
- zip(xrange(numCopies+1, 1000), statistics['numCopyList'])])
- if not self.done:
- self.seedStatus = _("%d seen now, plus %d distributed copies"
- "(%s)") % (statistics['numSeeds' ],
- statistics['numCopies'],
- nextCopies)
- else:
- self.seedStatus = _("%d distributed copies (next: %s)") % (
- statistics['numCopies'], nextCopies)
- self.peerStatus = _("%d seen now") % statistics['numPeers']
-
- self.fieldwin.erase()
- self.fieldwin.addnstr(0, 0, self.file, self.fieldw, curses.A_BOLD)
- self.fieldwin.addnstr(1, 0, self.fileSize, self.fieldw)
- self.fieldwin.addnstr(2, 0, self.downloadTo, self.fieldw)
- if self.progress:
- self.fieldwin.addnstr(3, 0, self.progress, self.fieldw, curses.A_BOLD)
- self.fieldwin.addnstr(4, 0, self.status, self.fieldw)
- self.fieldwin.addnstr(5, 0, self.downRate, self.fieldw)
- self.fieldwin.addnstr(6, 0, self.upRate, self.fieldw)
- self.fieldwin.addnstr(7, 0, self.shareRating, self.fieldw)
- self.fieldwin.addnstr(8, 0, self.seedStatus, self.fieldw)
- self.fieldwin.addnstr(9, 0, self.peerStatus, self.fieldw)
-
- self.spewwin.erase()
-
- if not spew:
- errsize = self.spewh
- if self.errors:
- self.spewwin.addnstr(0, 0, _("error(s):"), self.speww, curses.A_BOLD)
- errsize = len(self.errors)
- displaysize = min(errsize, self.spewh)
- displaytop = errsize - displaysize
- for i in range(displaysize):
- self.spewwin.addnstr(i, self.labelw, self.errors[displaytop + i],
- self.speww-self.labelw-1, curses.A_BOLD)
- else:
- if self.errors:
- self.spewwin.addnstr(0, 0, _("error:"), self.speww, curses.A_BOLD)
- self.spewwin.addnstr(0, self.labelw, self.errors[-1],
- self.speww-self.labelw-1, curses.A_BOLD)
- self.spewwin.addnstr(2, 0, _(" # IP Upload Download Completed Speed"), self.speww, curses.A_BOLD)
-
-
- if self.spew_scroll_time + SPEW_SCROLL_RATE < time():
- self.spew_scroll_time = time()
- if len(spew) > self.spewh-5 or self.spew_scroll_pos > 0:
- self.spew_scroll_pos += 1
- if self.spew_scroll_pos > len(spew):
- self.spew_scroll_pos = 0
-
- for i in range(len(spew)):
- spew[i]['lineno'] = i+1
- spew.append({'lineno': None})
- spew = spew[self.spew_scroll_pos:] + spew[:self.spew_scroll_pos]
-
- for i in range(min(self.spewh - 5, len(spew))):
- if not spew[i]['lineno']:
- continue
- self.spewwin.addnstr(i+3, 0, '%3d' % spew[i]['lineno'], 3)
- self.spewwin.addnstr(i+3, 4, spew[i]['ip'], 15)
- ul = spew[i]['upload']
- if ul[1] > 100:
- self.spewwin.addnstr(i+3, 20, '%6.0f KB/s' % (
- ul[1] / 1000), 11)
- self.spewwin.addnstr(i+3, 32, '-----', 5)
- if ul[2]:
- self.spewwin.addnstr(i+3, 33, 'I', 1)
- if ul[3]:
- self.spewwin.addnstr(i+3, 35, 'C', 1)
- dl = spew[i]['download']
- if dl[1] > 100:
- self.spewwin.addnstr(i+3, 38, '%6.0f KB/s' % (
- dl[1] / 1000), 11)
- self.spewwin.addnstr(i+3, 50, '-------', 7)
- if dl[2]:
- self.spewwin.addnstr(i+3, 51, 'I', 1)
- if dl[3]:
- self.spewwin.addnstr(i+3, 53, 'C', 1)
- if dl[4]:
- self.spewwin.addnstr(i+3, 55, 'S', 1)
- self.spewwin.addnstr(i+3, 58, '%5.1f%%' % (int(spew[i]['completed']*1000)/10), 6)
- if spew[i]['speed'] is not None:
- self.spewwin.addnstr(i+3, 64, '%5.0f KB/s' % (spew[i]['speed']/1000), 10)
-
- self.spewwin.addnstr(self.spewh-1, 0,
- _("downloading %d pieces, have %d fragments, "
- "%d of %d pieces completed") %
- (statistics['storage_active'], statistics['storage_dirty'],
- statistics['storage_numcomplete'], self.numpieces),
- self.speww-1)
-
- curses.panel.update_panels()
- curses.doupdate()
-
-
-class DL(Feedback):
-
- def __init__(self, metainfo, config, errlist):
- self.doneflag = threading.Event()
- self.metainfo = metainfo
- self.config = Preferences().initWithDict(config)
- self.errlist = errlist
-
- def run(self, scrwin):
- def reread():
- self.multitorrent.rawserver.external_add_task(self.reread_config,0)
- def ulrate(value):
- self.multitorrent.set_option('max_upload_rate', value)
- self.torrent.set_option('max_upload_rate', value)
-
- self.d = CursesDisplayer(scrwin, self.errlist, self.doneflag, reread, ulrate)
- try:
- self.multitorrent = Multitorrent(self.config, self.doneflag,
- self.global_error)
- # raises BTFailure if bad
- metainfo = ConvertedMetainfo(bdecode(self.metainfo))
- torrent_name = metainfo.name_fs
- if config['save_as']:
- if config['save_in']:
- raise BTFailure(_("You cannot specify both --save_as and "
- "--save_in"))
- saveas = config['save_as']
- elif config['save_in']:
- saveas = os.path.join(config['save_in'], torrent_name)
- else:
- saveas = torrent_name
-
- self.d.set_torrent_values(metainfo.name, os.path.abspath(saveas),
- metainfo.total_bytes, len(metainfo.hashes))
- self.torrent = self.multitorrent.start_torrent(metainfo,
- Preferences(self.config), self, saveas)
- except BTFailure, e:
- errlist.append(str(e))
- return
- self.get_status()
- self.multitorrent.rawserver.install_sigint_handler()
- self.multitorrent.rawserver.listen_forever()
- self.d.display({'activity':_("shutting down"), 'fractionDone':0})
- self.torrent.shutdown()
-
- def reread_config(self):
- try:
- newvalues = configfile.get_config(self.config, 'bittorrent-curses')
- except Exception, e:
- self.d.error(_("Error reading config: ") + str(e))
- return
- self.config.update(newvalues)
- # The set_option call can potentially trigger something that kills
- # the torrent (when writing this the only possibility is a change in
- # max_files_open causing an IOError while closing files), and so
- # the self.failed() callback can run during this loop.
- for option, value in newvalues.iteritems():
- self.multitorrent.set_option(option, value)
- for option, value in newvalues.iteritems():
- self.torrent.set_option(option, value)
-
- def get_status(self):
- self.multitorrent.rawserver.add_task(self.get_status,
- self.config['display_interval'])
- status = self.torrent.get_status(self.config['spew'])
- self.d.display(status)
-
- def global_error(self, level, text):
- self.d.error(text)
-
- def error(self, torrent, level, text):
- self.d.error(text)
-
- def failed(self, torrent, is_external):
- self.doneflag.set()
-
- def finished(self, torrent):
- self.d.finished()
-
-
-if __name__ == '__main__':
- uiname = 'bittorrent-curses'
- defaults = get_defaults(uiname)
-
- metainfo = None
- if len(sys.argv) <= 1:
- printHelp(uiname, defaults)
- sys.exit(1)
- try:
- config, args = configfile.parse_configuration_and_args(defaults,
- uiname, sys.argv[1:], 0, 1)
-
- torrentfile = None
- if len(args):
- torrentfile = args[0]
- for opt in ('responsefile', 'url'):
- if config[opt]:
- print '"--%s"' % opt, _("deprecated, do not use")
- torrentfile = config[opt]
- if torrentfile is not None:
- metainfo, errors = GetTorrent.get(torrentfile)
- if errors:
- raise BTFailure(_("Error reading .torrent file: ") + '\n'.join(errors))
- else:
- raise BTFailure(_("you must specify a .torrent file"))
- except BTFailure, e:
- print str(e)
- sys.exit(1)
-
- errlist = []
- dl = DL(metainfo, config, errlist)
- curses_wrapper(dl.run)
-
- if errlist:
- print _("These errors occurred during execution:")
- for error in errlist:
- print error
diff --git a/bittorrent-tracker b/bittorrent-tracker
deleted file mode 120000
index c6ade35..0000000
--- a/bittorrent-tracker
+++ /dev/null
@@ -1 +0,0 @@
-bittorrent-tracker.py \ No newline at end of file
diff --git a/bittorrent.desktop b/bittorrent.desktop
deleted file mode 100644
index df6d84c..0000000
--- a/bittorrent.desktop
+++ /dev/null
@@ -1,11 +0,0 @@
-[Desktop Entry]
-Encoding=UTF-8
-Name=BitTorrent File Transfer
-Comment=Distributed download of files from the Internet
-Exec=bittorrent
-Icon=bittorrent.png
-Terminal=false
-Type=Application
-StartupNotify=true
-Categories=Network;
-MimeType=application/x-bittorrent;
diff --git a/bittorrent.png b/bittorrent.png
deleted file mode 100644
index 52a4d49..0000000
--- a/bittorrent.png
+++ /dev/null
Binary files differ
diff --git a/bittorrent.py b/bittorrent.py
deleted file mode 100755
index c67f665..0000000
--- a/bittorrent.py
+++ /dev/null
@@ -1,3834 +0,0 @@
-#!/usr/bin/env python
-
-# The contents of this file are subject to the BitTorrent Open Source License
-# Version 1.1 (the License). You may not copy or use this file, in either
-# source code or executable form, except in compliance with the License. You
-# may obtain a copy of the License at http://www.bittorrent.com/license/.
-#
-# Software distributed under the License is distributed on an AS IS basis,
-# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
-# for the specific language governing rights and limitations under the
-# License.
-
-# Written by Uoti Urpala and Matt Chisholm
-
-from __future__ import division
-
-from BitTorrent.platform import install_translation
-install_translation()
-
-import sys
-import itertools
-import math
-import os
-import threading
-import datetime
-import random
-import atexit
-
-assert sys.version_info >= (2, 3), _("Install Python %s or greater") % '2.3'
-
-from BitTorrent import BTFailure, INFO, WARNING, ERROR, CRITICAL, status_dict, app_name
-
-from BitTorrent import configfile
-
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.IPC import ipc_interface
-from BitTorrent.prefs import Preferences
-from BitTorrent.platform import doc_root, btspawn, path_wrap, os_version, is_frozen_exe, get_startup_dir, create_shortcut, remove_shortcut
-from BitTorrent import zurllib
-
-defaults = get_defaults('bittorrent')
-defaults.extend((('donated' , '', ''), # the version that the user last donated for
- ('notified', '', ''), # the version that the user was last notified of
- ))
-
-
-ui_options = [
- 'max_upload_rate' ,
- 'minport' ,
- 'maxport' ,
- 'next_torrent_time' ,
- 'next_torrent_ratio' ,
- 'last_torrent_ratio' ,
- 'seed_forever' ,
- 'seed_last_forever' ,
- 'ask_for_save' ,
- 'save_in' ,
- 'open_from' ,
- 'ip' ,
- 'start_torrent_behavior',
- 'upnp' ,
- ]
-
-if os.name == 'nt':
- ui_options.extend( [
- 'launch_on_startup' ,
- 'minimize_to_tray' ,
- ])
-
-advanced_ui_options_index = len(ui_options)
-
-ui_options.extend([
- 'min_uploads' ,
- 'max_uploads' ,
- 'max_initiate' ,
- 'max_incomplete' ,
- 'max_allow_in' ,
- 'max_files_open' ,
- 'forwarded_port' ,
- 'display_interval',
- 'donated' ,
- 'notified' ,
- ])
-
-
-if is_frozen_exe:
- ui_options.append('progressbar_hack')
- defproghack = 0
- if os_version == 'XP':
- # turn on progress bar hack by default for Win XP
- defproghack = 1
- defaults.extend((('progressbar_hack' , defproghack, ''),))
-
-
-NAG_FREQUENCY = 3
-PORT_RANGE = 5
-
-defconfig = dict([(name, value) for (name, value, doc) in defaults])
-del name, value, doc
-
-def btgui_exit(ipc):
- ipc.stop()
-
-class global_logger(object):
- def __init__(self, logger = None):
- self.logger = logger
- def __call__(self, severity, msg):
- if self.logger:
- self.logger(severity, msg)
- else:
- sys.stderr.write("%s: %s\n" % (status_dict[severity], msg))
-
-# if it's application global, why do we pass a reference to it everywhere?
-global_log_func = global_logger()
-
-if __name__ == '__main__':
- zurllib.add_unsafe_thread()
-
- try:
- config, args = configfile.parse_configuration_and_args(defaults,
- 'bittorrent', sys.argv[1:], 0, None)
- except BTFailure, e:
- print str(e)
- sys.exit(1)
-
- config = Preferences().initWithDict(config)
- advanced_ui = config['advanced']
-
- newtorrents = args
- for opt in ('responsefile', 'url'):
- if config[opt]:
- print '"--%s"' % opt, _("deprecated, do not use")
- newtorrents.append(config[opt])
-
- ipc = ipc_interface(config, global_log_func)
-
- # this could be on the ipc object
- ipc_master = True
- try:
- ipc.create()
- except BTFailure:
- ipc_master = False
-
- try:
- ipc.send_command('no-op')
- except BTFailure:
- global_log_func(ERROR, _("Failed to communicate with another %s process "
- "but one seems to be running.") +
- _(" Closing all %s windows may fix the problem.")
- % (app_name, app_name))
- sys.exit(1)
-
- # make sure we clean up the ipc when we close
- atexit.register(btgui_exit, ipc)
-
- # it's not obvious, but 'newtorrents' is carried on to the gui
- # __main__ if we're the IPC master
-
- if not ipc_master:
-
- if newtorrents:
- # Not sure if anything really useful could be done if
- # these send_command calls fail
- for name in newtorrents:
- ipc.send_command('start_torrent', name, config['save_as'])
- sys.exit(0)
-
- try:
- ipc.send_command('show_error', _("%s already running")%app_name)
- except BTFailure:
- global_log_func(ERROR, _("Failed to communicate with another %s process.") +
- _(" Closing all %s windows may fix the problem.")
- % app_name)
- sys.exit(1)
-
-
-import gtk
-import pango
-import gobject
-import webbrowser
-
-assert gtk.pygtk_version >= (2, 6), _("PyGTK %s or newer required") % '2.6'
-
-from BitTorrent import HELP_URL, DONATE_URL, SEARCH_URL, version, branch
-
-from BitTorrent import TorrentQueue
-from BitTorrent import LaunchPath
-from BitTorrent import Desktop
-from BitTorrent import ClientIdentifier
-from BitTorrent import NewVersion
-
-from BitTorrent.parseargs import makeHelp
-from BitTorrent.TorrentQueue import RUNNING, RUN_QUEUED, QUEUED, KNOWN, ASKING_LOCATION
-from BitTorrent.TrayIcon import TrayIcon
-from BitTorrent.StatusLight import GtkStatusLight as StatusLight
-from BitTorrent.GUI import *
-
-
-main_torrent_dnd_tip = _("drag to reorder")
-torrent_menu_tip = _("right-click for menu")
-torrent_tip_format = '%s:\n %s\n %s'
-
-rate_label = ': %s'
-
-speed_classes = {
- ( 4, 5):_("dialup" ),
- ( 6, 14):_("DSL/cable 128k up"),
- ( 15, 29):_("DSL/cable 256k up"),
- ( 30, 91):_("DSL 768k up" ),
- ( 92, 137):_("T1" ),
- ( 138, 182):_("T1/E1" ),
- ( 183, 249):_("E1" ),
- ( 250, 5446):_("T3" ),
- (5447,18871):_("OC3" ),
- }
-
-def find_dir(path):
- if os.path.isdir(path):
- return path
- directory, garbage = os.path.split(path)
- while directory:
- if os.access(directory, os.F_OK) and os.access(directory, os.W_OK):
- return directory
- directory, garbage = os.path.split(directory)
- if garbage == '':
- break
- return None
-
-def smart_dir(path):
- path = find_dir(path)
- if path is None:
- path = Desktop.desktop
- return path
-
-class MenuItem(gtk.MenuItem):
- def __init__(self, label, accel_group=None, func=None):
- gtk.MenuItem.__init__(self, label)
- if func is not None:
- self.connect("activate", func)
- else:
- self.set_sensitive(False)
-
- if accel_group is not None:
- label = label.decode('utf-8')
- accel_index = label.find('_')
- if -1 < accel_index < len(label) - 1:
- accel_char = long(ord(label[accel_index+1]))
- accel_key = gtk.gdk.unicode_to_keyval(accel_char)
- if accel_key != accel_char | 0x01000000:
- self.add_accelerator("activate", accel_group, accel_key,
- gtk.gdk.CONTROL_MASK, gtk.ACCEL_VISIBLE)
- self.show()
-
-
-def build_menu(menu_items, accel_group=None):
- menu = gtk.Menu()
- for label,func in menu_items:
- if label == '----':
- s = gtk.SeparatorMenuItem()
- s.show()
- menu.add(s)
- else:
- item = MenuItem(label, accel_group=accel_group, func=func)
- item.show()
- menu.add(item)
- return menu
-
-
-class Validator(gtk.Entry):
- valid_chars = '1234567890'
- minimum = None
- maximum = None
- cast = int
-
- def __init__(self, option_name, config, setfunc):
- gtk.Entry.__init__(self)
- self.option_name = option_name
- self.config = config
- self.setfunc = setfunc
-
- self.set_text(str(config[option_name]))
-
- self.set_size_request(self.width,-1)
-
- self.connect('insert-text', self.text_inserted)
- self.connect('focus-out-event', self.focus_out)
-
- def get_value(self):
- value = None
- try:
- value = self.cast(self.get_text())
- except ValueError:
- pass
- return value
-
- def set_value(self, value):
- self.set_text(str(value))
- self.setfunc(self.option_name, value)
-
- def focus_out(self, entry, widget):
- value = self.get_value()
-
- if value is None:
- return
-
- if (self.minimum is not None) and (value < self.minimum):
- value = self.minimum
- if (self.maximum is not None) and (value > self.maximum):
- value = self.maximum
-
- self.set_value(value)
-
- def text_inserted(self, entry, input, position, user_data):
- for i in input:
- if (self.valid_chars is not None) and (i not in self.valid_chars):
- self.emit_stop_by_name('insert-text')
- return True
- return False
-
-class IPValidator(Validator):
- valid_chars = '1234567890.'
- width = 128
- cast = str
-
-class PortValidator(Validator):
- width = 64
- minimum = 1024
- maximum = 65535
-
- def add_end(self, end_name):
- self.end_option_name = end_name
-
- def set_value(self, value):
- self.set_text(str(value))
- self.setfunc(self.option_name, value)
- self.setfunc(self.end_option_name, value+PORT_RANGE)
-
-
-class PercentValidator(Validator):
- width = 48
- minimum = 0
-
-class MinutesValidator(Validator):
- width = 48
- minimum = 1
-
-class EnterUrlDialog(MessageDialog):
- flags = gtk.DIALOG_DESTROY_WITH_PARENT
- def __init__(self, parent):
- self.entry = gtk.Entry()
- self.entry.show()
- self.main = parent
- MessageDialog.__init__(self, parent.mainwindow,
- _("Enter torrent URL"),
- _("Enter the URL of a torrent file to open:"),
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_OK_CANCEL,
- yesfunc=lambda *args: parent.open_url(self.entry.get_text()),
- default=gtk.RESPONSE_OK
- )
- hbox = gtk.HBox()
- hbox.pack_start(self.entry, padding=SPACING)
- hbox.show()
- self.entry.set_activates_default(True)
- self.entry.set_flags(gtk.CAN_FOCUS)
- self.vbox.pack_start(hbox)
- self.entry.grab_focus()
-
- def close(self, *args):
- self.destroy()
-
- def destroy(self):
- MessageDialog.destroy(self)
- self.main.window_closed('enterurl')
-
-
-class RateSliderBox(gtk.VBox):
- base = 10
- multiplier = 4
- max_exponent = 3.3
-
- def __init__(self, config, torrentqueue):
- gtk.VBox.__init__(self, homogeneous=False)
- self.config = config
- self.torrentqueue = torrentqueue
-
- if self.config['max_upload_rate'] < self.slider_to_rate(0):
- self.config['max_upload_rate'] = self.slider_to_rate(0)
-
- self.speed_classes = {
- ( 4, 5):_("dialup" ),
- ( 6, 14):_("DSL/cable 128k up"),
- ( 15, 29):_("DSL/cable 256k up"),
- ( 30, 91):_("DSL 768k up" ),
- ( 92, 137):_("T1" ),
- ( 138, 182):_("T1/E1" ),
- ( 183, 249):_("E1" ),
- ( 250, 5446):_("T3" ),
- (5447,18871):_("OC3" ),
- }
-
- biggest_size = 0
- for v in self.speed_classes.values():
- width = gtk.Label(v).size_request()[0]
- if width > biggest_size:
- biggest_size = width
-
- self.rate_slider_label_box = gtk.HBox(spacing=SPACING,
- homogeneous=True)
-
- self.rate_slider_label = gtk.Label(_("Maximum upload rate:"))
- self.rate_slider_label.set_ellipsize(pango.ELLIPSIZE_START)
- self.rate_slider_label.set_alignment(1, 0.5)
- self.rate_slider_label_box.pack_start(self.rate_slider_label,
- expand=True, fill=True)
-
- self.rate_slider_value = gtk.Label(
- self.value_to_label(self.config['max_upload_rate']))
- self.rate_slider_value.set_alignment(0, 0.5)
- self.rate_slider_value.set_size_request(biggest_size, -1)
-
- self.rate_slider_label_box.pack_start(self.rate_slider_value,
- expand=True, fill=True)
-
- self.rate_slider_adj = gtk.Adjustment(
- self.rate_to_slider(self.config['max_upload_rate']), 0,
- self.max_exponent, 0.01, 0.1)
-
- self.rate_slider = gtk.HScale(self.rate_slider_adj)
- self.rate_slider.set_draw_value(False)
- self.rate_slider_adj.connect('value_changed', self.set_max_upload_rate)
-
- self.pack_start(self.rate_slider , expand=False, fill=False)
- self.pack_start(self.rate_slider_label_box , expand=False, fill=False)
-
- if False: # this shows the legend for the slider
- self.rate_slider_legend = gtk.HBox(homogeneous=True)
- for i in range(int(self.max_exponent+1)):
- label = gtk.Label(str(self.slider_to_rate(i)))
- alabel = halign(label, i/self.max_exponent)
- self.rate_slider_legend.pack_start(alabel,
- expand=True, fill=True)
- self.pack_start(self.rate_slider_legend, expand=False, fill=False)
-
-
- def start(self):
- self.set_max_upload_rate(self.rate_slider_adj)
-
- def rate_to_slider(self, value):
- return math.log(value/self.multiplier, self.base)
-
- def slider_to_rate(self, value):
- return int(round(self.base**value * self.multiplier))
-
- def value_to_label(self, value):
- conn_type = ''
- for key, conn in self.speed_classes.items():
- min_v, max_v = key
- if min_v <= value <= max_v:
- conn_type = ' (%s)'%conn
- break
- label = str(Rate(value*1024)) + conn_type
- return label
-
- def set_max_upload_rate(self, adj):
- option = 'max_upload_rate'
- value = self.slider_to_rate(adj.get_value())
- self.config[option] = value
- self.torrentqueue.set_config(option, value)
- self.rate_slider_value.set_text(self.value_to_label(int(value)))
-
-
-class StopStartButton(gtk.Button):
- stop_tip = _("Temporarily stop all running torrents")
- start_tip = _("Resume downloading")
-
- def __init__(self, main):
- gtk.Button.__init__(self)
- self.main = main
- self.connect('clicked', self.toggle)
-
- self.stop_image = gtk.Image()
- self.stop_image.set_from_stock('bt-pause', gtk.ICON_SIZE_BUTTON)
- self.stop_image.show()
-
- self.start_image = gtk.Image()
- self.start_image.set_from_stock('bt-play', gtk.ICON_SIZE_BUTTON)
- self.start_image.show()
-
- def toggle(self, widget):
- self.set_paused(not self.main.config['pause'])
-
- def set_paused(self, paused):
- image = self.get_child()
- if paused:
- if image == self.stop_image:
- self.remove(self.stop_image)
- if image != self.start_image:
- self.add(self.start_image)
- self.main.tooltips.set_tip(self, self.start_tip)
- self.main.stop_queue()
- else:
- if image == self.start_image:
- self.remove(self.start_image)
- if image != self.stop_image:
- self.add(self.stop_image)
- self.main.tooltips.set_tip(self, self.stop_tip )
- self.main.restart_queue()
-
-
-class VersionWindow(Window):
- def __init__(self, main, newversion, download_url):
- Window.__init__(self)
- self.set_title(_("New %s version available")%app_name)
- self.set_border_width(SPACING)
- self.set_resizable(False)
- self.main = main
- self.newversion = newversion
- self.download_url = download_url
- self.connect('destroy', lambda w: self.main.window_closed('version'))
- self.vbox = gtk.VBox(spacing=SPACING)
- self.hbox = gtk.HBox(spacing=SPACING)
- self.image = gtk.Image()
- self.image.set_from_stock(gtk.STOCK_DIALOG_INFO, gtk.ICON_SIZE_DIALOG)
- self.hbox.pack_start(self.image)
-
- self.label = gtk.Label()
- self.label.set_markup(
- (_("A newer version of %s is available.\n") % app_name) +
- (_("You are using %s, and the new version is %s.\n") % (version, newversion)) +
- (_("You can always get the latest version from \n%s") % self.download_url)
- )
- self.label.set_selectable(True)
- self.hbox.pack_start(self.label)
- self.vbox.pack_start(self.hbox)
- self.bbox = gtk.HBox(spacing=SPACING)
-
- self.closebutton = gtk.Button(_("Download _later"))
- self.closebutton.connect('clicked', self.close)
-
- self.newversionbutton = gtk.Button(_("Download _now"))
- self.newversionbutton.connect('clicked', self.get_newversion)
-
- self.bbox.pack_end(self.newversionbutton, expand=False, fill=False)
- self.bbox.pack_end(self.closebutton , expand=False, fill=False)
-
- self.checkbox = gtk.CheckButton(_("_Remind me later"))
- self.checkbox.set_active(True)
- self.checkbox.connect('toggled', self.remind_toggle)
-
- self.bbox.pack_start(self.checkbox, expand=False, fill=False)
-
- self.vbox.pack_start(self.bbox)
-
- self.add(self.vbox)
- self.show_all()
-
- def remind_toggle(self, widget):
- v = self.checkbox.get_active()
- notified = ''
- if v:
- notified = ''
- else:
- notified = self.newversion
- self.main.set_config('notified', str(notified))
-
- def close(self, widget):
- self.destroy()
-
- def get_newversion(self, widget):
- if self.main.updater.can_install():
- if self.main.updater.torrentfile is None:
- self.main.visit_url(self.download_url)
- else:
- self.main.start_auto_update()
- else:
- self.main.visit_url(self.download_url)
- self.destroy()
-
-
-class AboutWindow(object):
-
- def __init__(self, main, donatefunc):
- self.win = Window()
- self.win.set_title(_("About %s")%app_name)
- self.win.set_size_request(300,400)
- self.win.set_border_width(SPACING)
- self.win.set_resizable(False)
- self.win.connect('destroy', lambda w: main.window_closed('about'))
- self.scroll = gtk.ScrolledWindow()
- self.scroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.scroll.set_shadow_type(gtk.SHADOW_IN)
-
- self.outervbox = gtk.VBox()
-
- self.outervbox.pack_start(get_logo(96), expand=False, fill=False)
-
- version_str = version
- if int(version_str[2]) % 2:
- version_str = version_str + ' ' + _("Beta")
-
- self.outervbox.pack_start(gtk.Label(_("Version %s")%version_str), expand=False, fill=False)
-
- if branch is not None:
- blabel = gtk.Label('cdv client dir: %s' % branch)
- self.outervbox.pack_start(blabel, expand=False, fill=False)
-
- self.vbox = gtk.VBox()
- self.vbox.set_size_request(250, -1)
-
- for i, fn in enumerate(('credits', 'credits-l10n')):
- if i != 0:
- self.vbox.pack_start(gtk.HSeparator(), padding=SPACING,
- expand=False, fill=False)
- filename = os.path.join(doc_root, fn+'.txt')
- l = ''
- if not os.access(filename, os.F_OK|os.R_OK):
- l = _("Couldn't open %s") % filename
- else:
- credits_f = file(filename)
- l = credits_f.read()
- credits_f.close()
- if os.name == 'nt':
- # gtk ignores blank lines on win98
- l = l.replace('\n\n', '\n\t\n')
- label = gtk.Label(l.strip())
- label.set_line_wrap(True)
- label.set_selectable(True)
- label.set_justify(gtk.JUSTIFY_CENTER)
- label.set_size_request(250,-1)
- self.vbox.pack_start(label, expand=False, fill=False)
-
- self.scroll.add_with_viewport(self.vbox)
-
- self.outervbox.pack_start(self.scroll, padding=SPACING)
-
- self.donatebutton = gtk.Button(_("Donate"))
- self.donatebutton.connect('clicked', donatefunc)
- self.donatebuttonbox = gtk.HButtonBox()
- self.donatebuttonbox.pack_start(self.donatebutton,
- expand=False, fill=False)
- self.outervbox.pack_end(self.donatebuttonbox, expand=False, fill=False)
-
- self.win.add(self.outervbox)
-
- self.win.show_all()
-
- def close(self, widget):
- self.win.destroy()
-
-
-class LogWindow(object):
- def __init__(self, main, logbuffer, config):
- self.config = config
- self.main = main
- self.win = Window()
- self.win.set_title(_("%s Activity Log")%app_name)
- self.win.set_default_size(600, 200)
- self.win.set_border_width(SPACING)
-
- self.buffer = logbuffer
- self.text = gtk.TextView(self.buffer)
- self.text.set_editable(False)
- self.text.set_cursor_visible(False)
- self.text.set_wrap_mode(gtk.WRAP_WORD)
-
- self.scroll = gtk.ScrolledWindow()
- self.scroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.scroll.set_shadow_type(gtk.SHADOW_IN)
- self.scroll.add(self.text)
-
- self.vbox = gtk.VBox(spacing=SPACING)
- self.vbox.pack_start(self.scroll)
-
- self.buttonbox = gtk.HButtonBox()
- self.buttonbox.set_spacing(SPACING)
-
- self.closebutton = gtk.Button(stock='gtk-close')
- self.closebutton.connect('clicked', self.close)
-
- self.savebutton = gtk.Button(stock='gtk-save')
- self.savebutton.connect('clicked', self.save_log_file_selection)
-
- self.clearbutton = gtk.Button(stock='gtk-clear')
- self.clearbutton.connect('clicked', self.clear_log)
-
- self.buttonbox.pack_start(self.savebutton)
- self.buttonbox.pack_start(self.closebutton)
-
- self.hbox2 = gtk.HBox(homogeneous=False)
-
- self.hbox2.pack_end(self.buttonbox, expand=False, fill=False)
-
- bb = gtk.HButtonBox()
- bb.pack_start(self.clearbutton)
- self.hbox2.pack_start(bb, expand=False, fill=True)
-
- self.vbox.pack_end(self.hbox2, expand=False, fill=True)
-
- self.win.add(self.vbox)
- self.win.connect("destroy", lambda w: self.main.window_closed('log'))
- self.scroll_to_end()
- self.win.show_all()
-
- def scroll_to_end(self):
- mark = self.buffer.create_mark(None, self.buffer.get_end_iter())
- self.text.scroll_mark_onscreen(mark)
-
- def save_log_file_selection(self, *args):
- name = 'bittorrent.log'
- path = smart_dir(self.config['save_in'])
- fullname = os.path.join(path, name)
- self.main.open_window('savefile',
- title=_("Save log in:"),
- fullname=fullname,
- got_location_func=self.save_log,
- no_location_func=lambda: self.main.window_closed('savefile'))
-
-
- def save_log(self, saveas):
- self.main.window_closed('savefile')
- f = file(saveas, 'w')
- f.write(self.buffer.get_text(self.buffer.get_start_iter(),
- self.buffer.get_end_iter()))
- save_message = self.buffer.log_text(_("log saved"), None)
- f.write(save_message)
- f.close()
-
- def clear_log(self, *args):
- self.buffer.clear_log()
-
- def close(self, widget):
- self.win.destroy()
-
-
-class LogBuffer(gtk.TextBuffer):
-
- def __init__(self):
- gtk.TextBuffer.__init__(self)
-
- tt = self.get_tag_table()
-
- size_tag = gtk.TextTag('small')
- size_tag.set_property('size-points', 10)
- tt.add(size_tag)
-
- info_tag = gtk.TextTag('info')
- info_tag.set_property('foreground', '#00a040')
- tt.add(info_tag)
-
- warning_tag = gtk.TextTag('warning')
- warning_tag.set_property('foreground', '#a09000')
- tt.add(warning_tag)
-
- error_tag = gtk.TextTag('error')
- error_tag.set_property('foreground', '#b00000')
- tt.add(error_tag)
-
- critical_tag = gtk.TextTag('critical')
- critical_tag.set_property('foreground', '#b00000')
- critical_tag.set_property('weight', pango.WEIGHT_BOLD)
- tt.add(critical_tag)
-
-
- def log_text(self, text, severity=CRITICAL):
- now_str = datetime.datetime.strftime(datetime.datetime.now(),
- '[%Y-%m-%d %H:%M:%S] ')
- self.insert_with_tags_by_name(self.get_end_iter(), now_str, 'small')
- if severity is not None:
- self.insert_with_tags_by_name(self.get_end_iter(), '%s\n'%text,
- 'small', status_dict[severity])
- else:
- self.insert_with_tags_by_name(self.get_end_iter(),
- ' -- %s -- \n'%text, 'small')
-
- return now_str+text+'\n'
-
- def clear_log(self):
- self.set_text('')
- self.log_text(_("log cleared"), None)
-
-
-class CheckButton(gtk.CheckButton):
- def __init__(self, label, main, option_name, initial_value,
- extra_callback=None):
- gtk.CheckButton.__init__(self, label)
- self.main = main
- self.option_name = option_name
- self.option_type = type(initial_value)
- self.set_active(bool(initial_value))
- self.extra_callback = extra_callback
- self.connect('toggled', self.callback)
-
- def callback(self, *args):
- self.main.config[self.option_name] = \
- self.option_type(not self.main.config[self.option_name])
- self.main.setfunc(self.option_name, self.main.config[self.option_name])
- if self.extra_callback is not None:
- self.extra_callback()
-
-
-class SettingsWindow(object):
-
- def __init__(self, main, config, setfunc):
- self.main = main
- self.setfunc = setfunc
- self.config = config
- self.win = Window()
- self.win.connect("destroy", lambda w: main.window_closed('settings'))
- self.win.set_title(_("%s Settings")%app_name)
- self.win.set_border_width(SPACING)
-
- self.notebook = gtk.Notebook()
-
- self.vbox = gtk.VBox(spacing=SPACING)
- self.vbox.pack_start(self.notebook, expand=False, fill=False)
-
- # General tab
- if os.name == 'nt':
- self.cb_box = gtk.VBox(spacing=SPACING)
- self.cb_box.set_border_width(SPACING)
- self.notebook.append_page(self.cb_box, gtk.Label(_("General")))
-
- self.startup_checkbutton = CheckButton(
- _("Launch BitTorrent when Windows starts"), self,
- 'launch_on_startup', self.config['launch_on_startup'])
- self.cb_box.pack_start(self.startup_checkbutton, expand=False, fill=False)
- self.startup_checkbutton.connect('toggled', self.launch_on_startup)
-
- self.minimize_checkbutton = CheckButton(
- _("Minimize to system tray"), self,
- 'minimize_to_tray', self.config['minimize_to_tray'])
- self.cb_box.pack_start(self.minimize_checkbutton, expand=False, fill=False)
-
- # allow the user to set the progress bar text to all black
- self.progressbar_hack = CheckButton(
- _("Progress bar text is always black\n(requires restart)"),
- self, 'progressbar_hack', self.config['progressbar_hack'])
-
- self.cb_box.pack_start(self.progressbar_hack, expand=False, fill=False)
- # end General tab
-
- # Saving tab
- self.saving_box = gtk.VBox(spacing=SPACING)
- self.saving_box.set_border_width(SPACING)
- self.notebook.append_page(self.saving_box, gtk.Label(_("Saving")))
-
- self.dl_frame = gtk.Frame(_("Save new downloads in:"))
- self.saving_box.pack_start(self.dl_frame, expand=False, fill=False)
-
- self.dl_box = gtk.VBox(spacing=SPACING)
- self.dl_box.set_border_width(SPACING)
- self.dl_frame.add(self.dl_box)
- self.save_in_box = gtk.HBox(spacing=SPACING)
-
- self.dl_save_in = gtk.Entry()
- self.dl_save_in.set_editable(False)
- self.set_save_in(self.config['save_in'])
- self.save_in_box.pack_start(self.dl_save_in, expand=True, fill=True)
-
- self.dl_save_in_button = gtk.Button(_("Change..."))
- self.dl_save_in_button.connect('clicked', self.get_save_in)
- self.save_in_box.pack_start(self.dl_save_in_button, expand=False, fill=False)
- self.dl_box.pack_start(self.save_in_box, expand=False, fill=False)
-
- self.dl_ask_checkbutton = CheckButton(
- _("Ask where to save each new download"), self,
- 'ask_for_save', self.config['ask_for_save'])
-
- self.dl_box.pack_start(self.dl_ask_checkbutton, expand=False, fill=False)
- # end Saving tab
-
- # Downloading tab
- self.downloading_box = gtk.VBox(spacing=SPACING)
- self.downloading_box.set_border_width(SPACING)
- self.notebook.append_page(self.downloading_box, gtk.Label(_("Downloading")))
-
- self.dnd_frame = gtk.Frame(_("When starting a new torrent:"))
- self.dnd_box = gtk.VBox(spacing=SPACING, homogeneous=True)
- self.dnd_box.set_border_width(SPACING)
-
- self.dnd_states = ['replace','add','ask']
- self.dnd_original_state = self.config['start_torrent_behavior']
-
- self.always_replace_radio = gtk.RadioButton(
- group=None,
- label=_("_Stop another running torrent to make room"))
- self.dnd_box.pack_start(self.always_replace_radio)
- self.always_replace_radio.state_name = self.dnd_states[0]
-
- self.always_add_radio = gtk.RadioButton(
- group=self.always_replace_radio,
- label=_("_Don't stop other running torrents"))
- self.dnd_box.pack_start(self.always_add_radio)
- self.always_add_radio.state_name = self.dnd_states[1]
-
- self.always_ask_radio = gtk.RadioButton(
- group=self.always_replace_radio,
- label=_("_Ask each time")
- )
- self.dnd_box.pack_start(self.always_ask_radio)
- self.always_ask_radio.state_name = self.dnd_states[2]
-
- self.dnd_group = self.always_replace_radio.get_group()
- for r in self.dnd_group:
- r.connect('toggled', self.start_torrent_behavior_changed)
-
- self.set_start_torrent_behavior(self.config['start_torrent_behavior'])
-
- self.dnd_frame.add(self.dnd_box)
- self.downloading_box.pack_start(self.dnd_frame, expand=False, fill=False)
-
- # Seeding tab
- self.seeding_box = gtk.VBox(spacing=SPACING)
- self.seeding_box.set_border_width(SPACING)
- self.notebook.append_page(self.seeding_box, gtk.Label(_("Seeding")))
-
- def colon_split(framestr):
- COLONS = (':', u'\uff1a')
- for colon in COLONS:
- if colon in framestr:
- return framestr.split(colon)
- return '', framestr
-
- nt_framestr = _("Seed completed torrents: until share ratio reaches [_] percent, or for [_] minutes, whichever comes first.")
- nt_title, nt_rem = colon_split(nt_framestr)
- nt_msg1, nt_msg2, nt_msg4 = nt_rem.split('[_]')
- nt_msg3 = ''
- if ',' in nt_msg2:
- nt_msg2, nt_msg3 = nt_msg2.split(',')
- nt_msg2 += ','
-
- self.next_torrent_frame = gtk.Frame(nt_title+':')
- self.next_torrent_box = gtk.VBox(spacing=SPACING, homogeneous=True)
- self.next_torrent_box.set_border_width(SPACING)
-
- self.next_torrent_frame.add(self.next_torrent_box)
-
-
- self.next_torrent_ratio_box = gtk.HBox()
- self.next_torrent_ratio_box.pack_start(gtk.Label(nt_msg1),
- fill=False, expand=False)
- self.next_torrent_ratio_field = PercentValidator('next_torrent_ratio',
- self.config, self.setfunc)
- self.next_torrent_ratio_box.pack_start(self.next_torrent_ratio_field,
- fill=False, expand=False)
- self.next_torrent_ratio_box.pack_start(gtk.Label(nt_msg2),
- fill=False, expand=False)
- self.next_torrent_box.pack_start(self.next_torrent_ratio_box)
-
-
- self.next_torrent_time_box = gtk.HBox()
- self.next_torrent_time_box.pack_start(gtk.Label(nt_msg3),
- fill=False, expand=False)
- self.next_torrent_time_field = MinutesValidator('next_torrent_time',
- self.config, self.setfunc)
- self.next_torrent_time_box.pack_start(self.next_torrent_time_field,
- fill=False, expand=False)
- self.next_torrent_time_box.pack_start(gtk.Label(nt_msg4),
- fill=False, expand=False)
- self.next_torrent_box.pack_start(self.next_torrent_time_box)
-
- def seed_forever_extra():
- for field in (self.next_torrent_ratio_field,
- self.next_torrent_time_field):
- field.set_sensitive(not self.config['seed_forever'])
-
- seed_forever_extra()
- self.seed_forever = CheckButton( _("Seed indefinitely"), self,
- 'seed_forever',
- self.config['seed_forever'],
- seed_forever_extra)
- self.next_torrent_box.pack_start(self.seed_forever)
- # end next torrent seed behavior
-
- # begin last torrent seed behavior
- lt_framestr = _("Seed last completed torrent: until share ratio reaches [_] percent.")
- lt_title, lt_rem = colon_split(lt_framestr)
- lt_msg1, lt_msg2 = lt_rem.split('[_]')
-
- self.seeding_box.pack_start(self.next_torrent_frame, expand=False, fill=False)
-
- self.last_torrent_frame = gtk.Frame(lt_title+':')
- self.last_torrent_vbox = gtk.VBox(spacing=SPACING)
- self.last_torrent_vbox.set_border_width(SPACING)
- self.last_torrent_box = gtk.HBox()
- self.last_torrent_box.pack_start(gtk.Label(lt_msg1),
- expand=False, fill=False)
- self.last_torrent_ratio_field = PercentValidator('last_torrent_ratio',
- self.config, self.setfunc)
- self.last_torrent_box.pack_start(self.last_torrent_ratio_field,
- fill=False, expand=False)
- self.last_torrent_box.pack_start(gtk.Label(lt_msg2),
- fill=False, expand=False)
- self.last_torrent_vbox.pack_start(self.last_torrent_box)
-
- def seed_last_forever_extra():
- self.last_torrent_ratio_field.set_sensitive(
- not self.config['seed_last_forever'])
-
- seed_last_forever_extra()
-
- self.seed_last_forever = CheckButton(_("Seed indefinitely"), self,
- 'seed_last_forever',
- self.config['seed_last_forever'],
- seed_last_forever_extra)
- self.last_torrent_vbox.pack_start(self.seed_last_forever)
-
- self.last_torrent_frame.add(self.last_torrent_vbox)
- self.seeding_box.pack_start(self.last_torrent_frame, expand=False, fill=False)
-
- # Network tab
- self.network_box = gtk.VBox(spacing=SPACING)
- self.network_box.set_border_width(SPACING)
- self.notebook.append_page(self.network_box, gtk.Label(_("Network")))
-
- self.port_range_frame = gtk.Frame(_("Look for available port:"))
- self.port_range_box = gtk.VBox(spacing=SPACING)
- self.port_range_box.set_border_width(SPACING)
-
- self.port_range = gtk.HBox()
- self.port_range.pack_start(gtk.Label(_("starting at port: ")),
- expand=False, fill=False)
- self.minport_field = PortValidator('minport', self.config, self.setfunc)
- self.minport_field.add_end('maxport')
- self.port_range.pack_start(self.minport_field, expand=False, fill=False)
- self.minport_field.settingswindow = self
- self.port_range.pack_start(gtk.Label(' (1024-65535)'),
- expand=False, fill=False)
- self.port_range_box.pack_start(self.port_range,
- expand=False, fill=False)
-
- self.upnp = CheckButton(_("Enable automatic port mapping")+' (_UPnP)',
- self, 'upnp', self.config['upnp'], None)
- self.port_range_box.pack_start(self.upnp,
- expand=False, fill=False)
-
- self.port_range_frame.add(self.port_range_box)
- self.network_box.pack_start(self.port_range_frame, expand=False, fill=False)
-
- self.ip_frame = gtk.Frame(_("IP to report to the tracker:"))
- self.ip_box = gtk.VBox()
- self.ip_box.set_border_width(SPACING)
- self.ip_field = IPValidator('ip', self.config, self.setfunc)
- self.ip_box.pack_start(self.ip_field, expand=False, fill=False)
- label = gtk.Label(_("(Has no effect unless you are on the\nsame local network as the tracker)"))
- label.set_line_wrap(True)
- self.ip_box.pack_start(lalign(label), expand=False, fill=False)
- self.ip_frame.add(self.ip_box)
- self.network_box.pack_start(self.ip_frame, expand=False, fill=False)
-
- # end Network tab
-
- # Language tab
- self.languagechooser = LanguageChooser()
- self.notebook.append_page(self.languagechooser, gtk.Label("Language"))
- # end Language tab
-
- # Advanced tab
- if advanced_ui:
- self.advanced_box = gtk.VBox(spacing=SPACING)
- self.advanced_box.set_border_width(SPACING)
- hint = gtk.Label(_("WARNING: Changing these settings can\nprevent %s from functioning correctly.")%app_name)
- self.advanced_box.pack_start(lalign(hint), expand=False, fill=False)
- self.store = gtk.ListStore(*[gobject.TYPE_STRING] * 2)
- for option in ui_options[advanced_ui_options_index:]:
- self.store.append((option, str(self.config[option])))
-
- self.treeview = gtk.TreeView(self.store)
- r = gtk.CellRendererText()
- column = gtk.TreeViewColumn(_("Option"), r, text=0)
- self.treeview.append_column(column)
- r = gtk.CellRendererText()
- r.set_property('editable', True)
- r.connect('edited', self.store_value_edited)
- column = gtk.TreeViewColumn(_("Value"), r, text=1)
- self.treeview.append_column(column)
- self.advanced_frame = gtk.Frame()
- self.advanced_frame.set_shadow_type(gtk.SHADOW_IN)
- self.advanced_frame.add(self.treeview)
-
- self.advanced_box.pack_start(self.advanced_frame, expand=False, fill=False)
- self.notebook.append_page(self.advanced_box, gtk.Label(_("Advanced")))
-
-
- self.win.add(self.vbox)
- self.win.show_all()
-
-
- def get_save_in(self, widget=None):
- self.file_selection = self.main.open_window('choosefolder',
- title=_("Choose default download directory"),
- fullname=self.config['save_in'],
- got_location_func=self.set_save_in,
- no_location_func=lambda: self.main.window_closed('choosefolder'))
-
- def set_save_in(self, save_location):
- self.main.window_closed('choosefolder')
- if os.path.isdir(save_location):
- if save_location[-1] != os.sep:
- save_location += os.sep
- self.config['save_in'] = save_location
- save_in = path_wrap(self.config['save_in'])
- self.dl_save_in.set_text(save_in)
- self.setfunc('save_in', self.config['save_in'])
-
- def launch_on_startup(self, *args):
- dst = os.path.join(get_startup_dir(), app_name)
- if self.config['launch_on_startup']:
- src = os.path.abspath(sys.argv[0])
- create_shortcut(src, dst, "--start_minimized")
- else:
- try:
- remove_shortcut(dst)
- except Exception, e:
- self.main.global_error(WARNING, _("Failed to remove shortcut: %s") % str(e))
-
- def set_start_torrent_behavior(self, state_name):
- if state_name in self.dnd_states:
- for r in self.dnd_group:
- if r.state_name == state_name:
- r.set_active(True)
- else:
- r.set_active(False)
- else:
- self.always_replace_radio.set_active(True)
-
- def start_torrent_behavior_changed(self, radiobutton):
- if radiobutton.get_active():
- self.setfunc('start_torrent_behavior', radiobutton.state_name)
-
- def store_value_edited(self, cell, row, new_text):
- it = self.store.get_iter_from_string(row)
- option = ui_options[int(row)+advanced_ui_options_index]
- t = type(defconfig[option])
- try:
- if t is type(None) or t is str:
- value = new_text
- elif t is int or t is long:
- value = int(new_text)
- elif t is float:
- value = float(new_text)
- elif t is bool:
- value = value == 'True'
- else:
- raise TypeError, str(t)
- except ValueError:
- return
- self.setfunc(option, value)
- self.store.set(it, 1, str(value))
-
- def close(self, widget):
- self.win.destroy()
-
-
-class FileListWindow(object):
-
- SET_PRIORITIES = False
-
- def __init__(self, metainfo, closefunc):
- self.metainfo = metainfo
- self.setfunc = None
- self.allocfunc = None
- self.win = Window()
- self.win.set_title(_('Files in "%s"') % self.metainfo.name)
- self.win.connect("destroy", closefunc)
- self.tooltips = gtk.Tooltips()
-
- self.filepath_to_iter = {}
-
- self.box1 = gtk.VBox()
-
- size_request = (0,0)
- if self.SET_PRIORITIES:
- self.toolbar = gtk.Toolbar()
- for label, tip, stockicon, method, arg in (
- (_("Never" ), _("Never download" ), gtk.STOCK_DELETE, self.dosomething, -1,),
- (_("Normal"), _("Download normally"), gtk.STOCK_NEW , self.dosomething, 0,),
- (_("First" ), _("Download first" ),'bt-finished' , self.dosomething, +1,),):
- self.make_tool_item(label, tip, stockicon, method, arg)
- size_request = (-1,54)
- self.box1.pack_start(self.toolbar, False)
-
- self.sw = gtk.ScrolledWindow()
- self.sw.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
- self.box1.pack_start(self.sw)
- self.win.add(self.box1)
-
- columns = [_("Filename"),_("Length"),_('%')]
- pre_size_list = ['M'*30, '6666 MB', '100.0', 'Download','black']
- if self.SET_PRIORITIES:
- columns.append(_("Download"))
- num_columns = len(pre_size_list)
-
- self.store = gtk.TreeStore(*[gobject.TYPE_STRING] * num_columns)
- self.store.append(None, pre_size_list)
- self.treeview = gtk.TreeView(self.store)
- self.treeview.set_enable_search(True)
- self.treeview.set_search_column(0)
- cs = []
- for i, name in enumerate(columns):
- r = gtk.CellRendererText()
- r.set_property('xalign', (0, 1, 1, 1)[i])
- if i == 0:
- column = gtk.TreeViewColumn(name, r, text = i, foreground = len(pre_size_list)-1)
- else:
- column = gtk.TreeViewColumn(name, r, text = i)
- column.set_resizable(True)
- self.treeview.append_column(column)
- cs.append(column)
-
- self.sw.add(self.treeview)
- self.treeview.set_headers_visible(False)
- self.treeview.columns_autosize()
- self.box1.show_all()
- self.treeview.realize()
-
- for column in cs:
- column.set_fixed_width(max(5,column.get_width()))
- column.set_sizing(gtk.TREE_VIEW_COLUMN_FIXED)
- self.treeview.set_headers_visible(True)
- self.store.clear()
-
- if self.SET_PRIORITIES:
- self.treeview.get_selection().set_mode(gtk.SELECTION_MULTIPLE)
- else:
- self.treeview.get_selection().set_mode(gtk.SELECTION_NONE)
-
- self.piecelen = self.metainfo.piece_length
- self.lengths = self.metainfo.sizes
- self.initialize_file_priorities()#[0,0])
- for name, size, priority in itertools.izip(self.metainfo.orig_files,
- self.metainfo.sizes, self.priorities):
- parent_name, local_name = os.path.split(name)
- parent_iter = self.recursive_add(parent_name)
-
- row = [local_name, Size(size), '?','', 'black']
- it = self.store.append(parent_iter, row)
- self.filepath_to_iter[name] = it
-
- self.treeview.expand_all()
- tvsr = self.treeview.size_request()
- vertical_padding = 18
- size_request = [max(size_request[0],tvsr[0]),
- (size_request[1] + tvsr[1] ) + vertical_padding]
- maximum_height = 300
- if size_request[1] > maximum_height - SCROLLBAR_WIDTH:
- size_request[1] = maximum_height
- size_request[0] = size_request[0] + SCROLLBAR_WIDTH
- self.win.set_default_size(*size_request)
-
- self.win.show_all()
-
- def recursive_add(self, fullpath):
- if fullpath == '':
- return None
- elif self.filepath_to_iter.has_key(fullpath):
- return self.filepath_to_iter[fullpath]
- else:
- parent_path, local_path = os.path.split(fullpath)
- parent_iter = self.recursive_add(parent_path)
- it = self.store.append(parent_iter,
- (local_path,) +
- ('',) * (self.store.get_n_columns()-2) +
- ('black',))
- self.filepath_to_iter[fullpath] = it
- return it
-
- def make_tool_item(self, label, tip, stockicon, method, arg):
- icon = gtk.Image()
- icon.set_from_stock(stockicon, gtk.ICON_SIZE_SMALL_TOOLBAR)
- item = gtk.ToolButton(icon_widget=icon, label=label)
- item.set_homogeneous(True)
- item.set_tooltip(self.tooltips, tip)
- if arg is not None:
- item.connect('clicked', method, arg)
- else:
- item.connect('clicked', method)
- self.toolbar.insert(item, 0)
-
- def initialize_file_priorities(self):
- self.priorities = []
- for length in self.lengths:
- self.priorities.append(0)
-
-## Uoti wrote these methods. I have no idea what this code is supposed to do.
-## --matt
-## def set_priorities(self, widget):
-## r = []
-## piece = 0
-## pos = 0
-## curprio = prevprio = 1000
-## for priority, length in itertools.izip(self.priorities, self.lengths):
-## pos += length
-## curprio = min(priority, curprio)
-## while pos >= (piece + 1) * self.piecelen:
-## if curprio != prevprio:
-## r.extend((piece, curprio))
-## prevprio = curprio
-## if curprio == priority:
-## piece = pos // self.piecelen
-## else:
-## piece += 1
-## if pos == piece * self.piecelen:
-## curprio = 1000
-## else:
-## curprio = priority
-## if curprio != prevprio:
-## r.extend((piece, curprio))
-## self.setfunc(r)
-## it = self.store.get_iter_first()
-## for i in xrange(len(self.priorities)):
-## self.store.set_value(it, 5, "black")
-## it = self.store.iter_next(it)
-## self.origpriorities = list(self.priorities)
-##
-## def initialize_file_priorities(self, piecepriorities):
-## self.priorities = []
-## piecepriorities = piecepriorities + [999999999]
-## it = iter(piecepriorities)
-## assert it.next() == 0
-## pos = piece = curprio = 0
-## for length in self.lengths:
-## pos += length
-## priority = curprio
-## while pos >= piece * self.piecelen:
-## curprio = it.next()
-## if pos > piece * self.piecelen:
-## priority = max(priority, curprio)
-## piece = it.next()
-## self.priorities.append(priority)
-## self.origpriorities = list(self.priorities)
-
- def dosomething(self, widget, dowhat):
- self.treeview.get_selection().selected_foreach(self.adjustfile, dowhat)
-
- def adjustfile(self, treemodel, path, it, dowhat):
- length = treemodel.get(it, 1)[0]
- if length == '':
- child = treemodel.iter_children(it)
- while True:
- if child is None:
- return
- elif not treemodel.is_ancestor(it, child):
- return
- else:
- self.adjustfile(treemodel, path, child, dowhat)
- child = treemodel.iter_next(child)
-
- else:
- # BUG: need to set file priorities in backend here
- if dowhat == -1:
- text, color = _("never"), 'darkgrey'
- elif dowhat == 1:
- text, color = _("first"), 'darkgreen'
- else:
- text, color = '', 'black'
- treemodel.set_value(it, 3, text )
- treemodel.set_value(it, 4, color)
-
- def update(self, left, allocated):
- for name, left, total, alloc in itertools.izip(
- self.metainfo.orig_files, left, self.lengths, allocated):
- it = self.filepath_to_iter[name]
- if total == 0:
- p = 1
- else:
- p = (total - left) / total
- self.store.set_value(it, 2, "%.1f" % (int(p * 1000)/10))
-
- def close(self):
- self.win.destroy()
-
-
-class PeerListWindow(object):
-
- def __init__(self, torrent_name, closefunc):
- self.win = Window()
- self.win.connect("destroy", closefunc)
- self.win.set_title( _('Peers for "%s"')%torrent_name)
- self.sw = gtk.ScrolledWindow()
- self.sw.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.sw.set_shadow_type(gtk.SHADOW_IN)
- self.win.add(self.sw)
-
- column_header = [_("IP address"), _("Client"), _("Connection"), _("KB/s down"), _("KB/s up"), _("MB downloaded"), _("MB uploaded"), _("% complete"), _("KB/s est. peer download")]
- pre_size_list = ['666.666.666.666', 'TorrentStorm 1.3', 'bad peer', 66666, 66666, '1666.66', '1666.66', '100.0', 6666]
- numeric_cols = [3,4,5,6,7,8]
- store_types = [gobject.TYPE_STRING]*3 + [gobject.TYPE_INT]*2 + [gobject.TYPE_STRING]*3 + [gobject.TYPE_INT]
-
- if advanced_ui:
- column_header[2:2] = [_("Peer ID")]
- pre_size_list[2:2] = ['-AZ2104-']
- store_types[2:2] = [gobject.TYPE_STRING]
- column_header[5:5] = [_("Interested"),_("Choked"),_("Snubbed")]
- pre_size_list[5:5] = ['*','*','*']
- store_types[5:5] = [gobject.TYPE_STRING]*3
- column_header[9:9] = [_("Interested"),_("Choked"),_("Optimistic upload")]
- pre_size_list[9:9] = ['*','*','*']
- store_types[9:9] = [gobject.TYPE_STRING]*3
- numeric_cols = [4,8,12,13,14,15]
-
- num_columns = len(column_header)
- self.store = gtk.ListStore(*store_types)
- self.store.append(pre_size_list)
-
- def makesortfunc(sort_func):
- def sortfunc(treemodel, iter1, iter2, column):
- a_str = treemodel.get_value(iter1, column)
- b_str = treemodel.get_value(iter2, column)
- if a_str is not None and b_str is not None:
- return sort_func(a_str,b_str)
- else:
- return 0
- return sortfunc
-
- def ip_sort(a_str,b_str):
- for a,b in zip(a_str.split('.'), b_str.split('.')):
- if a == b:
- continue
- if len(a) == len(b):
- return cmp(a,b)
- return cmp(int(a), int(b))
- return 0
-
- def float_sort(a_str,b_str):
- a,b = 0,0
- try: a = float(a_str)
- except ValueError: pass
- try: b = float(b_str)
- except ValueError: pass
- return cmp(a,b)
-
- self.store.set_sort_func(0, makesortfunc(ip_sort), 0)
- for i in range(2,5):
- self.store.set_sort_func(num_columns-i, makesortfunc(float_sort), num_columns-i)
-
- self.treeview = gtk.TreeView(self.store)
- cs = []
- for i, name in enumerate(column_header):
- r = gtk.CellRendererText()
- if i in numeric_cols:
- r.set_property('xalign', 1)
- column = gtk.TreeViewColumn(name, r, text = i)
- column.set_resizable(True)
- column.set_min_width(5)
- column.set_sort_column_id(i)
- self.treeview.append_column(column)
- cs.append(column)
- self.treeview.set_rules_hint(True)
- self.sw.add(self.treeview)
- self.treeview.set_headers_visible(False)
- self.treeview.columns_autosize()
- self.sw.show_all()
- self.treeview.realize()
- for column in cs:
- column.set_fixed_width(column.get_width())
- column.set_sizing(gtk.TREE_VIEW_COLUMN_FIXED)
- self.treeview.set_headers_visible(True)
- self.store.clear()
- self.treeview.get_selection().set_mode(gtk.SELECTION_NONE)
- width = self.treeview.size_request()[0]
- self.win.set_default_size(width+SCROLLBAR_WIDTH, 300)
- self.win.show_all()
- self.prev = []
-
-
- def update(self, peers, bad_peers):
- fields = []
-
- def p_bool(value): return value and '*' or ''
-
- for peer in peers:
- field = []
- field.append(peer['ip'])
-
- client, version = ClientIdentifier.identify_client(peer['id'])
- field.append(client + ' ' + version)
-
- if advanced_ui:
- field.append(zurllib.quote(peer['id']))
-
- field.append(peer['initiation'] == 'R' and _("remote") or _("local"))
- dl = peer['download']
- ul = peer['upload']
-
- for l in (dl, ul):
- rate = l[1]
- if rate > 100:
- field.append(int(round(rate/(2**10))))
- else:
- field.append(0)
- if advanced_ui:
- field.append(p_bool(l[2]))
- field.append(p_bool(l[3]))
- if len(l) > 4:
- field.append(p_bool(l[4]))
- else:
- field.append(p_bool(peer['is_optimistic_unchoke']))
-
- field.append('%.2f'%round(dl[0] / 2**20, 2))
- field.append('%.2f'%round(ul[0] / 2**20, 2))
- field.append('%.1f'%round(int(peer['completed']*1000)/10, 1))
-
- field.append(int(peer['speed']//(2**10)))
-
- fields.append(field)
-
- for (ip, (is_banned, stats)) in bad_peers.iteritems():
- field = []
- field.append(ip)
-
- client, version = ClientIdentifier.identify_client(stats.peerid)
- field.append(client + ' ' + version)
-
- if advanced_ui:
- field.append(zurllib.quote(stats.peerid))
-
- field.append(_("bad peer"))
-
- # the sortable peer list won't take strings in these fields
- field.append(0)
-
- if advanced_ui:
- field.extend([0] * 7) # upRate, * fields
- else:
- field.extend([0] * 1) # upRate
-
- field.append(_("%d ok") % stats.numgood)
- field.append(_("%d bad") % len(stats.bad))
- if is_banned: # completion
- field.append(_("banned"))
- else:
- field.append(_("ok"))
- field.append(0) # peer dl rate
- fields.append(field)
-
- if self.store.get_sort_column_id() < 0:
- # ListStore is unsorted, it might be faster to set only modified fields
- it = self.store.get_iter_first()
- for old, new in itertools.izip(self.prev, fields):
- if old != new:
- for i, value in enumerate(new):
- if value != old[i]:
- self.store.set_value(it, i, value)
- it = self.store.iter_next(it)
- for i in range(len(fields), len(self.prev)):
- self.store.remove(it)
- for i in range(len(self.prev), len(fields)):
- self.store.append(fields[i])
- self.prev = fields
- else:
- # ListStore is sorted, no reason not to to reset all fields
- self.store.clear()
- for field in fields:
- self.store.append(field)
-
-
-
- def close(self):
- self.win.destroy()
-
-
-class TorrentInfoWindow(object):
-
- def __init__(self, torrent_box, closefunc):
- self.win = Window()
- self.torrent_box = torrent_box
- name = self.torrent_box.metainfo.name
- self.win.set_title(_('Info for "%s"')%name)
- self.win.set_size_request(-1,-1)
- self.win.set_border_width(SPACING)
- self.win.set_resizable(False)
- self.win.connect('destroy', closefunc)
- self.vbox = gtk.VBox(spacing=SPACING)
-
- self.table = gtk.Table(rows=4, columns=3, homogeneous=False)
- self.table.set_row_spacings(SPACING)
- self.table.set_col_spacings(SPACING)
- y = 0
-
- def add_item(key, val, y):
- self.table.attach(ralign(gtk.Label(key)), 0, 1, y, y+1)
- v = gtk.Label(val)
- v.set_selectable(True)
- self.table.attach(lalign(v), 1, 2, y, y+1)
-
- add_item(_("Torrent name:"), name, y)
- y+=1
-
- announce = ''
- if self.torrent_box.metainfo.is_trackerless:
- announce = _("(trackerless torrent)")
- else:
- announce = self.torrent_box.metainfo.announce
- add_item(_("Announce url:"), announce, y)
- y+=1
-
- size = Size(self.torrent_box.metainfo.total_bytes)
- num_files = _(", in one file")
- if self.torrent_box.is_batch:
- num_files = _(", in %d files") % len(self.torrent_box.metainfo.sizes)
- add_item(_("Total size:"), str(size)+num_files, y)
- y+=1
-
- if advanced_ui:
- pl = self.torrent_box.metainfo.piece_length
- count, lastlen = divmod(size, pl)
- sizedetail = '%d x %d + %d = %d' % (count, pl, lastlen, int(size))
- add_item(_("Pieces:"), sizedetail, y)
- y+=1
- add_item(_("Info hash:"), self.torrent_box.infohash.encode('hex'), y)
- y+=1
-
- path = self.torrent_box.dlpath
- filename = ''
- if path is None:
- path = ''
- else:
- if not self.torrent_box.is_batch:
- path,filename = os.path.split(self.torrent_box.dlpath)
- if path[-1] != os.sep:
- path += os.sep
- path = path_wrap(path)
- add_item(_("Save in:"), path, y)
- y+=1
-
- if not self.torrent_box.is_batch:
- add_item(_("File name:"), path_wrap(filename), y)
- y+=1
-
- self.vbox.pack_start(self.table)
-
- if self.torrent_box.metainfo.comment not in (None, ''):
- commentbuffer = gtk.TextBuffer()
- commentbuffer.set_text(self.torrent_box.metainfo.comment)
- commenttext = gtk.TextView(commentbuffer)
- commenttext.set_editable(False)
- commenttext.set_cursor_visible(False)
- commenttext.set_wrap_mode(gtk.WRAP_WORD)
- commentscroll = gtk.ScrolledWindow()
- commentscroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- commentscroll.set_shadow_type(gtk.SHADOW_IN)
- commentscroll.add(commenttext)
- self.vbox.pack_start(commentscroll)
-
- self.vbox.pack_start(gtk.HSeparator(), expand=False, fill=False)
-
- self.hbox = gtk.HBox(spacing=SPACING)
- lbbox = gtk.HButtonBox()
- rbbox = gtk.HButtonBox()
- lbbox.set_spacing(SPACING)
-
- if LaunchPath.can_launch_files:
- opendirbutton = IconButton(_("_Open directory"), stock=gtk.STOCK_OPEN)
- opendirbutton.connect('clicked', self.torrent_box.open_dir)
- lbbox.pack_start(opendirbutton, expand=False, fill=False)
- opendirbutton.set_sensitive(self.torrent_box.can_open_dir())
-
- filelistbutton = IconButton(_("Show _file list"), stock='gtk-index')
- if self.torrent_box.is_batch:
- filelistbutton.connect('clicked', self.torrent_box.open_filelist)
- else:
- filelistbutton.set_sensitive(False)
- lbbox.pack_start(filelistbutton, expand=False, fill=False)
-
- closebutton = gtk.Button(stock='gtk-close')
- closebutton.connect('clicked', lambda w: self.close())
- rbbox.pack_end(closebutton, expand=False, fill=False)
-
- self.hbox.pack_start(lbbox, expand=False, fill=False)
- self.hbox.pack_end( rbbox, expand=False, fill=False)
-
- self.vbox.pack_end(self.hbox, expand=False, fill=False)
-
- self.win.add(self.vbox)
-
- self.win.show_all()
-
- def close(self):
- self.win.destroy()
-
-
-class TorrentBox(gtk.EventBox):
- torrent_tip_format = '%s:\n %s\n %s'
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- gtk.EventBox.__init__(self)
- self.infohash = infohash
- self.metainfo = metainfo
- self.completion = completion
- self.main = main
-
- self.main_torrent_dnd_tip = _("drag to reorder")
- self.torrent_menu_tip = _("right-click for menu")
-
- self.set_save_location(dlpath)
-
- self.uptotal = self.main.torrents[self.infohash].uptotal
- self.downtotal = self.main.torrents[self.infohash].downtotal
- if self.downtotal > 0:
- self.up_down_ratio = self.uptotal / self.metainfo.total_bytes
- else:
- self.up_down_ratio = None
-
- self.infowindow = None
- self.filelistwindow = None
- self.is_batch = metainfo.is_batch
- self.menu = None
- self.menu_handler = None
-
- self.vbox = gtk.VBox(homogeneous=False, spacing=SPACING)
- self.label = gtk.Label()
- self.set_name()
-
- self.vbox.pack_start(lalign(self.label), expand=False, fill=False)
-
- self.hbox = gtk.HBox(homogeneous=False, spacing=SPACING)
-
- self.icon = gtk.Image()
- self.icon.set_size_request(-1, 29)
-
- self.iconbox = gtk.VBox()
- self.iconevbox = gtk.EventBox()
- self.iconevbox.add(self.icon)
- self.iconbox.pack_start(self.iconevbox, expand=False, fill=False)
- self.hbox.pack_start(self.iconbox, expand=False, fill=False)
-
- self.vbox.pack_start(self.hbox)
-
- self.infobox = gtk.VBox(homogeneous=False)
-
- self.progressbarbox = gtk.HBox(homogeneous=False, spacing=SPACING)
- self.progressbar = gtk.ProgressBar()
-
- self.reset_progressbar_color()
-
- if self.completion is not None:
- self.progressbar.set_fraction(self.completion)
- if self.completion >= 1:
- done_label = self.make_done_label()
- self.progressbar.set_text(done_label)
- else:
- self.progressbar.set_text('%.1f%%'%(self.completion*100))
- else:
- self.progressbar.set_text('?')
-
- self.progressbarbox.pack_start(self.progressbar,
- expand=True, fill=True)
-
- self.buttonevbox = gtk.EventBox()
- self.buttonbox = gtk.HBox(homogeneous=True, spacing=SPACING)
-
- self.infobutton = gtk.Button()
- self.infoimage = gtk.Image()
- self.infoimage.set_from_stock('bt-info', gtk.ICON_SIZE_BUTTON)
- self.infobutton.add(self.infoimage)
- self.infobutton.connect('clicked', self.open_info)
- self.main.tooltips.set_tip(self.infobutton,
- _("Torrent info"))
-
- self.buttonbox.pack_start(self.infobutton, expand=True)
-
- self.cancelbutton = gtk.Button()
- self.cancelimage = gtk.Image()
- if self.completion is not None and self.completion >= 1:
- self.cancelimage.set_from_stock('bt-remove', gtk.ICON_SIZE_BUTTON)
- self.main.tooltips.set_tip(self.cancelbutton,
- _("Remove torrent"))
- else:
- self.cancelimage.set_from_stock('bt-abort', gtk.ICON_SIZE_BUTTON)
- self.main.tooltips.set_tip(self.cancelbutton,
- _("Abort torrent"))
-
- self.cancelbutton.add(self.cancelimage)
- # not using 'clicked' because we want to check for CTRL key
- self.cancelbutton.connect('button-release-event', self.confirm_remove)
-
- self.buttonbox.pack_start(self.cancelbutton, expand=True, fill=False)
- self.buttonevbox.add(self.buttonbox)
-
- vbuttonbox = gtk.VBox(homogeneous=False)
- vbuttonbox.pack_start(self.buttonevbox, expand=False, fill=False)
- self.hbox.pack_end(vbuttonbox, expand=False, fill=False)
-
- self.infobox.pack_start(self.progressbarbox, expand=False, fill=False)
-
- self.hbox.pack_start(self.infobox, expand=True, fill=True)
- self.add( self.vbox )
-
- self.drag_source_set(gtk.gdk.BUTTON1_MASK,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
- self.connect('drag_data_get', self.drag_data_get)
-
- self.connect('drag_begin' , self.drag_begin )
- self.connect('drag_end' , self.drag_end )
- self.cursor_handler_id = self.connect('enter_notify_event', self.change_cursors)
-
-
- def set_save_location(self, dlpath):
- self.dlpath = dlpath
- updater_infohash = self.main.updater.infohash
- if updater_infohash == self.infohash:
- my_installer_dir = os.path.split(self.dlpath)[0]
- if self.main.updater.installer_dir != my_installer_dir:
- self.main.updater.set_installer_dir(my_installer_dir)
-
-
- def reset_progressbar_color(self):
- # Hack around broken GTK-Wimp theme:
- # make progress bar text always black
- # see task #694
- if is_frozen_exe and self.main.config['progressbar_hack']:
- style = self.progressbar.get_style().copy()
- black = style.black
- self.progressbar.modify_fg(gtk.STATE_PRELIGHT, black)
-
-
- def change_cursors(self, *args):
- # BUG: this is in a handler that is disconnected because the
- # window attributes are None until after show_all() is called
- self.window.set_cursor(gtk.gdk.Cursor(gtk.gdk.HAND2))
- self.buttonevbox.window.set_cursor(gtk.gdk.Cursor(gtk.gdk.LEFT_PTR))
- self.disconnect(self.cursor_handler_id)
-
-
- def drag_data_get(self, widget, context, selection, targetType, eventTime):
- selection.set(selection.target, 8, self.infohash)
-
- def drag_begin(self, *args):
- pass
-
- def drag_end(self, *args):
- self.main.drag_end()
-
- def make_done_label(self, statistics=None):
- s = ''
- if statistics and statistics['timeEst'] is not None:
- s = _(", will seed for %s") % Duration(statistics['timeEst'])
- elif statistics:
- s = _(", will seed indefinitely.")
-
- if self.up_down_ratio is not None:
- done_label = _("Done, share ratio: %d%%") % \
- (self.up_down_ratio*100) + s
- elif statistics is not None:
- done_label = _("Done, %s uploaded") % \
- Size(statistics['upTotal']) + s
- else:
- done_label = _("Done")
-
- return done_label
-
-
- def set_name(self):
- self.label.set_text(self.metainfo.name)
- self.label.set_ellipsize(pango.ELLIPSIZE_END)
-
- def make_menu(self, extra_menu_items=[]):
- if self.menu_handler:
- self.disconnect(self.menu_handler)
-
- ## Basic Info
- menu_items = [ MenuItem(_("Torrent _info" ), func=self.open_info), ]
- open_dir_func = None
- if LaunchPath.can_launch_files and self.can_open_dir():
- open_dir_func = self.open_dir
- menu_items.append( MenuItem(_("_Open directory" ), func=open_dir_func) )
- filelistfunc = None
- if self.is_batch:
- filelistfunc = self.open_filelist
- menu_items.append(MenuItem(_("_File list"), func=filelistfunc))
- if self.torrent_state == RUNNING:
- menu_items.append(MenuItem(_("_Peer list"), func=self.open_peerlist))
- ## end Basic Info
-
- menu_items.append(gtk.SeparatorMenuItem())
-
- ## Settings
- # change save location
- change_save_location_func = None
- if self.torrent_state != RUNNING and self.completion <= 0:
- change_save_location_func = self.change_save_location
- menu_items.append(MenuItem(_("_Change location"),
- func=change_save_location_func))
- # seed forever item
- self.seed_forever_item = gtk.CheckMenuItem(_("_Seed indefinitely"))
- self.reset_seed_forever()
- def sft(widget, *args):
- active = widget.get_active()
- infohash = self.infohash
- for option in ('seed_forever', 'seed_last_forever'):
- self.main.torrentqueue.set_config(option, active, infohash)
- self.main.torrentqueue.set_config(option, active, infohash)
- self.seed_forever_item.connect('toggled', sft)
- menu_items.append(self.seed_forever_item)
- ## end Settings
-
- menu_items.append(gtk.SeparatorMenuItem())
-
- ## Queue state dependent items
- if self.torrent_state == KNOWN:
- menu_items.append( MenuItem(_("Re_start"), func=self.move_to_end ))
- elif self.torrent_state == QUEUED:
- #Here's where we'll put the "Start hash check" menu item
- menu_items.append(MenuItem(_("Download _now"), func=self.start))
- elif self.torrent_state in (RUNNING, RUN_QUEUED):
- # no items for here
- pass
-
- ## Completion dependent items
- if self.completion is not None and self.completion >= 1:
- if self.torrent_state != KNOWN:
- menu_items.append(MenuItem(_("_Finish"), func=self.finish))
- menu_items.append( MenuItem(_("_Remove" ), func=self.confirm_remove))
- else:
- if self.torrent_state in (RUNNING, RUN_QUEUED):
- menu_items.append(MenuItem(_("Download _later"), func=self.move_to_end))
- else:
- #Here's where we'll put the "Seed _later" menu item
- pass
- menu_items.append(MenuItem(_("_Abort" ), func=self.confirm_remove))
-
- ## build the menu
- self.menu = gtk.Menu()
-
- for i in menu_items:
- i.show()
- self.menu.add(i)
-
- self.menu_handler = self.connect_object("event", self.show_menu, self.menu)
-
- def reset_seed_forever(self):
- sfb = False
- d = self.main.torrents[self.infohash].config.getDict()
- if d.has_key('seed_forever'):
- sfb = d['seed_forever']
- self.seed_forever_item.set_active(bool(sfb))
-
- def change_save_location(self, widget=None):
- self.main.change_save_location(self.infohash)
-
- def open_info(self, widget=None):
- if self.infowindow is None:
- self.infowindow = TorrentInfoWindow(self, self.infoclosed)
-
- def infoclosed(self, widget=None):
- self.infowindow = None
-
- def close_info(self):
- if self.infowindow is not None:
- self.infowindow.close()
-
- def open_filelist(self, widget):
- if not self.is_batch:
- return
- if self.filelistwindow is None:
- self.filelistwindow = FileListWindow(self.metainfo,
- self.filelistclosed)
- self.main.torrentqueue.check_completion(self.infohash, True)
-
- def filelistclosed(self, widget):
- self.filelistwindow = None
-
- def close_filelist(self):
- if self.filelistwindow is not None:
- self.filelistwindow.close()
-
- def close_child_windows(self):
- self.close_info()
- self.close_filelist()
-
- def destroy(self):
- if self.menu is not None:
- self.menu.destroy()
- self.menu = None
- gtk.EventBox.destroy(self)
-
- def show_menu(self, widget, event):
- if event.type == gtk.gdk.BUTTON_PRESS and event.button == 3:
- widget.popup(None, None, None, event.button, event.time)
- return True
- return False
-
- def _short_path(self, dlpath):
- path_length = 40
- sep = '...'
- ret = os.path.split(dlpath)[0]
- if len(ret) > path_length+len(sep):
- return ret[:int(path_length/2)]+sep+ret[-int(path_length/2):]
- else:
- return ret
-
- def get_path_to_open(self):
- path = self.dlpath
- if not self.is_batch:
- path = os.path.split(self.dlpath)[0]
- return path
-
- def can_open_dir(self):
- return os.access(self.get_path_to_open(), os.F_OK|os.R_OK)
-
- def open_dir(self, widget):
- LaunchPath.launchdir(self.get_path_to_open())
-
- def confirm_remove(self, widget, event=None):
- if event is not None and event.get_state() & gtk.gdk.CONTROL_MASK:
- self.remove()
- else:
- message = _('Are you sure you want to remove "%s"?') % self.metainfo.name
- if self.completion >= 1:
- if self.up_down_ratio is not None:
- message = _("Your share ratio for this torrent is %d%%. ")%(self.up_down_ratio*100) + message
- else:
- message = _("You have uploaded %s to this torrent. ")%(Size(self.uptotal)) + message
-
- d = MessageDialog(self.main.mainwindow,
- _("Remove this torrent?"),
- message,
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_OK_CANCEL,
- yesfunc=self.remove,
- default=gtk.RESPONSE_OK,
- )
-
- def remove(self):
- self.main.torrentqueue.remove_torrent(self.infohash)
-
-
-class KnownTorrentBox(TorrentBox):
-
- torrent_state = KNOWN
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- TorrentBox.__init__(self, infohash, metainfo, dlpath, completion, main)
-
- status_tip = ''
- if completion >= 1:
- self.icon.set_from_stock('bt-finished', gtk.ICON_SIZE_LARGE_TOOLBAR)
- status_tip = _("Finished")
- known_torrent_dnd_tip = _("drag into list to seed")
- else:
- self.icon.set_from_stock('bt-broken', gtk.ICON_SIZE_LARGE_TOOLBAR)
- status_tip = _("Failed")
- known_torrent_dnd_tip = _("drag into list to resume")
-
- self.main.tooltips.set_tip(self.iconevbox,
- self.torrent_tip_format % (status_tip,
- known_torrent_dnd_tip,
- self.torrent_menu_tip))
- self.make_menu()
- self.show_all()
-
- def move_to_end(self, widget):
- self.main.change_torrent_state(self.infohash, QUEUED)
-
-
-class DroppableTorrentBox(TorrentBox):
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- TorrentBox.__init__(self, infohash, metainfo, dlpath, completion, main)
-
- self.drag_dest_set(gtk.DEST_DEFAULT_DROP,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
-
- self.connect('drag_data_received', self.drag_data_received)
- self.connect('drag_motion', self.drag_motion)
- self.index = None
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
- if targetType == BT_TARGET_TYPE:
- half_height = self.size_request()[1] // 2
- where = cmp(y, half_height)
- if where == 0: where = 1
- self.parent.put_infohash_at_child(selection.data, self, where)
- else:
- self.main.accept_dropped_file(widget, context, x, y, selection, targetType, time)
-
- def drag_motion(self, widget, context, x, y, time):
- self.get_current_index()
- half_height = self.size_request()[1] // 2
- if y < half_height:
- self.parent.highlight_before_index(self.index)
- else:
- self.parent.highlight_after_index(self.index)
- return False
-
- def drag_end(self, *args):
- self.parent.highlight_child()
- TorrentBox.drag_end(self, *args)
-
- def get_current_index(self):
- self.index = self.parent.get_index_from_child(self)
-
-
-class QueuedTorrentBox(DroppableTorrentBox):
- icon_name = 'bt-queued'
- torrent_state = QUEUED
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- DroppableTorrentBox.__init__(self, infohash, metainfo, dlpath, completion, main)
-
- self.state_name = _("Waiting")
- self.main.tooltips.set_tip(self.iconevbox,
- self.torrent_tip_format % (self.state_name,
- self.main_torrent_dnd_tip,
- self.torrent_menu_tip))
-
- self.icon.set_from_stock(self.icon_name, gtk.ICON_SIZE_LARGE_TOOLBAR)
- self.make_menu()
- self.show_all()
-
- def start(self, widget):
- self.main.runbox.put_infohash_last(self.infohash)
-
- def finish(self, widget):
- self.main.change_torrent_state(self.infohash, KNOWN)
-
-
-class PausedTorrentBox(DroppableTorrentBox):
- icon_name = 'bt-paused'
- torrent_state = RUN_QUEUED
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- DroppableTorrentBox.__init__(self, infohash, metainfo, dlpath, completion, main)
-
- self.state_name = _("Paused")
- self.main.tooltips.set_tip(self.iconevbox,
- self.torrent_tip_format % (self.state_name,
- self.main_torrent_dnd_tip,
- self.torrent_menu_tip))
-
- self.icon.set_from_stock(self.icon_name, gtk.ICON_SIZE_LARGE_TOOLBAR)
- self.make_menu()
- self.show_all()
-
- def move_to_end(self, widget):
- self.main.change_torrent_state(self.infohash, QUEUED)
-
- def finish(self, widget):
- self.main.change_torrent_state(self.infohash, KNOWN)
-
- def update_status(self, statistics):
- # in case the TorrentQueue thread calls widget.update_status()
- # before the GUI has changed the torrent widget to a
- # RunningTorrentBox
- pass
-
-
-class RunningTorrentBox(PausedTorrentBox):
- torrent_state = RUNNING
-
- def __init__(self, infohash, metainfo, dlpath, completion, main):
- DroppableTorrentBox.__init__(self, infohash, metainfo, dlpath, completion, main)
-
- self.main.tooltips.set_tip(self.iconevbox,
- self.torrent_tip_format % (_("Running"),
- self.main_torrent_dnd_tip,
- self.torrent_menu_tip))
-
- self.seed = False
- self.peerlistwindow = None
- self.update_peer_list_flag = 0
-
- self.icon.set_from_stock('bt-running', gtk.ICON_SIZE_LARGE_TOOLBAR)
-
- self.rate_label_box = gtk.HBox(homogeneous=True)
-
- self.up_rate = gtk.Label()
- self.down_rate = gtk.Label()
- self.rate_label_box.pack_start(lalign(self.up_rate ),
- expand=True, fill=True)
- self.rate_label_box.pack_start(lalign(self.down_rate),
- expand=True, fill=True)
-
- self.infobox.pack_start(self.rate_label_box)
-
- if advanced_ui:
- self.extrabox = gtk.VBox(homogeneous=False)
- #self.extrabox = self.vbox
-
- self.up_curr = FancyLabel(_("Current up: %s" ), 0)
- self.down_curr = FancyLabel(_("Current down: %s"), 0)
- self.curr_box = gtk.HBox(homogeneous=True)
- self.curr_box.pack_start(lalign(self.up_curr ), expand=True, fill=True)
- self.curr_box.pack_start(lalign(self.down_curr), expand=True, fill=True)
- self.extrabox.pack_start(self.curr_box)
-
- self.up_prev = FancyLabel(_("Previous up: %s" ), 0)
- self.down_prev = FancyLabel(_("Previous down: %s"), 0)
- self.prev_box = gtk.HBox(homogeneous=True)
- self.prev_box.pack_start(lalign(self.up_prev ), expand=True, fill=True)
- self.prev_box.pack_start(lalign(self.down_prev), expand=True, fill=True)
- self.extrabox.pack_start(self.prev_box)
-
- self.share_ratio = FancyLabel(_("Share ratio: %0.02f%%"), 0)
- self.extrabox.pack_start(lalign(self.share_ratio))
-
- self.peer_info = FancyLabel(_("%s peers, %s seeds. Totals from "
- "tracker: %s"), 0, 0, 'NA')
- self.extrabox.pack_start(lalign(self.peer_info))
-
- self.dist_copies = FancyLabel(_("Distributed copies: %d; Next: %s"), 0, '')
- self.extrabox.pack_start(lalign(self.dist_copies))
-
- self.piece_info = FancyLabel(_("Pieces: %d total, %d complete, "
- "%d partial, %d active (%d empty)"), *(0,)*5)
- self.extrabox.pack_start(lalign(self.piece_info))
-
- self.bad_info = FancyLabel(_("%d bad pieces + %s in discarded requests"), 0, 0)
- self.extrabox.pack_start(lalign(self.bad_info))
-
- # extra info
-
- pl = self.metainfo.piece_length
- tl = self.metainfo.total_bytes
- count, lastlen = divmod(tl, pl)
- self.piece_count = count + (lastlen > 0)
-
- self.infobox.pack_end(self.extrabox, expand=False, fill=False)
-
- self.make_menu()
- self.show_all()
-
-
- def change_to_completed(self):
- self.completion = 1.0
- self.cancelimage.set_from_stock('bt-remove', gtk.ICON_SIZE_BUTTON)
- self.main.tooltips.set_tip(self.cancelbutton,
- _("Remove torrent"))
-
- updater_infohash = self.main.updater.infohash
- if updater_infohash == self.infohash:
- self.main.updater.start_install()
-
- self.make_menu()
-
- def close_child_windows(self):
- TorrentBox.close_child_windows(self)
- self.close_peerlist()
-
- def open_filelist(self, widget):
- if not self.is_batch:
- return
- if self.filelistwindow is None:
- self.filelistwindow = FileListWindow(self.metainfo,
- self.filelistclosed)
- self.main.make_statusrequest()
-
- def open_peerlist(self, widget):
- if self.peerlistwindow is None:
- self.peerlistwindow = PeerListWindow(self.metainfo.name,
- self.peerlistclosed)
- self.main.make_statusrequest()
-
- def peerlistclosed(self, widget):
- self.peerlistwindow = None
- self.update_peer_list_flag = 0
-
- def close_peerlist(self):
- if self.peerlistwindow is not None:
- self.peerlistwindow.close()
-
- rate_label = ': %s'
- eta_label = '?'
- done_label = _("Done")
- progress_bar_label = _("%.1f%% done, %s remaining")
- down_rate_label = _("Download rate")
- up_rate_label = _("Upload rate" )
-
- def update_status(self, statistics):
- fractionDone = statistics.get('fractionDone')
- activity = statistics.get('activity')
-
- self.main.set_title(torrentName=self.metainfo.name,
- fractionDone=fractionDone)
-
- dt = self.downtotal
- if statistics.has_key('downTotal'):
- dt += statistics['downTotal']
-
- ut = self.uptotal
- if statistics.has_key('upTotal'):
- ut += statistics['upTotal']
-
- if dt > 0:
- self.up_down_ratio = ut / self.metainfo.total_bytes
-
- done_label = self.done_label
- eta_label = self.eta_label
- if 'numPeers' in statistics:
- eta = statistics.get('timeEst')
- if eta is not None:
- eta_label = Duration(eta)
- if fractionDone == 1:
- done_label = self.make_done_label(statistics)
-
- if fractionDone == 1:
- self.progressbar.set_fraction(1)
- self.progressbar.set_text(done_label)
- self.reset_seed_forever()
- if not self.completion >= 1:
- self.change_to_completed()
- else:
- self.progressbar.set_fraction(fractionDone)
- progress_bar_label = self.progress_bar_label % \
- (int(fractionDone*1000)/10, eta_label)
- self.progressbar.set_text(progress_bar_label)
-
-
- if 'numPeers' not in statistics:
- return
-
- self.down_rate.set_text(self.down_rate_label+self.rate_label %
- Rate(statistics['downRate']))
- self.up_rate.set_text (self.up_rate_label+self.rate_label %
- Rate(statistics['upRate']))
-
- if advanced_ui:
- if self.up_down_ratio is not None:
- self.share_ratio.set_value(self.up_down_ratio*100)
-
- num_seeds = statistics['numSeeds']
- if self.seed:
- num_seeds = statistics['numOldSeeds'] = 0 # !@# XXX
-
- if statistics['trackerPeers'] is not None:
- totals = '%d/%d' % (statistics['trackerPeers'],
- statistics['trackerSeeds'])
- else:
- totals = _("NA")
- self.peer_info.set_value(statistics['numPeers'], num_seeds, totals)
-
- self.up_curr.set_value(str(Size(statistics['upTotal'])))
- self.down_curr.set_value(str(Size(statistics['downTotal'])))
-
- self.up_prev.set_value(str(Size(self.uptotal)))
- self.down_prev.set_value(str(Size(self.downtotal)))
-
- # refresh extra info
- self.piece_info.set_value(self.piece_count,
- statistics['storage_numcomplete'],
- statistics['storage_dirty'],
- statistics['storage_active'],
- statistics['storage_new'] )
-
- self.dist_copies.set_value( statistics['numCopies'], ', '.join(["%d:%.1f%%" % (a, int(b*1000)/10) for a, b in zip(itertools.count(int(statistics['numCopies']+1)), statistics['numCopyList'])]))
-
- self.bad_info.set_value(statistics['storage_numflunked'], Size(statistics['discarded']))
-
- if self.peerlistwindow is not None:
- if self.update_peer_list_flag == 0:
- spew = statistics.get('spew')
- if spew is not None:
- self.peerlistwindow.update(spew, statistics['bad_peers'])
- self.update_peer_list_flag = (self.update_peer_list_flag + 1) % 4
- if self.filelistwindow is not None:
- if 'files_left' in statistics:
- self.filelistwindow.update(statistics['files_left'],
- statistics['files_allocated'])
-
-
-class DroppableHSeparator(PaddedHSeparator):
-
- def __init__(self, box, spacing=SPACING):
- PaddedHSeparator.__init__(self, spacing)
- self.box = box
- self.main = box.main
-
- self.drag_dest_set(gtk.DEST_DEFAULT_DROP,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
-
- self.connect('drag_data_received', self.drag_data_received)
- self.connect('drag_motion' , self.drag_motion )
-
- def drag_highlight(self):
- self.sep.drag_highlight()
- self.main.add_unhighlight_handle()
-
- def drag_unhighlight(self):
- self.sep.drag_unhighlight()
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
- if targetType == BT_TARGET_TYPE:
- self.box.drop_on_separator(self, selection.data)
- else:
- self.main.accept_dropped_file(widget, context, x, y, selection, targetType, time)
-
- def drag_motion(self, wid, context, x, y, time):
- self.drag_highlight()
- return False
-
-
-class DroppableBox(HSeparatedBox):
- def __init__(self, main, spacing=0):
- HSeparatedBox.__init__(self, spacing=spacing)
- self.main = main
- self.drag_dest_set(gtk.DEST_DEFAULT_DROP,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
- self.connect('drag_data_received', self.drag_data_received)
- self.connect('drag_motion', self.drag_motion)
-
- def drag_motion(self, widget, context, x, y, time):
- return False
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
- pass
-
-
-class KnownBox(DroppableBox):
-
- def __init__(self, main, spacing=0):
- DroppableBox.__init__(self, main, spacing=spacing)
- self.drag_dest_set(gtk.DEST_DEFAULT_DROP,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
-
- def pack_start(self, widget, *args, **kwargs):
- old_len = len(self.get_children())
- DroppableBox.pack_start(self, widget, *args, **kwargs)
- if old_len <= 0:
- self.main.maximize_known_pane()
- self.main.knownscroll.scroll_to_bottom()
-
- def remove(self, widget):
- DroppableBox.remove(self, widget)
- new_len = len(self.get_children())
- if new_len == 0:
- self.main.maximize_known_pane()
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
- if targetType == BT_TARGET_TYPE:
- infohash = selection.data
- self.main.finish(infohash)
- else:
- self.main.accept_dropped_file(widget, context, x, y, selection, targetType, time)
-
- def drag_motion(self, widget, context, x, y, time):
- self.main.drag_highlight(widget=self)
-
- def drag_highlight(self):
- self.main.knownscroll.drag_highlight()
- self.main.add_unhighlight_handle()
-
- def drag_unhighlight(self):
- self.main.knownscroll.drag_unhighlight()
-
-
-class RunningAndQueueBox(gtk.VBox):
-
- def __init__(self, main, **kwargs):
- gtk.VBox.__init__(self, **kwargs)
- self.main = main
-
- def drop_on_separator(self, sep, infohash):
- self.main.change_torrent_state(infohash, QUEUED, 0)
-
- def highlight_between(self):
- self.drag_highlight()
-
- def drag_highlight(self):
- self.get_children()[1].drag_highlight()
-
- def drag_unhighlight(self):
- self.get_children()[1].drag_unhighlight()
-
-
-class SpacerBox(DroppableBox):
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
- if targetType == BT_TARGET_TYPE:
- infohash = selection.data
- self.main.queuebox.put_infohash_last(infohash)
- else:
- self.main.accept_dropped_file(widget, context, x, y, selection, targetType, time)
-
- return True
-
-BEFORE = -1
-AFTER = 1
-
-class ReorderableBox(DroppableBox):
-
- def new_separator(self):
- return DroppableHSeparator(self)
-
- def __init__(self, main):
- DroppableBox.__init__(self, main)
- self.main = main
-
- self.drag_dest_set(gtk.DEST_DEFAULT_DROP,
- TARGET_ALL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
-
- self.connect('drag_data_received', self.drag_data_received)
- self.connect('drag_motion' , self.drag_motion)
-
- def drag_data_received(self, widget, context, x, y, selection, targetType, time):
-
- if targetType == BT_TARGET_TYPE:
- half_height = self.size_request()[1] // 2
- if y < half_height:
- self.put_infohash_first(selection.data)
- else:
- self.put_infohash_last(selection.data)
- else:
- self.main.accept_dropped_file(widget, context, x, y, selection, targetType, time)
- return True
-
- def drag_motion(self, widget, context, x, y, time):
- return False
-
- def drag_highlight(self):
- final = self.get_children()[-1]
- final.drag_highlight()
- self.main.add_unhighlight_handle()
-
- def drag_unhighlight(self):
- self.highlight_child(index=None)
- self.parent.drag_unhighlight()
-
- def highlight_before_index(self, index):
- self.drag_unhighlight()
- children = self._get_children()
- if index > 0:
- children[index*2 - 1].drag_highlight()
- else:
- self.highlight_at_top()
-
- def highlight_after_index(self, index):
- self.drag_unhighlight()
- children = self._get_children()
- if index*2 < len(children)-1:
- children[index*2 + 1].drag_highlight()
- else:
- self.highlight_at_bottom()
-
- def highlight_child(self, index=None):
- for i, child in enumerate(self._get_children()):
- if index is not None and i == index*2:
- child.drag_highlight()
- else:
- child.drag_unhighlight()
-
-
- def drop_on_separator(self, sep, infohash):
- children = self._get_children()
- for i, child in enumerate(children):
- if child == sep:
- reference_child = children[i-1]
- self.put_infohash_at_child(infohash, reference_child, AFTER)
- break
-
-
- def get_queue(self):
- queue = []
- c = self.get_children()
- for t in c:
- queue.append(t.infohash)
- return queue
-
- def put_infohash_first(self, infohash):
- self.highlight_child()
- children = self.get_children()
- if len(children) > 1 and infohash == children[0].infohash:
- return
-
- self.put_infohash_at_index(infohash, 0)
-
- def put_infohash_last(self, infohash):
- self.highlight_child()
- children = self.get_children()
- end = len(children)
- if len(children) > 1 and infohash == children[end-1].infohash:
- return
-
- self.put_infohash_at_index(infohash, end)
-
- def put_infohash_at_child(self, infohash, reference_child, where):
- self.highlight_child()
- if infohash == reference_child.infohash:
- return
-
- target_index = self.get_index_from_child(reference_child)
- if where == AFTER:
- target_index += 1
- self.put_infohash_at_index(infohash, target_index)
-
- def get_index_from_child(self, child):
- c = self.get_children()
- ret = -1
- try:
- ret = c.index(child)
- except ValueError:
- pass
- return ret
-
- def highlight_at_top(self):
- raise NotImplementedError
-
- def highlight_at_bottom(self):
- raise NotImplementedError
-
- def put_infohash_at_index(self, infohash, end):
- raise NotImplementedError
-
-class RunningBox(ReorderableBox):
-
- def put_infohash_at_index(self, infohash, target_index):
- #print 'RunningBox.put_infohash_at_index', infohash.encode('hex')[:8], target_index
-
- l = self.get_queue()
- replaced = None
- if l:
- replaced = l[-1]
- self.main.confirm_replace_running_torrent(infohash, replaced,
- target_index)
-
- def highlight_at_top(self):
- pass
- # BUG: Don't know how I will indicate in the UI that the top of the list is highlighted
-
- def highlight_at_bottom(self):
- self.parent.highlight_between()
-
-
-class QueuedBox(ReorderableBox):
-
- def put_infohash_at_index(self, infohash, target_index):
- #print 'want to put', infohash.encode('hex'), 'at', target_index
- self.main.change_torrent_state(infohash, QUEUED, target_index)
-
- def highlight_at_top(self):
- self.parent.highlight_between()
-
- def highlight_at_bottom(self):
- pass
- # BUG: Don't know how I will indicate in the UI that the bottom of the list is highlighted
-
-
-
-class Struct(object):
- pass
-
-
-class SearchField(gtk.Entry):
- def __init__(self, default_text, visit_url_func):
- gtk.Entry.__init__(self)
- self.default_text = default_text
- self.visit_url_func = visit_url_func
- self.set_text(self.default_text)
- self.set_size_request(150, -1)
-
- # default gtk Entry dnd processing is broken on linux!
- # - default Motion handling causes asyncs
- # - there's no way to filter the default text dnd
- # see the parent window for a very painful work-around
- self.drag_dest_unset()
-
- self.connect('key-press-event', self.check_for_enter)
- self.connect('button-press-event', self.begin_edit)
- self.search_completion = gtk.EntryCompletion()
- self.search_completion.set_text_column(0)
- self.search_store = gtk.ListStore(gobject.TYPE_STRING)
- self.search_completion.set_model(self.search_store)
- self.set_completion(self.search_completion)
- self.reset_text()
- self.timeout_id = None
-
- def begin_edit(self, *args):
- if self.get_text() == self.default_text:
- self.set_text('')
-
- def check_for_enter(self, widget, event):
- if event.keyval in (gtk.keysyms.Return, gtk.keysyms.KP_Enter):
- self.search()
-
- def reset_text(self):
- self.set_text(self.default_text)
-
- def search(self, *args):
- search_term = self.get_text()
- if search_term and search_term != self.default_text:
- self.search_store.append([search_term])
- search_url = SEARCH_URL % {'query' :zurllib.quote(search_term),
- 'client':'M-%s'%version.replace('.','-')}
-
- self.timeout_id = gobject.timeout_add(2000, self.resensitize)
- self.set_sensitive(False)
- self.visit_url_func(search_url, callback=self.resensitize)
- else:
- self.reset_text()
- self.select_region(0, -1)
- self.grab_focus()
-
- def resensitize(self):
- self.set_sensitive(True)
- self.reset_text()
- if self.timeout_id is not None:
- gobject.source_remove(self.timeout_id)
- self.timeout_id = None
-
-
-class DownloadInfoFrame(object):
-
- def __init__(self, config, torrentqueue):
- self.config = config
- if self.config['save_in'] == '':
- self.config['save_in'] = smart_dir('')
-
- self.torrentqueue = torrentqueue
- self.torrents = {}
- self.running_torrents = {}
- self.lists = {}
- self.update_handle = None
- self.unhighlight_handle = None
- self.custom_size = False
- self.child_windows = {}
- self.postponed_save_windows = []
- self.helpwindow = None
- self.errordialog = None
-
- self.mainwindow = Window(gtk.WINDOW_TOPLEVEL)
-
- #tray icon
- self.trayicon = TrayIcon(not self.config['start_minimized'],
- toggle_func=self.toggle_shown,
- quit_func=self.quit)
- self.traythread = threading.Thread(target=self.trayicon.enable,
- args=())
- self.traythread.setDaemon(True)
-
- if os.name == "nt":
- # gtk has no way to check this?
- self.iconized = False
- self.mainwindow.connect('window-state-event', self.window_event)
-
- if self.config['start_minimized']:
- self.mainwindow.iconify()
-
- gtk.gdk.threads_enter()
-
- self.mainwindow.set_border_width(0)
-
- self.set_seen_remote_connections(False)
- self.set_seen_connections(False)
-
- self.mainwindow.drag_dest_set(gtk.DEST_DEFAULT_ALL,
- TARGET_EXTERNAL,
- gtk.gdk.ACTION_MOVE|gtk.gdk.ACTION_COPY)
-
- self.mainwindow.connect('drag_leave' , self.drag_leave )
- self.mainwindow.connect('drag_data_received', self.accept_dropped_file)
-
- self.mainwindow.set_size_request(WINDOW_WIDTH, -1)
-
- self.mainwindow.connect('destroy', self.cancel)
-
- self.mainwindow.connect('size-allocate', self.size_was_allocated)
-
- self.accel_group = gtk.AccelGroup()
-
- self.mainwindow.add_accel_group(self.accel_group)
-
- #self.accel_group.connect(ord('W'), gtk.gdk.CONTROL_MASK, gtk.ACCEL_LOCKED,
- # lambda *args: self.mainwindow.destroy())
-
- self.tooltips = gtk.Tooltips()
-
- self.logbuffer = LogBuffer()
- self.log_text(_("%s started")%app_name, severity=None)
-
- self.box1 = gtk.VBox(homogeneous=False, spacing=0)
-
- self.box2 = gtk.VBox(homogeneous=False, spacing=0)
- self.box2.set_border_width(SPACING)
-
- self.menubar = gtk.MenuBar()
- self.box1.pack_start(self.menubar, expand=False, fill=False)
-
- self.ssbutton = StopStartButton(self)
-
- # keystrokes used: A D F H L N O P Q S U X (E)
-
- quit_menu_label = _("_Quit")
- if os.name == 'nt':
- quit_menu_label = _("E_xit")
-
- file_menu_items = ((_("_Open torrent file"), self.select_torrent_to_open),
- (_("Open torrent _URL"), self.enter_url_to_open),
- (_("Make _new torrent" ), self.make_new_torrent),
-
- ('----' , None),
- (_("_Pause/Play"), self.ssbutton.toggle),
- ('----' , None),
- (quit_menu_label , lambda w: self.mainwindow.destroy()),
- )
- view_menu_items = ((_("Show/Hide _finished torrents"), self.toggle_known),
- # BUG: if you reorder this menu, see def set_custom_size() first
- (_("_Resize window to fit"), lambda w: self.resize_to_fit()),
- ('----' , None),
- (_("_Log") , lambda w: self.open_window('log')),
- # 'View log of all download activity',
- #('----' , None),
- (_("_Settings") , lambda w: self.open_window('settings')),
- #'Change download behavior and network settings',
- )
- help_menu_items = ((_("_Help") , self.open_help),
- #(_("_Help Window") , lambda w: self.open_window('help')),
- (_("_About") , lambda w: self.open_window('about')),
- (_("_Donate") , lambda w: self.donate()),
- #(_("Rais_e") , lambda w: self.raiseerror()),
- )
-
- self.filemenu = gtk.MenuItem(_("_File"))
-
- self.filemenu.set_submenu(build_menu(file_menu_items, self.accel_group))
- self.filemenu.show()
-
- self.viewmenu = gtk.MenuItem(_("_View"))
- self.viewmenu.set_submenu(build_menu(view_menu_items, self.accel_group))
- self.viewmenu.show()
-
- self.helpmenu = gtk.MenuItem(_("_Help"))
- self.helpmenu.set_submenu(build_menu(help_menu_items, self.accel_group))
- self.helpmenu.show()
-
- if os.name != 'nt':
- self.helpmenu.set_right_justified(True)
-
- self.menubar.append(self.filemenu)
- self.menubar.append(self.viewmenu)
- self.menubar.append(self.helpmenu)
-
- self.menubar.show()
-
- self.header = gtk.HBox(homogeneous=False)
-
- self.box1.pack_start(self.box2, expand=False, fill=False)
-
- # control box: rate slider, start-stop button, search widget, status light
- self.controlbox = gtk.HBox(homogeneous=False)
-
- controlbox_padding = SPACING//2
-
- # stop-start button
- self.controlbox.pack_start(malign(self.ssbutton),
- expand=False, fill=False)
-
- # rate slider
- self.rate_slider_box = RateSliderBox(self.config, self.torrentqueue)
- self.controlbox.pack_start(self.rate_slider_box,
- expand=True, fill=True,
- padding=controlbox_padding)
-
- self.controlbox.pack_start(gtk.VSeparator(), expand=False, fill=False,
- padding=controlbox_padding)
-
- # search box
- self.search_field = SearchField(_("Search for torrents"), self.visit_url)
- sfa = gtk.Alignment(xalign=0, yalign=0.5, xscale=1, yscale=0)
- sfa.add(self.search_field)
- self.controlbox.pack_start(sfa,
- expand=False, fill=False, padding=controlbox_padding)
-
- # separator
- self.controlbox.pack_start(gtk.VSeparator(), expand=False, fill=False,
- padding=controlbox_padding)
-
- # status light
- self.status_light = StatusLight(self)
-
- self.controlbox.pack_start(malign(self.status_light),
- expand=False, fill=False)
-
- self.box2.pack_start(self.controlbox,
- expand=False, fill=False, padding=0)
- # end control box
-
- self.paned = gtk.VPaned()
-
- self.knownscroll = ScrolledWindow()
- self.knownscroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.knownscroll.set_shadow_type(gtk.SHADOW_NONE)
- self.knownscroll.set_size_request(-1, SPACING)
-
- self.knownbox = KnownBox(self)
- self.knownbox.set_border_width(SPACING)
-
- self.knownscroll.add_with_viewport(self.knownbox)
- self.paned.pack1(self.knownscroll, resize=False, shrink=True)
-
-
- self.mainscroll = AutoScrollingWindow()
- self.mainscroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.mainscroll.set_shadow_type(gtk.SHADOW_NONE)
- self.mainscroll.set_size_request(-1, SPACING)
-
- self.scrollbox = RunningAndQueueBox(self, homogeneous=False)
- self.scrollbox.set_border_width(SPACING)
-
- self.runbox = RunningBox(self)
- self.scrollbox.pack_start(self.runbox, expand=False, fill=False)
-
- self.scrollbox.pack_start(DroppableHSeparator(self.scrollbox), expand=False, fill=False)
-
- self.queuebox = QueuedBox(self)
- self.scrollbox.pack_start(self.queuebox, expand=False, fill=False)
-
- self.scrollbox.pack_start(SpacerBox(self), expand=True, fill=True)
-
- self.mainscroll.add_with_viewport(self.scrollbox)
-
- self.paned.pack2(self.mainscroll, resize=True, shrink=False)
-
- self.box1.pack_start(self.paned)
-
- self.box1.show_all()
-
- self.mainwindow.add(self.box1)
-
- self.set_title()
- self.set_size()
-
- self.mainwindow.show()
-
- self.paned.set_position(0)
- self.search_field.grab_focus()
-
- self.updater = NewVersion.Updater(
- gtk_wrap,
- self.new_version,
- self.torrentqueue.start_new_torrent,
- self.confirm_install_new_version ,
- self.global_error ,
- self.config['new_version'] ,
- self.config['current_version'] )
-
- self.nag()
-
- gtk.gdk.threads_leave()
-
- def window_event(self, widget, event, *args):
- if event.changed_mask == gtk.gdk.WINDOW_STATE_ICONIFIED:
- if self.config['minimize_to_tray']:
- if self.iconized == False:
- self.mainwindow.hide()
- self.trayicon.set_toggle_state(self.iconized)
- self.iconized = not self.iconized
-
- def drag_leave(self, *args):
- self.drag_end()
-
- def make_new_torrent(self, widget=None):
- btspawn(self.torrentqueue, 'maketorrent')
-
- def accept_dropped_file(self, widget, context, x, y, selection,
- targetType, time):
- if targetType == EXTERNAL_FILE_TYPE:
- d = selection.data.strip()
- file_uris = d.split('\r\n')
- for file_uri in file_uris:
- # this catches non-url entries, I've seen "\x00" at the end of lists
- if file_uri.find(':/') != -1:
- file_name = zurllib.url2pathname(file_uri)
- file_name = file_name[7:]
- if os.name == 'nt':
- file_name = file_name.strip('\\')
- self.open_torrent( file_name )
- elif targetType == EXTERNAL_STRING_TYPE:
-
- data = selection.data.strip()
-
- # size must be > 0,0 for the intersection code to register it
- drop_rect = gtk.gdk.Rectangle(x, y, 1, 1)
- if ((self.search_field.intersect(drop_rect) is not None) and
- (not data.lower().endswith(".torrent"))):
-
- client_point = self.mainwindow.translate_coordinates(self.search_field, x, y)
- layout_offset = self.search_field.get_layout_offsets()
- point = []
- # subtract (not add) the offset, because we're hit-testing the layout, not the widget
- point.append(client_point[0] - layout_offset[0])
- point.append(client_point[1] - layout_offset[1])
- # ha ha ha. pango is so ridiculous
- point[0] *= pango.SCALE
- point[1] *= pango.SCALE
- layout = self.search_field.get_layout()
- position = layout.xy_to_index(*point)
- self.search_field.insert_text(data, position[0])
- else:
- self.open_url(data)
-
- def drag_highlight(self, widget=None):
- widgets = (self.knownbox, self.runbox, self.queuebox)
- for w in widgets:
- if w != widget:
- w.drag_unhighlight()
- for w in widgets:
- if w == widget:
- w.drag_highlight()
- self.add_unhighlight_handle()
-
- def drag_end(self):
- self.drag_highlight(widget=None)
- self.mainscroll.stop_scrolling()
-
- def set_title(self, torrentName=None, fractionDone=None):
- title = app_name
- trunc = '...'
- sep = ': '
-
- if self.config['pause']:
- title += sep+_("(stopped)")
- elif len(self.running_torrents) == 1 and torrentName and \
- fractionDone is not None:
- maxlen = WINDOW_TITLE_LENGTH - len(app_name) - len(trunc) - len(sep)
- if len(torrentName) > maxlen:
- torrentName = torrentName[:maxlen] + trunc
- title = '%s%s%0.1f%%%s%s'% (app_name,
- sep,
- (int(fractionDone*1000)/10),
- sep,
- torrentName)
- elif len(self.running_torrents) > 1:
- title += sep+_("(multiple)")
-
- if self.mainwindow.get_title() != title:
- self.mainwindow.set_title(title)
- if self.trayicon.get_tooltip() != title:
- self.trayicon.set_tooltip(title)
-
- def _guess_size(self):
- paned_height = self.scrollbox.size_request()[1]
- if hasattr(self.paned, 'style_get_property'):
- paned_height += self.paned.style_get_property('handle-size')
- else:
- paned_height += 5
- paned_height += self.paned.get_position()
- paned_height += 4 # fudge factor, probably from scrolled window beveling ?
- paned_height = max(paned_height, MIN_MULTI_PANE_HEIGHT)
-
- new_height = self.menubar.size_request()[1] + \
- self.box2.size_request()[1] + \
- paned_height
- new_height = min(new_height, MAX_WINDOW_HEIGHT)
- new_width = max(self.scrollbox.size_request()[0] + SCROLLBAR_WIDTH, WINDOW_WIDTH)
- return new_width, new_height
-
- def set_size(self):
- if not self.custom_size:
- self.mainwindow.resize(*self._guess_size())
-
- def size_was_allocated(self, *args):
- current_size = self.mainwindow.get_size()
- target_size = self._guess_size()
- if current_size == target_size:
- self.set_custom_size(False)
- else:
- self.set_custom_size(True)
-
- def resize_to_fit(self):
- self.set_custom_size(False)
- self.set_size()
-
- def set_custom_size(self, val):
- self.custom_size = val
- # BUG this is a hack:
- self.viewmenu.get_submenu().get_children()[1].set_sensitive(val)
-
- # BUG need to add handler on resize event to keep track of
- # old_position when pane is hidden manually
- def split_pane(self):
- pos = self.paned.get_position()
- if pos > 0:
- self.paned.old_position = pos
- self.paned.set_position(0)
- else:
- if hasattr(self.paned, 'old_position'):
- self.paned.set_position(self.paned.old_position)
- else:
- self.maximize_known_pane()
-
- def maximize_known_pane(self):
- self.set_pane_position(self.knownbox.size_request()[1])
-
- def set_pane_position(self, pane_position):
- pane_position = min(MAX_WINDOW_HEIGHT//2, pane_position)
- self.paned.set_position(pane_position)
-
- def toggle_known(self, widget=None):
- self.split_pane()
-
- def open_window(self, window_name, *args, **kwargs):
- if os.name == 'nt':
- self.mainwindow.present()
- savewidget = SaveFileSelection
- if window_name == 'savedir':
- savewidget = CreateFolderSelection
- window_name = 'savefile'
- if self.child_windows.has_key(window_name):
- if window_name == 'savefile':
- kwargs['show'] = False
- self.postponed_save_windows.append(savewidget(self, **kwargs))
- return
-
- if window_name == 'log' :
- self.child_windows[window_name] = LogWindow(self, self.logbuffer, self.config)
- elif window_name == 'about' :
- self.child_windows[window_name] = AboutWindow(self, lambda w: self.donate())
- elif window_name == 'help' :
- self.child_windows[window_name] = HelpWindow(self, makeHelp('bittorrent', defaults))
- elif window_name == 'settings':
- self.child_windows[window_name] = SettingsWindow(self, self.config, self.set_config)
- elif window_name == 'version' :
- self.child_windows[window_name] = VersionWindow(self, *args)
- elif window_name == 'openfile':
- self.child_windows[window_name] = OpenFileSelection(self, **kwargs)
- elif window_name == 'savefile':
- self.child_windows[window_name] = savewidget(self, **kwargs)
- elif window_name == 'choosefolder':
- self.child_windows[window_name] = ChooseFolderSelection(self, **kwargs)
- elif window_name == 'enterurl':
- self.child_windows[window_name] = EnterUrlDialog(self, **kwargs)
-
- return self.child_windows[window_name]
-
- def window_closed(self, window_name):
- if self.child_windows.has_key(window_name):
- del self.child_windows[window_name]
- if window_name == 'savefile' and self.postponed_save_windows:
- newwin = self.postponed_save_windows.pop(-1)
- newwin.show()
- self.child_windows['savefile'] = newwin
-
- def close_window(self, window_name):
- self.child_windows[window_name].close(None)
-
- def new_version(self, newversion, download_url):
- if not self.config['notified'] or \
- newversion != NewVersion.Version.from_str(self.config['notified']):
- if not self.torrents.has_key(self.updater.infohash):
- self.open_window('version', newversion, download_url)
- else:
- dlpath = os.path.split(self.torrents[self.updater.infohash].dlpath)[0]
- self.updater.set_installer_dir(dlpath)
- self.updater.start_install()
-
- def check_version(self):
- self.updater.check()
-
- def start_auto_update(self):
- if not self.torrents.has_key(self.updater.infohash):
- self.updater.download()
- else:
- self.global_error(INFO, _("Already downloading %s installer") % self.updater.version)
-
- def confirm_install_new_version(self):
- MessageDialog(self.mainwindow,
- _("Install new %s now?")%app_name,
- _("Do you want to quit %s and install the new version, "
- "%s, now?")%(app_name,self.updater.version),
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_YES_NO,
- yesfunc=self.install_new_version,
- nofunc=None,
- default=gtk.RESPONSE_YES
- )
-
- def install_new_version(self):
- self.updater.launch_installer(self.torrentqueue)
- self.cancel()
-
-
- def open_help(self,widget):
- if self.helpwindow is None:
- msg = (_("%s help is at \n%s\nWould you like to go there now?")%
- (app_name, HELP_URL))
- self.helpwindow = MessageDialog(self.mainwindow,
- _("Visit help web page?"),
- msg,
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_OK_CANCEL,
- yesfunc=self.visit_help,
- nofunc =self.help_closed,
- default=gtk.RESPONSE_OK
- )
-
- def visit_help(self):
- self.visit_url(HELP_URL)
- self.help_closed()
-
- def close_help(self):
- self.helpwindow.close()
-
- def help_closed(self, widget=None):
- self.helpwindow = None
-
-
- def set_config(self, option, value):
- self.config[option] = value
- if option == 'display_interval':
- self.init_updates()
- self.torrentqueue.set_config(option, value)
-
-
- def confirm_remove_finished_torrents(self,widget):
- count = 0
- for infohash, t in self.torrents.iteritems():
- if t.state == KNOWN and t.completion >= 1:
- count += 1
- if count:
- if self.paned.get_position() == 0:
- self.toggle_known()
- msg = ''
- if count == 1:
- msg = _("There is one finished torrent in the list. ") + \
- _("Do you want to remove it?")
- else:
- msg = _("There are %d finished torrents in the list. ") % count +\
- _("Do you want to remove all of them?")
- MessageDialog(self.mainwindow,
- _("Remove all finished torrents?"),
- msg,
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_OK_CANCEL,
- yesfunc=self.remove_finished_torrents,
- default=gtk.RESPONSE_OK)
- else:
- MessageDialog(self.mainwindow,
- _("No finished torrents"),
- _("There are no finished torrents to remove."),
- type=gtk.MESSAGE_INFO,
- default=gtk.RESPONSE_OK)
-
- def remove_finished_torrents(self):
- for infohash, t in self.torrents.iteritems():
- if t.state == KNOWN and t.completion >= 1:
- self.torrentqueue.remove_torrent(infohash)
- if self.paned.get_position() > 0:
- self.toggle_known()
-
- def cancel(self, widget=None):
- for window_name in self.child_windows.keys():
- self.close_window(window_name)
-
- if self.errordialog is not None:
- self.errordialog.destroy()
- self.errors_closed()
-
- for t in self.torrents.itervalues():
- if t.widget is not None:
- t.widget.close_child_windows()
-
- self.torrentqueue.set_done()
- gtk.main_quit()
-
- # Currently called if the user started bittorrent from a terminal
- # and presses ctrl-c there, or if the user quits BitTorrent from
- # the tray icon (on windows)
- def quit(self):
- self.mainwindow.destroy()
-
- def make_statusrequest(self):
- if self.config['pause']:
- return True
- for infohash, t in self.running_torrents.iteritems():
- self.torrentqueue.request_status(infohash, t.widget.peerlistwindow
- is not None, t.widget.filelistwindow is not None)
- if not len(self.running_torrents):
- self.status_light.send_message('empty')
- return True
-
- def enter_url_to_open(self, widget):
- self.open_window('enterurl')
-
- def open_url(self, url):
- self.torrentqueue.start_new_torrent_by_name(url)
-
- def select_torrent_to_open(self, widget):
- open_location = self.config['open_from']
- if not open_location:
- open_location = self.config['save_in']
- path = smart_dir(open_location)
- self.open_window('openfile',
- title=_("Open torrent:"),
- fullname=path,
- got_location_func=self.open_torrent,
- no_location_func=lambda: self.window_closed('openfile'))
-
-
- def open_torrent(self, name):
- self.window_closed('openfile')
- open_location = os.path.split(name)[0]
- if open_location[-1] != os.sep:
- open_location += os.sep
- self.set_config('open_from', open_location)
-
- self.torrentqueue.start_new_torrent_by_name(name)
-
- def change_save_location(self, infohash):
- def no_location():
- self.window_closed('savefile')
-
- t = self.torrents[infohash]
- metainfo = t.metainfo
-
- selector = self.open_window(metainfo.is_batch and 'savedir' or \
- 'savefile',
- title=_("Change save location for ") + metainfo.name,
- fullname=t.dlpath,
- got_location_func = \
- lambda fn: self.got_changed_location(infohash, fn),
- no_location_func=no_location)
-
- def got_changed_location(self, infohash, fullpath):
- self.window_closed('savefile')
- self.torrentqueue.set_save_location(infohash, fullpath)
-
- def save_location(self, infohash, metainfo):
- name = metainfo.name_fs
-
- if self.config['save_as'] and \
- os.access(os.path.split(self.config['save_as'])[0], os.W_OK):
- path = self.config['save_as']
- self.got_location(infohash, path, store_in_config=False)
- self.config['save_as'] = ''
- return
-
- path = smart_dir(self.config['save_in'])
-
- fullname = os.path.join(path, name)
-
- if not self.config['ask_for_save']:
- if os.access(fullname, os.F_OK):
- message = MessageDialog(self.mainwindow,
- _("File exists!"),
- _('"%s" already exists. '
- "Do you want to choose a different file name?") % path_wrap(name),
- buttons=gtk.BUTTONS_YES_NO,
- nofunc= lambda : self.got_location(infohash, fullname),
- yesfunc=lambda : self.get_save_location(infohash, metainfo, fullname),
- default=gtk.RESPONSE_NO)
-
- else:
- self.got_location(infohash, fullname)
- else:
- self.get_save_location(infohash, metainfo, fullname)
-
- def get_save_location(self, infohash, metainfo, fullname):
- def no_location():
- self.window_closed('savefile')
- self.torrentqueue.remove_torrent(infohash)
-
- selector = self.open_window(metainfo.is_batch and 'savedir' or \
- 'savefile',
- title=_("Save location for ") + metainfo.name,
- fullname=fullname,
- got_location_func = lambda fn: \
- self.got_location(infohash, fn),
- no_location_func=no_location)
-
- self.torrents[infohash].widget = selector
-
- def got_location(self, infohash, fullpath, store_in_config=True):
- self.window_closed('savefile')
- self.torrents[infohash].widget = None
- save_in = os.path.split(fullpath)[0]
-
- metainfo = self.torrents[infohash].metainfo
- if metainfo.is_batch:
- bottom_dirs, top_dir_name = os.path.split(save_in)
- if metainfo.name_fs == top_dir_name:
-
- message = MessageDialog(self.mainwindow, _("Directory exists!"),
- _('"%s" already exists.'\
- " Do you intend to create an identical,"\
- " duplicate directory inside the existing"\
- " directory?")%path_wrap(save_in),
- buttons=gtk.BUTTONS_YES_NO,
- nofunc =lambda : self.got_location(infohash, save_in ),
- yesfunc=lambda : self._got_location(infohash, save_in, fullpath, store_in_config=store_in_config),
- default=gtk.RESPONSE_NO,
- )
- return
- self._got_location(infohash, save_in, fullpath, store_in_config=store_in_config)
-
- def _got_location(self, infohash, save_in, fullpath, store_in_config=True):
- if store_in_config:
- if save_in[-1] != os.sep:
- save_in += os.sep
- self.set_config('save_in', save_in)
- self.torrents[infohash].dlpath = fullpath
- self.torrentqueue.set_save_location(infohash, fullpath)
-
- def add_unhighlight_handle(self):
- if self.unhighlight_handle is not None:
- gobject.source_remove(self.unhighlight_handle)
-
- self.unhighlight_handle = gobject.timeout_add(2000,
- self.unhighlight_after_a_while,
- priority=gobject.PRIORITY_LOW)
-
- def unhighlight_after_a_while(self):
- self.drag_highlight()
- gobject.source_remove(self.unhighlight_handle)
- self.unhighlight_handle = None
- return False
-
- def init_updates(self):
- if self.update_handle is not None:
- gobject.source_remove(self.update_handle)
- self.update_handle = gobject.timeout_add(
- int(self.config['display_interval'] * 1000),
- self.make_statusrequest)
-
- def remove_torrent_widget(self, infohash):
- t = self.torrents[infohash]
- self.lists[t.state].remove(infohash)
- if t.state == RUNNING:
- del self.running_torrents[infohash]
- self.set_title()
- if t.state == ASKING_LOCATION:
- if t.widget is not None:
- t.widget.destroy()
- return
-
- if t.state in (KNOWN, RUNNING, QUEUED):
- t.widget.close_child_windows()
-
- if t.state == RUNNING:
- self.runbox.remove(t.widget)
- elif t.state == QUEUED:
- self.queuebox.remove(t.widget)
- elif t.state == KNOWN:
- self.knownbox.remove(t.widget)
-
- t.widget.destroy()
-
- self.set_size()
-
- def create_torrent_widget(self, infohash, queuepos=None):
- t = self.torrents[infohash]
- l = self.lists.setdefault(t.state, [])
- if queuepos is None:
- l.append(infohash)
- else:
- l.insert(queuepos, infohash)
- if t.state == ASKING_LOCATION:
- self.save_location(infohash, t.metainfo)
- self.nag()
- return
- elif t.state == RUNNING:
- self.running_torrents[infohash] = t
- if not self.config['pause']:
- t.widget = RunningTorrentBox(infohash, t.metainfo, t.dlpath,
- t.completion, self)
- else:
- t.widget = PausedTorrentBox(infohash, t.metainfo, t.dlpath,
- t.completion, self)
- box = self.runbox
- elif t.state == QUEUED:
- t.widget = QueuedTorrentBox(infohash, t.metainfo, t.dlpath,
- t.completion, self)
- box = self.queuebox
- elif t.state == KNOWN:
- t.widget = KnownTorrentBox(infohash, t.metainfo, t.dlpath,
- t.completion, self)
- box = self.knownbox
- box.pack_start(t.widget, expand=False, fill=False)
- if queuepos is not None:
- box.reorder_child(t.widget, queuepos)
-
- self.set_size()
-
- def log_text(self, text, severity=ERROR):
- self.logbuffer.log_text(text, severity)
- if self.child_windows.has_key('log'):
- self.child_windows['log'].scroll_to_end()
-
- def _error(self, severity, err_str):
- err_str = err_str.decode('utf-8', 'replace').encode('utf-8')
- err_str = err_str.strip()
- if severity >= ERROR:
- self.error_modal(err_str)
- self.log_text(err_str, severity)
-
- def error(self, infohash, severity, text):
- if self.torrents.has_key(infohash):
- name = self.torrents[infohash].metainfo.name
- err_str = '"%s" : %s'%(name,text)
- self._error(severity, err_str)
- else:
- ihex = infohash.encode('hex')
- err_str = '"%s" : %s'%(ihex,text)
- self._error(severity, err_str)
- self._error(WARNING, 'Previous error raised for invalid infohash: "%s"' % ihex)
-
- def global_error(self, severity, text):
- err_str = _("(global message) : %s")%text
- self._error(severity, err_str)
-
- def error_modal(self, text):
- if self.child_windows.has_key('log'):
- return
-
- title = _("%s Error") % app_name
-
- if self.errordialog is not None:
- if not self.errordialog.multi:
- self.errordialog.destroy()
- self.errordialog = MessageDialog(self.mainwindow, title,
- _("Multiple errors have occurred. "
- "Click OK to view the error log."),
- buttons=gtk.BUTTONS_OK_CANCEL,
- yesfunc=self.multiple_errors_yes,
- nofunc=self.errors_closed,
- default=gtk.RESPONSE_OK
- )
- self.errordialog.multi = True
- else:
- # already showing the multi error dialog, so do nothing
- pass
- else:
- self.errordialog = MessageDialog(self.mainwindow, title, text,
- yesfunc=self.errors_closed,
- default=gtk.RESPONSE_OK)
- self.errordialog.multi = False
-
-
- def multiple_errors_yes(self):
- self.errors_closed()
- self.open_window('log')
-
- def errors_closed(self):
- self.errordialog = None
-
- def open_log(self):
- self.open_window('log')
-
- def stop_queue(self):
- self.set_config('pause', True)
- self.set_title()
- self.status_light.send_message('stop')
- self.set_seen_remote_connections(False)
- self.set_seen_connections(False)
- q = list(self.runbox.get_queue())
- for infohash in q:
- t = self.torrents[infohash]
- self.remove_torrent_widget(infohash)
- self.create_torrent_widget(infohash)
-
- def restart_queue(self):
- self.set_config('pause', False)
- q = list(self.runbox.get_queue())
- for infohash in q:
- t = self.torrents[infohash]
- self.remove_torrent_widget(infohash)
- self.create_torrent_widget(infohash)
- self.start_status_light()
-
- def start_status_light(self):
- if len(self.running_torrents):
- self.status_light.send_message('start')
- else:
- self.status_light.send_message('empty')
-
- def update_status(self, torrent, statistics):
- if self.config['pause']:
- self.status_light.send_message('start')
- return
-
- if self.seen_remote_connections:
- self.status_light.send_message('seen_remote_peers')
- elif self.seen_connections:
- self.status_light.send_message('seen_peers')
- else:
- self.start_status_light()
-
- self.running_torrents[torrent].widget.update_status(statistics)
- if statistics.get('numPeers'):
- self.set_seen_connections(seen=True)
- if (not self.seen_remote_connections and
- statistics.get('ever_got_incoming')):
- self.set_seen_remote_connections(seen=True)
- if self.updater is not None:
- updater_infohash = self.updater.infohash
- if self.torrents.has_key(updater_infohash):
- updater_torrent = self.torrents[updater_infohash]
- if updater_torrent.state == QUEUED:
- self.change_torrent_state(updater_infohash, RUNNING,
- index=0, replaced=0,
- force_running=True)
-
- def set_seen_remote_connections(self, seen=False):
- if seen:
- self.status_light.send_message('seen_remote_peers')
- self.seen_remote_connections = seen
-
- def set_seen_connections(self, seen=False):
- if seen:
- self.status_light.send_message('seen_peers')
- self.seen_connections = seen
-
- def new_displayed_torrent(self, infohash, metainfo, dlpath, state, config,
- completion=None, uptotal=0, downtotal=0):
- t = Struct()
- t.metainfo = metainfo
- t.dlpath = dlpath
- t.state = state
- t.config = config
- t.completion = completion
- t.uptotal = uptotal
- t.downtotal = downtotal
- t.widget = None
- self.torrents[infohash] = t
- self.create_torrent_widget(infohash)
-
- def torrent_state_changed(self, infohash, dlpath, state, completion,
- uptotal, downtotal, queuepos=None):
- t = self.torrents[infohash]
- self.remove_torrent_widget(infohash)
- t.dlpath = dlpath
- t.state = state
- t.completion = completion
- t.uptotal = uptotal
- t.downtotal = downtotal
- self.create_torrent_widget(infohash, queuepos)
-
- def reorder_torrent(self, infohash, queuepos):
- self.remove_torrent_widget(infohash)
- self.create_torrent_widget(infohash, queuepos)
-
- def update_completion(self, infohash, completion, files_left=None,
- files_allocated=None):
- t = self.torrents[infohash]
- if files_left is not None and t.widget.filelistwindow is not None:
- t.widget.filelistwindow.update(files_left, files_allocated)
-
- def removed_torrent(self, infohash):
- self.remove_torrent_widget(infohash)
- del self.torrents[infohash]
-
- def change_torrent_state(self, infohash, newstate, index=None,
- replaced=None, force_running=False):
- t = self.torrents[infohash]
- pred = succ = None
- if index is not None:
- l = self.lists.setdefault(newstate, [])
- if index > 0:
- pred = l[index - 1]
- if index < len(l):
- succ = l[index]
- self.torrentqueue.change_torrent_state(infohash, t.state, newstate,
- pred, succ, replaced, force_running)
-
- def finish(self, infohash):
- t = self.torrents[infohash]
- if t is None or t.state == KNOWN:
- return
- self.change_torrent_state(infohash, KNOWN)
-
- def confirm_replace_running_torrent(self, infohash, replaced, index):
- replace_func = lambda *args: self.change_torrent_state(infohash,
- RUNNING, index, replaced)
- add_func = lambda *args: self.change_torrent_state(infohash,
- RUNNING, index, force_running=True)
- moved_torrent = self.torrents[infohash]
-
- if moved_torrent.state == RUNNING:
- self.change_torrent_state(infohash, RUNNING, index)
- return
-
- if self.config['start_torrent_behavior'] == 'replace':
- replace_func()
- return
- elif self.config['start_torrent_behavior'] == 'add':
- add_func()
- return
-
- moved_torrent_name = moved_torrent.metainfo.name
- confirm = MessageDialog(self.mainwindow,
- _("Stop running torrent?"),
- _('You are about to start "%s". Do you want to stop another running torrent as well?')%(moved_torrent_name),
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_YES_NO,
- yesfunc=replace_func,
- nofunc=add_func,
- default=gtk.RESPONSE_YES)
-
- def nag(self):
- if ((self.config['donated'] != version) and
- #(random.random() * NAG_FREQUENCY) < 1) and
- False):
- title = _("Have you donated?")
- message = _("Welcome to the new version of %s. Have you donated?")%app_name
- self.nagwindow = MessageDialog(self.mainwindow,
- title,
- message,
- type=gtk.MESSAGE_QUESTION,
- buttons=gtk.BUTTONS_YES_NO,
- yesfunc=self.nag_yes, nofunc=self.nag_no,
- default=gtk.RESPONSE_NO)
-
- def nag_no(self):
- self.donate()
-
- def nag_yes(self):
- self.set_config('donated', version)
- MessageDialog(self.mainwindow,
- _("Thanks!"),
- _("Thanks for donating! To donate again, "
- 'select "Donate" from the "Help" menu.'),
- type=gtk.MESSAGE_INFO,
- default=gtk.RESPONSE_OK
- )
-
- def donate(self):
- self.visit_url(DONATE_URL)
-
-
- def visit_url(self, url, callback=None):
- t = threading.Thread(target=self._visit_url,
- args=(url,callback))
- t.setDaemon(True)
- t.start()
-
- def _visit_url(self, url, callback=None):
- webbrowser.open(url)
- if callback:
- gtk_wrap(callback)
-
- def toggle_shown(self):
- if self.config['minimize_to_tray']:
- if self.mainwindow.get_property('visible'):
- self.mainwindow.hide()
- else:
- self.mainwindow.show_all()
- else:
- if not self.iconized:
- self.mainwindow.iconify()
- else:
- self.mainwindow.deiconify()
-
-
- def raiseerror(self, *args):
- raise ValueError('test traceback behavior')
-
-#this class provides a thin layer around the loop so that the main window
-#doesn't have to run it. It protects againstexceptions in mainwindow creation
-#preventing the loop from starting (and causing "The grey screen of BT")
-class MainLoop:
- def __init__(self):
- self.mainwindow = None
- self.started = 0
-
- gtk.gdk.threads_init()
-
- def set_mainwindow(self, mainwindow):
- self.mainwindow = mainwindow
-
- def run(self):
- self.mainwindow.traythread.start()
- gtk.gdk.threads_enter()
-
- if self.mainwindow:
- self.mainwindow.ssbutton.set_paused(self.mainwindow.config['pause'])
- self.mainwindow.rate_slider_box.start()
- self.mainwindow.init_updates()
-
- try:
- #the main loop has been started
- self.started = 1
- gtk.main()
- except KeyboardInterrupt:
- gtk.gdk.threads_leave()
- if self.mainwindow:
- self.mainwindow.torrentqueue.set_done()
- raise
-
- gtk.gdk.threads_leave()
-
- def quit(self):
- if self.mainwindow:
- self.mainwindow.quit()
-
-
-def btgui_exit_gtk(mainloop):
- # if the main loop has never run, we have to run it to flush blocking threads
- # if it has run, running it a second time will cause duplicate-destruction problems
- if not mainloop.started:
- # queue up a command to close the gui
- gobject.idle_add(lock_wrap, mainloop.quit)
- # run the main loop so we process all queued commands, then quit
- mainloop.run()
-
-if __name__ == '__main__':
-
- mainloop = MainLoop()
-
- # make sure we start the gtk loop once before we close
- atexit.register(btgui_exit_gtk, mainloop)
-
- torrentqueue = TorrentQueue.TorrentQueue(config, ui_options, ipc)
- d = DownloadInfoFrame(config,TorrentQueue.ThreadWrappedQueue(torrentqueue))
-
- mainloop.set_mainwindow(d)
- global_log_func.logger = d.global_error
-
- startflag = threading.Event()
- dlthread = threading.Thread(target = torrentqueue.run,
- args = (d, gtk_wrap, startflag))
- dlthread.setDaemon(False)
- dlthread.start()
- startflag.wait()
- # the wait may have been terminated because of an error
- if torrentqueue.initialized == -1:
- raise BTFailure(_("Could not start the TorrentQueue, see above for errors."))
-
- torrentqueue.rawserver.install_sigint_handler()
- for name in newtorrents:
- d.torrentqueue.start_new_torrent_by_name(name)
-
- try:
- mainloop.run()
- except KeyboardInterrupt:
- # the gtk main loop is closed in MainLoop
- sys.exit(1)
- d.trayicon.disable()
-
diff --git a/changetracker-console b/changetracker-console
deleted file mode 120000
index f4dd34a..0000000
--- a/changetracker-console
+++ /dev/null
@@ -1 +0,0 @@
-changetracker-console.py \ No newline at end of file
diff --git a/images/bittorrent.ico b/images/bittorrent.ico
deleted file mode 100644
index 47e6e70..0000000
--- a/images/bittorrent.ico
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/abort.png b/images/icons/default/abort.png
deleted file mode 100644
index cd33fc0..0000000
--- a/images/icons/default/abort.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/broken.png b/images/icons/default/broken.png
deleted file mode 100644
index 7d49e88..0000000
--- a/images/icons/default/broken.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/finished.png b/images/icons/default/finished.png
deleted file mode 100644
index 7c95d07..0000000
--- a/images/icons/default/finished.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/info.png b/images/icons/default/info.png
deleted file mode 100644
index 7dcd792..0000000
--- a/images/icons/default/info.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/pause.png b/images/icons/default/pause.png
deleted file mode 100644
index 145b933..0000000
--- a/images/icons/default/pause.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/paused.png b/images/icons/default/paused.png
deleted file mode 100644
index f65fbd5..0000000
--- a/images/icons/default/paused.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/play.png b/images/icons/default/play.png
deleted file mode 100644
index 8e2f2cb..0000000
--- a/images/icons/default/play.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/queued.png b/images/icons/default/queued.png
deleted file mode 100644
index 8135c68..0000000
--- a/images/icons/default/queued.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/remove.png b/images/icons/default/remove.png
deleted file mode 100644
index c8e37be..0000000
--- a/images/icons/default/remove.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/running.png b/images/icons/default/running.png
deleted file mode 100644
index 7ca2c0d..0000000
--- a/images/icons/default/running.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-broken.png b/images/icons/default/status-broken.png
deleted file mode 100644
index 095a6a2..0000000
--- a/images/icons/default/status-broken.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-natted.png b/images/icons/default/status-natted.png
deleted file mode 100644
index 9e67557..0000000
--- a/images/icons/default/status-natted.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-pre-natted.png b/images/icons/default/status-pre-natted.png
deleted file mode 100644
index 513ccca..0000000
--- a/images/icons/default/status-pre-natted.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-running.png b/images/icons/default/status-running.png
deleted file mode 100644
index fd7a309..0000000
--- a/images/icons/default/status-running.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-starting.png b/images/icons/default/status-starting.png
deleted file mode 100644
index 7c909d5..0000000
--- a/images/icons/default/status-starting.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/status-stopped.png b/images/icons/default/status-stopped.png
deleted file mode 100644
index 4fdb7d9..0000000
--- a/images/icons/default/status-stopped.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/default/trashcan.png b/images/icons/default/trashcan.png
deleted file mode 100644
index 709bd49..0000000
--- a/images/icons/default/trashcan.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/broken.png b/images/icons/old/broken.png
deleted file mode 100644
index 3f74744..0000000
--- a/images/icons/old/broken.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/finished.png b/images/icons/old/finished.png
deleted file mode 100644
index fc29d9a..0000000
--- a/images/icons/old/finished.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/info.png b/images/icons/old/info.png
deleted file mode 100644
index 75c3ff5..0000000
--- a/images/icons/old/info.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/pause.png b/images/icons/old/pause.png
deleted file mode 100644
index 3da5aeb..0000000
--- a/images/icons/old/pause.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/paused.png b/images/icons/old/paused.png
deleted file mode 100644
index ea83f83..0000000
--- a/images/icons/old/paused.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/play.png b/images/icons/old/play.png
deleted file mode 100644
index 7ae6b2e..0000000
--- a/images/icons/old/play.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/queued.png b/images/icons/old/queued.png
deleted file mode 100644
index d03b6c2..0000000
--- a/images/icons/old/queued.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/remove.png b/images/icons/old/remove.png
deleted file mode 100644
index f09bdc0..0000000
--- a/images/icons/old/remove.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/running.png b/images/icons/old/running.png
deleted file mode 100644
index 5fb45e1..0000000
--- a/images/icons/old/running.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-broken.png b/images/icons/old/status-broken.png
deleted file mode 100644
index 7cfa3ef..0000000
--- a/images/icons/old/status-broken.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-natted.png b/images/icons/old/status-natted.png
deleted file mode 100644
index b155e93..0000000
--- a/images/icons/old/status-natted.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-pre-natted.png b/images/icons/old/status-pre-natted.png
deleted file mode 100644
index f311ba8..0000000
--- a/images/icons/old/status-pre-natted.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-running.png b/images/icons/old/status-running.png
deleted file mode 100644
index 7a89822..0000000
--- a/images/icons/old/status-running.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-starting.png b/images/icons/old/status-starting.png
deleted file mode 100644
index 09e3519..0000000
--- a/images/icons/old/status-starting.png
+++ /dev/null
Binary files differ
diff --git a/images/icons/old/status-stopped.png b/images/icons/old/status-stopped.png
deleted file mode 100644
index 15a5a43..0000000
--- a/images/icons/old/status-stopped.png
+++ /dev/null
Binary files differ
diff --git a/images/logo/bittorrent_32.png b/images/logo/bittorrent_32.png
deleted file mode 100644
index aa016bd..0000000
--- a/images/logo/bittorrent_32.png
+++ /dev/null
Binary files differ
diff --git a/images/logo/bittorrent_96.png b/images/logo/bittorrent_96.png
deleted file mode 100644
index aefd45e..0000000
--- a/images/logo/bittorrent_96.png
+++ /dev/null
Binary files differ
diff --git a/khashmir/KRateLimiter.py b/khashmir/KRateLimiter.py
index a9a9cdc..0b7bb7f 100644
--- a/khashmir/KRateLimiter.py
+++ b/khashmir/KRateLimiter.py
@@ -8,8 +8,8 @@
# for the specific language governing rights and limitations under the
# License.
-from BitTorrent.platform import bttime as time
-from BitTorrent.CurrentRateMeasure import Measure
+from NohGooee.platform import bttime as time
+from NohGooee.CurrentRateMeasure import Measure
from const import *
from random import randrange, shuffle
from traceback import print_exc
diff --git a/khashmir/actions.py b/khashmir/actions.py
index 2bbe94b..97ca949 100644
--- a/khashmir/actions.py
+++ b/khashmir/actions.py
@@ -8,7 +8,7 @@
# for the specific language governing rights and limitations under the
# License.
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
import const
diff --git a/khashmir/cache.py b/khashmir/cache.py
index ab4df30..e38fc71 100644
--- a/khashmir/cache.py
+++ b/khashmir/cache.py
@@ -8,7 +8,7 @@
# for the specific language governing rights and limitations under the
# License.
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
class Cache:
def __init__(self, touch_on_access = False):
diff --git a/khashmir/inserter.py b/khashmir/inserter.py
index d45ff04..f3ade91 100644
--- a/khashmir/inserter.py
+++ b/khashmir/inserter.py
@@ -12,8 +12,8 @@
usage = "usage: inserter.py <contact host> <contact port>"
from utkhashmir import UTKhashmir
-from BitTorrent.RawServer_magic import RawServer
-from BitTorrent.defaultargs import common_options, rare_options
+from NohGooee.RawServer_magic import RawServer
+from NohGooee.defaultargs import common_options, rare_options
from khashmir.khash import newID
from random import randrange
from threading import Event
diff --git a/khashmir/khashmir.py b/khashmir/khashmir.py
index d939f67..23ee305 100644
--- a/khashmir/khashmir.py
+++ b/khashmir/khashmir.py
@@ -11,12 +11,12 @@
import const
from socket import gethostbyname
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
from sha import sha
import re
-from BitTorrent.defaultargs import common_options, rare_options
-from BitTorrent.RawServer_magic import RawServer
+from NohGooee.defaultargs import common_options, rare_options
+from NohGooee.RawServer_magic import RawServer
from ktable import KTable, K
from knode import *
@@ -31,9 +31,9 @@ import sys
import os
import traceback
-from BitTorrent.bencode import bencode, bdecode
+from NohGooee.bencode import bencode, bdecode
-from BitTorrent.defer import Deferred
+from NohGooee.defer import Deferred
from random import randrange
from kstore import sample
diff --git a/khashmir/knode.py b/khashmir/knode.py
index 560252a..3a85265 100644
--- a/khashmir/knode.py
+++ b/khashmir/knode.py
@@ -9,7 +9,7 @@
# License.
from node import Node
-from BitTorrent.defer import Deferred
+from NohGooee.defer import Deferred
from const import NULL_ID
from krpc import KRPCProtocolError
diff --git a/khashmir/krpc.py b/khashmir/krpc.py
index 86c9973..d826784 100644
--- a/khashmir/krpc.py
+++ b/khashmir/krpc.py
@@ -8,11 +8,11 @@
# for the specific language governing rights and limitations under the
# License.
-from BitTorrent.defer import Deferred
-from BitTorrent.bencode import bencode, bdecode
+from NohGooee.defer import Deferred
+from NohGooee.bencode import bencode, bdecode
import socket
-from BitTorrent.RawServer_magic import Handler
-from BitTorrent.platform import bttime
+from NohGooee.RawServer_magic import Handler
+from NohGooee.platform import bttime
import time
from math import log10
diff --git a/khashmir/kstore.py b/khashmir/kstore.py
index 5c01200..ca59bfa 100644
--- a/khashmir/kstore.py
+++ b/khashmir/kstore.py
@@ -20,7 +20,7 @@ except ImportError:
d[choice(l)] = 1
return d.keys()
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
class KItem:
def __init__(self, key, value):
diff --git a/khashmir/ktable.py b/khashmir/ktable.py
index e0a07b4..1139ea3 100644
--- a/khashmir/ktable.py
+++ b/khashmir/ktable.py
@@ -8,7 +8,7 @@
# for the specific language governing rights and limitations under the
# License.
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
from bisect import *
from types import *
diff --git a/khashmir/node.py b/khashmir/node.py
index 65a48ef..3d9acde 100644
--- a/khashmir/node.py
+++ b/khashmir/node.py
@@ -9,7 +9,7 @@
# License.
import khash
-from BitTorrent.platform import bttime as time
+from NohGooee.platform import bttime as time
from types import *
class Node:
diff --git a/khashmir/test_khashmir.py b/khashmir/test_khashmir.py
index e22028e..19e6175 100644
--- a/khashmir/test_khashmir.py
+++ b/khashmir/test_khashmir.py
@@ -10,7 +10,7 @@
from unittest import *
-from BitTorrent import RawServer_magic
+from NohGooee import RawServer_magic
from khashmir import *
import khash
diff --git a/khashmir/test_krpc.py b/khashmir/test_krpc.py
index 2ba4343..8e57cd9 100644
--- a/khashmir/test_krpc.py
+++ b/khashmir/test_krpc.py
@@ -10,7 +10,7 @@
from unittest import *
from krpc import *
-from BitTorrent.defaultargs import common_options, rare_options
+from NohGooee.defaultargs import common_options, rare_options
from threading import Event
from node import Node
diff --git a/khashmir/test_kstore.py b/khashmir/test_kstore.py
index d2f2b15..8081dad 100644
--- a/khashmir/test_kstore.py
+++ b/khashmir/test_kstore.py
@@ -9,7 +9,7 @@
# License.
import unittest
-from BitTorrent.platform import bttime
+from NohGooee.platform import bttime
from time import sleep
from kstore import KStore
diff --git a/khashmir/unet.py b/khashmir/unet.py
index e163a3f..65f1220 100644
--- a/khashmir/unet.py
+++ b/khashmir/unet.py
@@ -14,8 +14,8 @@
# usage: knet.py <num_nodes> <start_port> <ip_address>
from utkhashmir import UTKhashmir
-from BitTorrent.RawServer_magic import RawServer
-from BitTorrent.defaultargs import common_options, rare_options
+from NohGooee.RawServer_magic import RawServer
+from NohGooee.defaultargs import common_options, rare_options
from random import randrange
from threading import Event
import sys, os
diff --git a/language_codes.py b/language_codes.py
index 3464f30..ce657ed 100644
--- a/language_codes.py
+++ b/language_codes.py
@@ -1,8 +1,8 @@
import sys
-from BitTorrent import language_names
+from NohGooee import language_names
if '-a' in sys.argv:
- from BitTorrent.language import unfinished_language_names
+ from NohGooee.language import unfinished_language_names
language_names.update(unfinished_language_names)
languages = language_names.keys()
diff --git a/launchmany-console b/launchmany-console
deleted file mode 120000
index 3ee3ad1..0000000
--- a/launchmany-console
+++ /dev/null
@@ -1 +0,0 @@
-launchmany-console.py \ No newline at end of file
diff --git a/launchmany-curses b/launchmany-curses
deleted file mode 120000
index f58dba2..0000000
--- a/launchmany-curses
+++ /dev/null
@@ -1 +0,0 @@
-launchmany-curses.py \ No newline at end of file
diff --git a/launchmany-curses.py b/launchmany-curses.py
deleted file mode 100755
index 8f925ae..0000000
--- a/launchmany-curses.py
+++ /dev/null
@@ -1,301 +0,0 @@
-#!/usr/bin/env python
-
-# The contents of this file are subject to the BitTorrent Open Source License
-# Version 1.1 (the License). You may not copy or use this file, in either
-# source code or executable form, except in compliance with the License. You
-# may obtain a copy of the License at http://www.bittorrent.com/license/.
-#
-# Software distributed under the License is distributed on an AS IS basis,
-# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
-# for the specific language governing rights and limitations under the
-# License.
-
-# Written by John Hoffman
-
-from __future__ import division
-
-from BitTorrent.platform import install_translation
-install_translation()
-
-DOWNLOAD_SCROLL_RATE = 1
-
-import sys, os
-from threading import Event
-from time import time, localtime, strftime
-
-from BitTorrent.launchmanycore import LaunchMany
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.parseargs import parseargs, printHelp
-from BitTorrent import configfile
-from BitTorrent import version
-from BitTorrent import BTFailure
-
-try:
- curses = import_curses()
- import curses.panel
- from curses.wrapper import wrapper as curses_wrapper
- from signal import signal, SIGWINCH
-except:
- print _("Textmode GUI initialization failed, cannot proceed.")
- print
- print _("This download interface requires the standard Python module "
- "\"curses\", which is unfortunately not available for the native "
- "Windows port of Python. It is however available for the Cygwin "
- "port of Python, running on all Win32 systems (www.cygwin.com).")
- print
- print _("You may still use \"btdownloadheadless.py\" to download.")
- sys.exit(1)
-
-exceptions = []
-
-def fmttime(n):
- if n <= 0:
- return None
- n = int(n)
- m, s = divmod(n, 60)
- h, m = divmod(m, 60)
- if h > 1000000:
- return _("connecting to peers")
- return _("ETA in %d:%02d:%02d") % (h, m, s)
-
-def fmtsize(n):
- n = long(n)
- unit = [' B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB', 'EiB', 'ZiB', 'YiB']
- i = 0
- if (n > 999):
- i = 1
- while i + 1 < len(unit) and (n >> 10) >= 999:
- i += 1
- n >>= 10
- n /= 1024
- if i > 0:
- size = '%.1f' % n + '%s' % unit[i]
- else:
- size = '%.0f' % n + '%s' % unit[i]
- return size
-
-def ljust(s, size):
- s = s[:size]
- return s + (' '*(size-len(s)))
-
-def rjust(s, size):
- s = s[:size]
- return (' '*(size-len(s)))+s
-
-
-class CursesDisplayer(object):
-
- def __init__(self, scrwin):
- self.messages = []
- self.scroll_pos = 0
- self.scroll_time = 0
-
- self.scrwin = scrwin
- signal(SIGWINCH, self.winch_handler)
- self.changeflag = Event()
- self._remake_window()
- curses.use_default_colors()
-
- def winch_handler(self, signum, stackframe):
- self.changeflag.set()
- curses.endwin()
- self.scrwin.refresh()
- self.scrwin = curses.newwin(0, 0, 0, 0)
- self._remake_window()
- self._display_messages()
-
- def _remake_window(self):
- self.scrh, self.scrw = self.scrwin.getmaxyx()
- self.scrpan = curses.panel.new_panel(self.scrwin)
- self.mainwinh = (2*self.scrh)//3
- self.mainwinw = self.scrw - 4 # - 2 (bars) - 2 (spaces)
- self.mainwiny = 2 # + 1 (bar) + 1 (titles)
- self.mainwinx = 2 # + 1 (bar) + 1 (space)
- # + 1 to all windows so we can write at mainwinw
-
- self.mainwin = curses.newwin(self.mainwinh, self.mainwinw+1,
- self.mainwiny, self.mainwinx)
- self.mainpan = curses.panel.new_panel(self.mainwin)
- self.mainwin.scrollok(0)
- self.mainwin.nodelay(1)
-
- self.headerwin = curses.newwin(1, self.mainwinw+1,
- 1, self.mainwinx)
- self.headerpan = curses.panel.new_panel(self.headerwin)
- self.headerwin.scrollok(0)
-
- self.totalwin = curses.newwin(1, self.mainwinw+1,
- self.mainwinh+1, self.mainwinx)
- self.totalpan = curses.panel.new_panel(self.totalwin)
- self.totalwin.scrollok(0)
-
- self.statuswinh = self.scrh-4-self.mainwinh
- self.statuswin = curses.newwin(self.statuswinh, self.mainwinw+1,
- self.mainwinh+3, self.mainwinx)
- self.statuspan = curses.panel.new_panel(self.statuswin)
- self.statuswin.scrollok(0)
-
- try:
- self.scrwin.border(ord('|'),ord('|'),ord('-'),ord('-'),ord(' '),ord(' '),ord(' '),ord(' '))
- except:
- pass
- rcols = (_("Size"),_("Download"),_("Upload"))
- rwids = (8, 10, 10)
- rwid = sum(rwids)
- start = self.mainwinw - rwid
- self.headerwin.addnstr(0, 2, '#', start, curses.A_BOLD)
- self.headerwin.addnstr(0, 4, _("Filename"), start, curses.A_BOLD)
-
- for s,w in zip(rcols, rwids):
- st = start + max(w - len(s), 0)
- self.headerwin.addnstr(0, st, s[:w], len(s[:w]), curses.A_BOLD)
- start += w
-
- self.totalwin.addnstr(0, self.mainwinw - 27, _("Totals:"), 7, curses.A_BOLD)
-
- self._display_messages()
-
- curses.panel.update_panels()
- curses.doupdate()
- self.changeflag.clear()
-
-
- def _display_line(self, s, bold = False):
- if self.disp_end:
- return True
- line = self.disp_line
- self.disp_line += 1
- if line < 0:
- return False
- if bold:
- self.mainwin.addnstr(line, 0, s, self.mainwinw, curses.A_BOLD)
- else:
- self.mainwin.addnstr(line, 0, s, self.mainwinw)
- if self.disp_line >= self.mainwinh:
- self.disp_end = True
- return self.disp_end
-
- def _display_data(self, data):
- if 3*len(data) <= self.mainwinh:
- self.scroll_pos = 0
- self.scrolling = False
- elif self.scroll_time + DOWNLOAD_SCROLL_RATE < time():
- self.scroll_time = time()
- self.scroll_pos += 1
- self.scrolling = True
- if self.scroll_pos >= 3*len(data)+2:
- self.scroll_pos = 0
-
- i = self.scroll_pos//3
- self.disp_line = (3*i)-self.scroll_pos
- self.disp_end = False
-
- while not self.disp_end:
- ii = i % len(data)
- if i and not ii:
- if not self.scrolling:
- break
- self._display_line('')
- if self._display_line(''):
- break
- ( name, status, progress, peers, seeds, seedsmsg, dist,
- uprate, dnrate, upamt, dnamt, size, t, msg ) = data[ii]
- t = fmttime(t)
- if t:
- status = t
- name = ljust(name,self.mainwinw-32)
- size = rjust(fmtsize(size),8)
- uprate = rjust('%s/s' % fmtsize(uprate),10)
- dnrate = rjust('%s/s' % fmtsize(dnrate),10)
- line = "%3d %s%s%s%s" % (ii+1, name, size, dnrate, uprate)
- self._display_line(line, True)
- if peers + seeds:
- datastr = _(" (%s) %s - %s peers %s seeds %s dist copies - %s dn %s up") % (
- progress, status, peers, seeds, dist,
- fmtsize(dnamt), fmtsize(upamt) )
- else:
- datastr = ' '+status+' ('+progress+')'
- self._display_line(datastr)
- self._display_line(' '+ljust(msg,self.mainwinw-4))
- i += 1
-
- def display(self, data):
- if self.changeflag.isSet():
- return
-
- inchar = self.mainwin.getch()
- if inchar == 12: # ^L
- self._remake_window()
-
- self.mainwin.erase()
- if data:
- self._display_data(data)
- else:
- self.mainwin.addnstr( 1, self.mainwinw//2-5,
- _("no torrents"), 12, curses.A_BOLD )
- totalup = 0
- totaldn = 0
- for ( name, status, progress, peers, seeds, seedsmsg, dist,
- uprate, dnrate, upamt, dnamt, size, t, msg ) in data:
- totalup += uprate
- totaldn += dnrate
-
- totalup = '%s/s' % fmtsize(totalup)
- totaldn = '%s/s' % fmtsize(totaldn)
-
- self.totalwin.erase()
- self.totalwin.addnstr(0, self.mainwinw-27, _("Totals:"), 7, curses.A_BOLD)
- self.totalwin.addnstr(0, self.mainwinw-20 + (10-len(totaldn)),
- totaldn, 10, curses.A_BOLD)
- self.totalwin.addnstr(0, self.mainwinw-10 + (10-len(totalup)),
- totalup, 10, curses.A_BOLD)
-
- curses.panel.update_panels()
- curses.doupdate()
-
- return inchar in (ord('q'),ord('Q'))
-
- def message(self, s):
- self.messages.append(strftime('%x %X - ',localtime(time()))+s)
- self._display_messages()
-
- def _display_messages(self):
- self.statuswin.erase()
- winpos = 0
- for s in self.messages[-self.statuswinh:]:
- self.statuswin.addnstr(winpos, 0, s, self.mainwinw)
- winpos += 1
- curses.panel.update_panels()
- curses.doupdate()
-
- def exception(self, s):
- exceptions.append(s)
- self.message(_("SYSTEM ERROR - EXCEPTION GENERATED"))
-
-
-
-def LaunchManyWrapper(scrwin, config):
- LaunchMany(config, CursesDisplayer(scrwin), 'launchmany-curses')
-
-
-if __name__ == '__main__':
- uiname = 'launchmany-curses'
- defaults = get_defaults(uiname)
- try:
- if len(sys.argv) < 2:
- printHelp(uiname, defaults)
- sys.exit(1)
- config, args = configfile.parse_configuration_and_args(defaults,
- uiname, sys.argv[1:], 0, 1)
- if args:
- config['torrent_dir'] = args[0]
- if not os.path.isdir(config['torrent_dir']):
- raise BTFailure(_("Warning: ")+args[0]+_(" is not a directory"))
- except BTFailure, e:
- print _("error: ") + str(e) + _("\nrun with no args for parameter explanations")
- sys.exit(1)
-
- curses_wrapper(LaunchManyWrapper, config)
- if exceptions:
- print _("\nEXCEPTION:")
- print exceptions[0]
diff --git a/maketorrent b/maketorrent
deleted file mode 120000
index d6a8e31..0000000
--- a/maketorrent
+++ /dev/null
@@ -1 +0,0 @@
-maketorrent.py \ No newline at end of file
diff --git a/maketorrent-console b/maketorrent-console
deleted file mode 120000
index 09524ba..0000000
--- a/maketorrent-console
+++ /dev/null
@@ -1 +0,0 @@
-maketorrent-console.py \ No newline at end of file
diff --git a/maketorrent.py b/maketorrent.py
deleted file mode 100755
index ba5d275..0000000
--- a/maketorrent.py
+++ /dev/null
@@ -1,577 +0,0 @@
-#!/usr/bin/env python
-
-# The contents of this file are subject to the BitTorrent Open Source License
-# Version 1.1 (the License). You may not copy or use this file, in either
-# source code or executable form, except in compliance with the License. You
-# may obtain a copy of the License at http://www.bittorrent.com/license/.
-#
-# Software distributed under the License is distributed on an AS IS basis,
-# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
-# for the specific language governing rights and limitations under the
-# License.
-
-# Written by Matt Chisholm
-
-from __future__ import division
-
-from BitTorrent.platform import install_translation
-install_translation()
-
-import os
-import sys
-
-assert sys.version_info >= (2, 3), _("Install Python %s or greater") % '2.3'
-
-from threading import Event
-
-import gtk
-import gobject
-
-from BitTorrent.GUI import *
-from BitTorrent import Desktop
-from BitTorrent import version
-from BitTorrent import configfile
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.makemetafile import make_meta_files
-from BitTorrent.parseargs import makeHelp
-from BitTorrent.platform import btspawn
-from BitTorrent.ConvertedMetainfo import set_filesystem_encoding
-
-defaults = get_defaults('maketorrent')
-defconfig = dict([(name, value) for (name, value, doc) in defaults])
-del name, value, doc
-ui_options = ('torrent_dir','piece_size_pow2','tracker_list','use_tracker')
-
-def sfe_ef(e,s):
- print s
-set_filesystem_encoding(defconfig['filesystem_encoding'], sfe_ef)
-
-EXTENSION = '.torrent'
-
-MAXIMUM_NODES = 8
-
-class MainWindow(Window):
-
- def __init__(self, config):
- Window.__init__(self)
- self.mainwindow = self # temp hack to make modal win32 file choosers work
- self.tooltips = gtk.Tooltips()
- self.connect('destroy', self.quit)
- self.set_title(_("%s torrent file creator %s")%(app_name, version))
- self.set_border_width(SPACING)
-
- self.config = config
- self.tracker_list = []
- if self.config['tracker_list']:
- self.tracker_list = self.config['tracker_list'].split(',')
-
- right_column_width=276
- self.box = gtk.VBox(spacing=SPACING)
-
- self.box.pack_start(lalign(gtk.Label(
- _("Make torrent file for this file/directory:"))),
- expand=False, fill=False)
-
- self.filebox = gtk.Entry()
- self.filebox.set_editable(False)
- self.change_button = gtk.Button(_("Choose..."))
- self.change_button.connect('clicked', self.choose_files)
-
- hb = gtk.HBox(spacing=SPACING)
- hb.pack_start(self.filebox, expand=True, fill=True)
- hb.pack_end(self.change_button, expand=False, fill=False)
-
- self.box.pack_start(hb, expand=False, fill=False, padding=0)
-
- self.box.pack_start(lalign(gtk.Label(
- _("(Directories will become batch torrents)"))),
- expand=False, fill=False, padding=0)
-
- self.box.pack_start(gtk.HSeparator(), expand=False, fill=False, padding=0)
-
- self.table = gtk.Table(rows=3,columns=2,homogeneous=False)
- self.table.set_col_spacings(SPACING)
- self.table.set_row_spacings(SPACING)
- y = 0
-
- # Piece size
- self.table.attach(ralign(gtk.Label(_("Piece size:"))),0,1,y,y+1,
- xoptions=gtk.FILL, yoptions=0)
-
- self.piece_size = gtk.combo_box_new_text()
- self.piece_size.offset = 15
- for i in range(7):
- self.piece_size.append_text(str(Size(2**(i+self.piece_size.offset))))
- self.piece_size.set_active(self.config['piece_size_pow2'] -
- self.piece_size.offset)
-
- self.piece_size_box = gtk.HBox(spacing=SPACING)
- self.piece_size_box.pack_start(self.piece_size,
- expand=False, fill=False)
- self.table.attach(self.piece_size_box,1,2,y,y+1,
- xoptions=gtk.FILL|gtk.EXPAND, yoptions=0)
- y+=1
-
-
- # Announce URL / Tracker
- self.tracker_radio = gtk.RadioButton(group=None, label=_("Use _tracker:"))
- self.tracker_radio.value = True
-
- self.table.attach(self.tracker_radio,0,1,y,y+1,
- xoptions=gtk.FILL, yoptions=0)
- self.announce_entry = gtk.Entry()
- self.announce_completion = gtk.EntryCompletion()
- self.announce_entry.set_completion(self.announce_completion)
- self.announce_completion.set_text_column(0)
- self.build_completion()
-
- self.tracker_radio.entry = self.announce_entry
- if self.config['use_tracker'] == self.tracker_radio.value:
- self.announce_entry.set_sensitive(True)
- else:
- self.announce_entry.set_sensitive(False)
-
- if self.config['tracker_name']:
- self.announce_entry.set_text(self.config['tracker_name'])
- elif len(self.tracker_list):
- self.announce_entry.set_text(self.tracker_list[0])
- else:
- self.announce_entry.set_text('http://my.tracker:6969/announce')
-
- self.announce_entry.set_size_request(right_column_width,-1)
- self.table.attach(self.announce_entry,1,2,y,y+1, xoptions=gtk.FILL|gtk.EXPAND, yoptions=0)
- y+=1
-
- # DHT / Trackerless
- self.dht_radio = gtk.RadioButton(group=self.tracker_radio,
- label=_("Use _DHT:"))
- self.dht_radio.value = False
-
- self.table.attach(align(self.dht_radio,0,0), 0,1,y,y+1,
- xoptions=gtk.FILL|gtk.EXPAND, yoptions=0)
-
- self.dht_nodes_expander = gtk.Expander(_("Nodes (optional):"))
- self.dht_nodes_expander.connect('size-allocate', self.resize_to_fit)
-
- self.dht_nodes = NodeList(self, 'router.bittorrent.com:6881')
- self.dht_frame = gtk.Frame()
- self.dht_frame.add(self.dht_nodes)
- self.dht_frame.set_shadow_type(gtk.SHADOW_IN)
- self.dht_nodes_expander.add(self.dht_frame)
-
- self.table.attach(self.dht_nodes_expander,1,2,y,y+1, xoptions=gtk.FILL|gtk.EXPAND, yoptions=0)
- self.dht_radio.entry = self.dht_nodes
-
- if self.config['use_tracker'] == self.dht_radio.value:
- self.dht_nodes.set_sensitive(True)
- else:
- self.dht_nodes.set_sensitive(False)
-
- y+=1
-
- for w in self.tracker_radio.get_group():
- w.connect('toggled', self.toggle_tracker_dht)
-
- for w in self.tracker_radio.get_group():
- if w.value == bool(self.config['use_tracker']):
- w.set_active(True)
- else:
- w.set_active(False)
-
- # Hsep
- self.table.attach(gtk.HSeparator(),0,2,y,y+1,yoptions=0)
- y+=1
-
- # Comment
- self.comment_expander = gtk.Expander(_("Comments:"))
- self.comment_expander.connect('size-allocate', self.resize_to_fit)
-
- self.comment_buffer = gtk.TextBuffer()
- self.comment_text = gtk.TextView()
- self.comment_text.set_buffer(self.comment_buffer)
- self.comment_text.set_wrap_mode(gtk.WRAP_WORD)
- self.comment_scroll = gtk.ScrolledWindow()
- self.comment_scroll.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_ALWAYS)
- self.comment_scroll.set_shadow_type(gtk.SHADOW_IN)
- self.comment_scroll.add(self.comment_text)
-
- self.comment_expander.add(self.comment_scroll)
- self.table.attach(self.comment_expander,0,2,y,y+1,
- xoptions=gtk.FILL, yoptions=0)
- y+=1
-
- # add table
- self.box.pack_start(self.table, expand=True, fill=True, padding=0)
-
- # buttons
-
- self.buttonbox = gtk.HBox(homogeneous=True, spacing=SPACING)
-
- self.quitbutton = gtk.Button(stock=gtk.STOCK_CLOSE)
-##=======
-## # Piece size
-## self.table.attach(ralign(gtk.Label('Piece size:')),0,1,y,y+1,
-## xoptions=gtk.FILL, yoptions=0)
-
-
-## self.piece_size_box = gtk.HBox(spacing=SPACING)
-## self.piece_size_box.pack_start(self.piece_size, expand=False, fill=False)
-## self.table.attach(self.piece_size_box,1,2,y,y+1, xoptions=gtk.FILL|gtk.EXPAND, yoptions=0)
-## y+=1
-
-
-## self.box.pack_start(self.table, expand=True, fill=True)
-
-## self.buttonbox = gtk.HBox(homogeneous=True, spacing=SPACING)
-
-## self.quitbutton = gtk.Button(stock=gtk.STOCK_QUIT)
-##>>>>>>> remote
- self.quitbutton.connect('clicked', self.quit)
- self.buttonbox.pack_start(self.quitbutton, expand=True, fill=True)
-
- self.buttonbox.pack_start(gtk.Label(''), expand=True, fill=True)
-
- self.makebutton = IconButton(_("_Make"), stock=gtk.STOCK_EXECUTE)
- self.makebutton.connect('clicked', self.make)
- self.makebutton.set_sensitive(False)
- self.buttonbox.pack_end(self.makebutton, expand=True, fill=True)
-
- self.box.pack_end(self.buttonbox, expand=False, fill=False)
-
- self.announce_entry.connect('changed', self.check_buttons)
- self.filebox.connect('changed', self.check_buttons)
- for w in self.tracker_radio.get_group():
- w.connect('clicked', self.check_buttons)
-
- self.box.pack_end(gtk.HSeparator(), expand=False, fill=False)
-
- self.add(self.box)
-
-# HelpWindow(None, makeHelp('maketorrent', defaults))
-
- self.box.show_all()
-## extraheight = self.dht_frame.size_request()[1] + \
-## self.comment_scroll.size_request()[1]
-## sr = self.box.size_request()
-## self.resize(sr[0] + SPACING*2, sr[1]+extraheight + SPACING*2)
- self.resize_to_fit()
- self.show_all()
-
- def toggle_tracker_dht(self, widget):
- if widget.get_active():
- self.config['use_tracker'] = widget.value
-
- for e in [self.announce_entry, self.dht_nodes]:
- if widget.entry is e:
- e.set_sensitive(True)
- else:
- e.set_sensitive(False)
-
- def choose_files(self,widget):
- fn = None
- if self.config['torrent_dir']:
- fn = self.config['torrent_dir']
- else:
- fn = Desktop.desktop
-
- FileOrFolderSelection(self, fullname=fn,
- got_multiple_location_func=self.add_files)
-
- def add_files(self, names):
- for name in names:
- self.filebox.set_text(name)
- torrent_dir = os.path.split(name)[0]
- if torrent_dir[-1] != os.sep:
- torrent_dir += os.sep
- self.config['torrent_dir'] = torrent_dir
-
- def get_piece_size_exponent(self):
- i = self.piece_size.get_active()
- exp = i+self.piece_size.offset
- self.config['piece_size_pow2'] = exp
- return exp
-
- def get_file(self):
- return self.filebox.get_text()
-
- def get_announce(self):
- if self.config['use_tracker']:
- announce = self.announce_entry.get_text()
- self.config['tracker_name'] = announce
- else:
- announce = self.dht_nodes.get_text()
- return announce
-
- def make(self, widget):
- file_name = self.get_file()
- piece_size_exponent = self.get_piece_size_exponent()
- announce = self.get_announce()
- comment = self.comment_buffer.get_text(
- *self.comment_buffer.get_bounds())
-
- if self.config['use_tracker']:
- self.add_tracker(announce)
- errored = False
- if not errored:
- d = ProgressDialog(self, [file_name,], announce,
- piece_size_exponent, comment)
- d.main()
-
- def check_buttons(self, *widgets):
- file_name = self.get_file()
- tracker = self.announce_entry.get_text()
- if file_name not in (None, ''):
- if self.config['use_tracker']:
- if len(tracker) >= len('http://x.cc'):
- self.makebutton.set_sensitive(True)
- else:
- self.makebutton.set_sensitive(False)
- else:
- self.makebutton.set_sensitive(True)
- else:
- self.makebutton.set_sensitive(False)
-
- def save_config(self):
- def error_callback(error, string): print string
- configfile.save_ui_config(self.config, 'maketorrent', ui_options, error_callback)
-
- def quit(self, widget):
- self.save_config()
- self.destroy()
-
- def add_tracker(self, tracker_name):
- try:
- self.tracker_list.pop(self.tracker_list.index(tracker_name))
- except ValueError:
- pass
- self.tracker_list[0:0] = [tracker_name,]
-
- self.config['tracker_list'] = ','.join(self.tracker_list)
- self.build_completion()
-
- def build_completion(self):
- liststore = gtk.ListStore(gobject.TYPE_STRING)
- for t in self.tracker_list:
- liststore.append([t])
- self.announce_completion.set_model(liststore)
-
- def resize_to_fit(self, *args):
- garbage, y = self.size_request()
- x, garbage = self.get_size()
- gobject.idle_add(self.resize, x, y)
-
-
-class AppWindow(MainWindow):
- def quit(self, widget):
- MainWindow.quit(self, widget)
- gtk.main_quit()
-
-
-class NodeList(gtk.TreeView):
- def __init__(self, parent, nodelist):
- self.store = gtk.ListStore(gobject.TYPE_STRING, gobject.TYPE_STRING)
- pre_size_list = ['router.bittorrent.com', '65536']
- self.store.append(pre_size_list)
-
- gtk.TreeView.__init__(self, self.store)
- self.set_enable_search(False)
-
- self.host_render = gtk.CellRendererText()
- self.host_render.set_property('editable', True)
- self.host_column = gtk.TreeViewColumn(_("_Host"), self.host_render,
- text=0)
- self.append_column(self.host_column)
- self.host_render.connect('edited', self.store_host_value)
-
- self.port_render = gtk.CellRendererText()
- self.port_render.set_property('editable', True)
- self.port_column = gtk.TreeViewColumn(_("_Port"), self.port_render,
- text=1)
- self.append_column(self.port_column)
- self.port_render.connect('edited', self.store_port_value)
-
- #self.columns_autosize()
- #self.host_column.set_fixed_width(self.host_column.get_width())
- #self.host_column.set_sizing(gtk.TREE_VIEW_COLUMN_FIXED)
- #self.realize()
- #self.port_column.set_fixed_width(self.port_column.get_width())
- #self.port_column.set_sizing(gtk.TREE_VIEW_COLUMN_FIXED)
-
- self.store.clear()
-
- for i, e in enumerate(nodelist.split(',')):
- host, port = e.split(':')
- self.store.append((host, port))
-
- if i < MAXIMUM_NODES - 1:
- self.store.append(('',''))
-
- def store_host_value(self, cell, row, value):
- parts = value.split('.')
- if value != '':
- for p in parts:
- if not p.isalnum():
- return
- try:
- value = value.encode('idna')
- except UnicodeError:
- return
- it = self.store.get_iter_from_string(row)
- self.store.set(it, 0, str(value))
- self.check_row(row)
-
- def store_port_value(self, cell, row, value):
- if value != '':
- try:
- v = int(value)
- if v > 65535:
- value = 65535
- if v < 0:
- value = 0
- except:
- return # return on non-integer values
- it = self.store.get_iter_from_string(row)
- self.store.set(it, 1, str(value))
- #curs = self.get_cursor()
- #print curs
- #print type(curs[0][0])
-
- self.check_row(row)
- #newpath = ((int(row)+1,), self.port_column)
- #print newpath
- #self.set_cursor(newpath)
-
- def check_row(self, row):
- # called after editing to see whether we should add a new
- # blank row, or remove the now blank currently edited row.
- it = self.store.get_iter_from_string(row)
- host_value = self.store.get_value(it, 0)
- port_value = self.store.get_value(it, 1)
- if host_value and port_value and \
- int(row) == len(self.store)-1 and \
- int(row) < MAXIMUM_NODES -1 :
- self.store.append(('',''))
- elif host_value == '' and \
- port_value == '' and \
- int(row) != len(self.store)-1:
- self.store.remove(it)
-
- def get_nodes(self):
- retlist = []
- it = self.store.get_iter_first()
- while it:
- host = self.store.get_value(it, 0)
- port = self.store.get_value(it, 1)
- if host != '' and port != '':
- retlist.append((host,port))
- it = self.store.iter_next(it)
- return retlist
-
- def get_text(self):
- nodelist = self.get_nodes()
- return ','.join(['%s:%s'%node for node in nodelist])
-
-
-class ProgressDialog(gtk.Dialog):
-
- def __init__(self, parent, file_list, announce, piece_length, comment):
- gtk.Dialog.__init__(self, parent=parent, flags=gtk.DIALOG_MODAL|gtk.DIALOG_DESTROY_WITH_PARENT)
- self.set_size_request(400,-1)
- self.set_border_width(SPACING)
- self.set_title(_("Building torrents..."))
- self.file_list = file_list
- self.announce = announce
- self.piece_length = piece_length
- self.comment = comment
-
- self.flag = Event() # ???
-
- self.label = gtk.Label(_("Checking file sizes..."))
- self.label.set_line_wrap(True)
-
- self.vbox.set_spacing(SPACING)
- self.vbox.pack_start(lalign(self.label), expand=False, fill=False)
-
- self.progressbar = gtk.ProgressBar()
- self.vbox.pack_start(self.progressbar, expand=False, fill=False)
-
- self.cancelbutton = gtk.Button(stock=gtk.STOCK_CANCEL)
- self.cancelbutton.connect('clicked', self.cancel)
- self.action_area.pack_end(self.cancelbutton)
-
- self.show_all()
-
- self.done_button = gtk.Button(stock=gtk.STOCK_OK)
- self.done_button.connect('clicked', self.cancel)
-
- self.seed_button = gtk.Button(_("Start seeding"))
- self.seed_button.connect('clicked', self.seed)
-
- def main(self):
- self.complete()
-
- def seed(self, widget=None):
- for f in self.file_list:
- btspawn(None, 'bittorrent', f+EXTENSION, '--save_as', f)
- self.cancel()
-
- def cancel(self, widget=None):
- self.flag.set()
- self.destroy()
-
- def set_progress_value(self, value):
- self.progressbar.set_fraction(value)
- self._update_gui()
-
- def set_file(self, filename):
- self.label.set_text(_("building ") + filename + EXTENSION)
- self._update_gui()
-
- def _update_gui(self):
- while gtk.events_pending():
- gtk.main_iteration(block=False)
-
- def complete(self):
- try:
- make_meta_files(self.announce,
- self.file_list,
- flag=self.flag,
- progressfunc=self.set_progress_value,
- filefunc=self.set_file,
- piece_len_pow2=self.piece_length,
- comment=self.comment,
- use_tracker=config['use_tracker'],
- data_dir=config['data_dir'],
- )
- if not self.flag.isSet():
- self.set_title(_("Done."))
- self.label.set_text(_("Done building torrents."))
- self.set_progress_value(1)
- self.action_area.remove(self.cancelbutton)
- self.action_area.pack_start(self.seed_button)
- self.action_area.pack_start(self.done_button)
- self.seed_button.show()
- self.done_button.show()
- except (OSError, IOError), e:
- self.set_title(_("Error!"))
- self.label.set_text(_("Error building torrents: ") + str(e))
-
-
-
-
-def run():
- config, args = configfile.parse_configuration_and_args(defaults,
- 'maketorrent', [], 0, None)
- MainWindow(config)
-
-
-if __name__ == '__main__':
- config, args = configfile.parse_configuration_and_args(defaults,
- 'maketorrent', sys.argv[1:], 0, None)
- AppWindow(config)
- try:
- gtk.main()
- except KeyboardInterrupt:
- # gtk.mainloop not running
- # exit and don't save config options
- sys.exit(1)
diff --git a/changetracker-console.py b/nohgooee-changetracker
index 976a536..d523e6e 100755
--- a/changetracker-console.py
+++ b/nohgooee-changetracker
@@ -12,12 +12,12 @@
# Written by Henry 'Pi' James and Bram Cohen
-from BitTorrent.platform import install_translation
+from NohGooee.platform import install_translation
install_translation()
from os.path import basename
from sys import argv, exit
-from BitTorrent.bencode import bencode, bdecode
+from NohGooee.bencode import bencode, bdecode
if len(argv) < 3:
print _("Usage: %s TRACKER_URL [TORRENTFILE [TORRENTFILE ... ] ]") % basename(argv[0])
diff --git a/maketorrent-console.py b/nohgooee-maketorrent
index c103fe0..ebbdb5f 100755
--- a/maketorrent-console.py
+++ b/nohgooee-maketorrent
@@ -13,15 +13,15 @@
# Written by Bram Cohen
if __name__ == '__main__':
- from BitTorrent.platform import install_translation
+ from NohGooee.platform import install_translation
install_translation()
import sys
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent import configfile
-from BitTorrent.makemetafile import make_meta_files
-from BitTorrent.parseargs import parseargs, printHelp
-from BitTorrent import BTFailure
+from NohGooee.defaultargs import get_defaults
+from NohGooee import configfile
+from NohGooee.makemetafile import make_meta_files
+from NohGooee.parseargs import parseargs, printHelp
+from NohGooee import BTFailure
defaults = get_defaults('maketorrent-console')
defaults.extend([
diff --git a/launchmany-console.py b/nohgooee-seed
index f327178..e650d6d 100755
--- a/launchmany-console.py
+++ b/nohgooee-seed
@@ -13,18 +13,18 @@
# Written by John Hoffman
if __name__ == '__main__':
- from BitTorrent.platform import install_translation
+ from NohGooee.platform import install_translation
install_translation()
import sys
import os
-from BitTorrent.launchmanycore import LaunchMany
-from BitTorrent.defaultargs import get_defaults
-from BitTorrent.parseargs import parseargs, printHelp
-from BitTorrent import configfile
-from BitTorrent import version
-from BitTorrent import BTFailure
+from NohGooee.launchmanycore import LaunchMany
+from NohGooee.defaultargs import get_defaults
+from NohGooee.parseargs import parseargs, printHelp
+from NohGooee import configfile
+from NohGooee import version
+from NohGooee import BTFailure
exceptions = []
diff --git a/btseed.init b/nohgooee-seed.init
index 7214eed..7214eed 100755
--- a/btseed.init
+++ b/nohgooee-seed.init
diff --git a/torrentinfo-console.py b/nohgooee-torrentinfo
index e9263e0..2f3d15a 100755
--- a/torrentinfo-console.py
+++ b/nohgooee-torrentinfo
@@ -12,14 +12,14 @@
# Written by Henry 'Pi' James, Loring Holden and Matt Chisholm
-from BitTorrent.platform import install_translation
+from NohGooee.platform import install_translation
install_translation()
from sys import *
from os.path import *
from sha import *
-from BitTorrent.bencode import *
-from BitTorrent import version, app_name
+from NohGooee.bencode import *
+from NohGooee import version, app_name
NAME, EXT = splitext(basename(argv[0]))
diff --git a/bttrack.init b/nohgooee-tracker.init
index 319c526..319c526 100755
--- a/bttrack.init
+++ b/nohgooee-tracker.init
diff --git a/bittorrent-tracker.py b/nohgooee-tracker.tac
index 4c176da..e957433 100755
--- a/bittorrent-tracker.py
+++ b/nohgooee-tracker.tac
@@ -12,10 +12,10 @@
# Written by Bram Cohen
-from BitTorrent.platform import install_translation
+from NohGooee.platform import install_translation
install_translation()
-from BitTorrent.track import Tracker, InfoPage, Scrape, File, Announce, FavIcon
+from NohGooee.track import Tracker, InfoPage, Scrape, File, Announce, FavIcon
from twisted.application import internet, service
from twisted.web import static, server
diff --git a/redirdonate.html b/redirdonate.html
deleted file mode 100644
index f3d4f0c..0000000
--- a/redirdonate.html
+++ /dev/null
@@ -1 +0,0 @@
-<meta http-equiv="refresh" content="0;url=http://www.bittorrent.com/donate.html">
diff --git a/setup.py b/setup.py
index 5ff1134..ff2d64f 100644
--- a/setup.py
+++ b/setup.py
@@ -15,13 +15,13 @@
import os
os.system('sh ./makei18n.sh')
-from BitTorrent.platform import install_translation
+from NohGooee.platform import install_translation
install_translation()
import sys
from distutils.core import setup, Extension
-from BitTorrent import version, languages
-from BitTorrent.platform import calc_unix_dirs
+from NohGooee import version, languages
+from NohGooee.platform import calc_unix_dirs
import glob
diff --git a/test/test_ClientIdentifier.py b/test/test_ClientIdentifier.py
index 220fe7e..ea79eec 100644
--- a/test/test_ClientIdentifier.py
+++ b/test/test_ClientIdentifier.py
@@ -23,7 +23,7 @@
import sys
sys.path = ['.',] + sys.path #HACK
-from BitTorrent import ClientIdentifier
+from NohGooee import ClientIdentifier
print "Using:", ClientIdentifier
diff --git a/torrentinfo-console b/torrentinfo-console
deleted file mode 120000
index e436c6c..0000000
--- a/torrentinfo-console
+++ /dev/null
@@ -1 +0,0 @@
-torrentinfo-console.py \ No newline at end of file