1
mirror of https://github.com/qbittorrent/qBittorrent synced 2025-10-14 11:52:15 +02:00

Compare commits

..

179 Commits

Author SHA1 Message Date
Christophe Dumez
6cf2b44b8a Tagged v2.2.3 release 2010-04-04 20:05:10 +00:00
Christophe Dumez
ba22fa8331 Bump to v2.2.3 2010-04-04 19:55:16 +00:00
Christophe Dumez
5ce02cb612 Clean fix for progress display with cleanlooks style 2010-03-31 14:36:16 +00:00
Christophe Dumez
1013f39a42 A msvc compilation fix 2010-03-30 19:40:35 +00:00
Christophe Dumez
cd5c4bf464 On Windows, add qBittorrent executable folder to PATH envar 2010-03-30 19:03:12 +00:00
Christophe Dumez
84bfc54b03 Updated Changelog 2010-03-30 12:13:43 +00:00
Christophe Dumez
5b3b5eb2ef Enable Apply button when alternative rate limits are changed 2010-03-30 12:09:51 +00:00
Christophe Dumez
990a863d41 Several compilation and execution fixes for Windows and OS/2
Cleaner binutils gold linker support
2010-03-30 11:39:40 +00:00
Christophe Dumez
7f27d10735 Fix possible error in boost exception handling 2010-03-29 10:44:33 +00:00
Christophe Dumez
1377a75a53 Fix typo 2010-03-27 16:00:47 +00:00
Christophe Dumez
bcd33fc861 ANother Windows fix 2010-03-27 15:58:28 +00:00
Christophe Dumez
46d8fa1656 Another compilation fix 2010-03-27 15:50:50 +00:00
Christophe Dumez
28cf69b84d Windows compilation fix improvement 2010-03-27 09:17:40 +00:00
Christophe Dumez
89389df74d Compilation fix on Windows (getuid missing) 2010-03-27 09:06:01 +00:00
Christophe Dumez
77c29f48cb Fix possible crash when deleting a torrent just after pausing it 2010-03-23 21:42:33 +00:00
Christophe Dumez
c5d92f3d69 FEATURE: DHT port can be set from Web UI 2010-03-22 20:41:36 +00:00
Christophe Dumez
54487c8247 Improvement to last commit 2010-03-22 19:42:47 +00:00
Christophe Dumez
be64008870 Bump to v2.2.2 2010-03-22 19:12:34 +00:00
Christophe Dumez
8113b150dd Updated french translation 2010-03-22 19:07:36 +00:00
Christophe Dumez
4a33367cb0 Fix to last commit 2010-03-22 19:04:48 +00:00
Christophe Dumez
0af5d82114 BUGFIX: Fix possible crash with folder scanning 2010-03-22 18:57:32 +00:00
Christophe Dumez
10c4fd330a I18N: Updated Polish translation (thanks Szymon Świerkosz) 2010-03-22 18:24:32 +00:00
Christophe Dumez
9a30d5a295 Properly raise SIGSEGV/SIGABRT after catching it 2010-03-20 21:44:11 +00:00
Christophe Dumez
724b47d999 Save fast resume data every 3 minutes 2010-03-20 21:25:31 +00:00
Christophe Dumez
2c0f7c33a2 Made M3U files previewable 2010-03-20 19:38:21 +00:00
Christophe Dumez
ce33e266fe Attempt to fix mac compilation 2010-03-20 19:14:17 +00:00
Christophe Dumez
2f291daefa Fix Ctrl+A in Web UI 2010-03-20 15:48:48 +00:00
Christophe Dumez
722f2aeb5d BUGFIX: Ask for user confirmation for recursive torrent download
BUGFIX: Fix "add file" dialog in torrent creation tool
2010-03-20 11:33:09 +00:00
Christophe Dumez
d5b9598b5b BUGFIX: Fix file filtering in complex torrents 2010-03-19 11:14:35 +00:00
Christophe Dumez
cc7d74b67c BUGFIX: Fix progress display with cleanlook style 2010-03-19 08:06:56 +00:00
Christophe Dumez
e853b0b736 Code optimization 2010-03-18 23:25:17 +00:00
Christophe Dumez
5e395b24a9 Code optimization 2010-03-18 23:13:41 +00:00
Christophe Dumez
9c3789f83f FEATURE: Display pieces that are being downloaded 2010-03-18 23:03:56 +00:00
Christophe Dumez
758595dc8c BUGFIX: Added back file prioritizing in Web UI 2010-03-18 20:07:10 +00:00
Christophe Dumez
01f9e989ef Bump to v2.2.1 2010-03-18 19:32:43 +00:00
Christophe Dumez
eb9f0cb559 Added back folder watching to Web UI 2010-03-18 19:27:23 +00:00
Christophe Dumez
2592948182 Fix Web UI compatiblity with Safari 2010-03-16 00:24:39 +00:00
Christophe Dumez
6f6ab1c439 Qt 4.4 compilation fix 2010-03-15 18:12:55 +00:00
Christophe Dumez
b10e606dda Branched v2.2.x 2010-03-14 20:44:17 +00:00
Christophe Dumez
9034094cf9 Fix headless compilation 2010-03-04 08:36:23 +00:00
Christophe Dumez
c48766aeb7 - Slight RSS cleanup 2010-03-03 23:11:40 +00:00
Christophe Dumez
28a6afeb02 Clean up and optimize transferlist class 2010-03-03 21:59:12 +00:00
Christophe Dumez
c8d0f5a104 Folder scanning settings are now properly saved 2010-03-03 21:17:45 +00:00
Christophe Dumez
3c396257de Use QXmlStreamReader instead of QDomDocument to save memory when parsing the RSS documents 2010-03-03 21:11:40 +00:00
Christophe Dumez
a9be841d2d Keep on cleaning up 2010-03-03 19:04:34 +00:00
Christophe Dumez
7d0581a7a5 Started code clean up and optimization 2010-03-03 17:27:25 +00:00
Christophe Dumez
4efeb66b73 Remove useless cast
Added missing include that caused misleading error message
2010-03-03 15:23:34 +00:00
Christophe Dumez
3b05f8b4b4 Reorganized header file 2010-03-03 14:48:49 +00:00
Christophe Dumez
6b4f09d740 - Cleanup GUI class 2010-03-03 14:42:57 +00:00
Christophe Dumez
f1b02c1280 Make sure options and console windows are deleted on exit 2010-03-03 13:15:13 +00:00
Christophe Dumez
3d546a4c5d BUGFIX: Only one log window can be opened at a time 2010-03-03 13:07:27 +00:00
Christophe Dumez
19368bcefa Added virtual destructor to avoid memory leaks 2010-03-03 13:03:13 +00:00
Christophe Dumez
dbbf26449c - Clean up main code
- Use fromLocal8Bit() instead fromUtf8() on program parameters
2010-03-03 12:55:42 +00:00
Christophe Dumez
8f28804f8c Added Json encode support for QVariantList and QStringList 2010-02-28 17:24:35 +00:00
Christophe Dumez
b7edfea4ce Disable scan folder preferences in Web UI (for now) since it was broken by "multipleScanFolders" patch 2010-02-28 17:17:14 +00:00
Christophe Dumez
23b2f94c40 Call qDeleteAll on m_pathList 2010-02-28 16:23:59 +00:00
Christophe Dumez
8f40f41fef Qt4.4 Compatibility fix (QDate::StandaloneFormat) 2010-02-28 16:07:09 +00:00
Christophe Dumez
33f868144b Use a regular pointer instead of a QSharedPointer to fix Qt 4.4 compatibility 2010-02-28 16:00:52 +00:00
Christophe Dumez
b2545bb709 Added Christian Kandeler to contributors 2010-02-28 15:50:25 +00:00
Christophe Dumez
3b6e1e82d9 Updated language files 2010-02-28 15:22:31 +00:00
Christophe Dumez
7710c88797 FEATURE: Support for multiple scan folders
* Patch by Christian Kandeler (Thanks!)
2010-02-28 15:15:00 +00:00
Christophe Dumez
4d5001d18d Display more useful information in log window when an I/O error occurs
I/O errors are now reported in nox version too
2010-02-22 19:30:36 +00:00
Christophe Dumez
0f4f108eb5 BUGFIX: Fix ratio calculation for directly seeded torrents (Thanks phorane) 2010-02-17 08:10:57 +00:00
Christophe Dumez
f0d0bb7170 FEATURE: Allow to change the priority of several files at once 2010-02-16 20:50:44 +00:00
Christophe Dumez
66157da5c2 Fix browse button for torrent export directory in preferences 2010-02-16 19:40:41 +00:00
Christophe Dumez
13493e1afe - Global Upload/Download rates can be set by clicking on the status bar values 2010-02-15 20:57:55 +00:00
Christophe Dumez
f6bfacda2c FEATURE: Global transfer information are displayed in the new Web UI status bar 2010-02-15 20:07:15 +00:00
Christophe Dumez
f7a86b5484 Add URL seeds from duplicate torrents to existing ones 2010-02-15 18:45:39 +00:00
Christophe Dumez
66cd3f8184 Fix save path display in Web UI too 2010-02-14 15:30:10 +00:00
Christophe Dumez
3a237c93be Make sure torrent save path is displayed 2010-02-14 15:22:34 +00:00
Christophe Dumez
4c34066727 FEATURE: Trackers can be added from Web UI 2010-02-14 15:15:35 +00:00
Christophe Dumez
1960008c83 Fix Web UI authentication with Konqueror 2010-02-12 00:00:55 +00:00
Christophe Dumez
deffbd6321 Updated Russian translation 2010-02-11 11:45:30 +00:00
Christophe Dumez
53927c9aa0 Revert useless 64bits patch 2010-02-10 23:22:47 +00:00
Christophe Dumez
d84346616a Added -L/usr/lib64 for 64bits 2010-02-10 22:28:01 +00:00
Christophe Dumez
e1183dbc0b Bump to beta4 2010-02-10 21:34:31 +00:00
Christophe Dumez
602f1574ca - Fix possible race condition in search engine 2010-02-10 21:20:44 +00:00
Christophe Dumez
358f7d16da Add back CONFIG += link_pkgconfig or it causes crashes 2010-02-10 21:14:44 +00:00
Christophe Dumez
e4006d6175 - Update helper version 2010-02-10 20:15:21 +00:00
Christophe Dumez
949b4ce4e9 - Improve gzip file detection in HTTP downloader (do not trust HTTP header, check magic number) 2010-02-10 20:02:55 +00:00
Christophe Dumez
cbafac8ea9 - Make it impossible to open more than one options dialog 2010-02-09 23:32:54 +00:00
Christophe Dumez
e4bf116ce8 - Fix a crash when adding an already existing torrent 2010-02-09 21:35:20 +00:00
Christophe Dumez
bccdad4b1b - Fix memory leak in rss 2010-02-09 21:20:43 +00:00
Christophe Dumez
9b372b3cce Important fix regarding actions on selected torrents. With filters enabled, it could happen that non-selected torrents are affected. 2010-02-09 20:44:33 +00:00
Christophe Dumez
98d0c00f85 Link against boost and ssl to fix issues with gold linker 2010-02-09 12:01:13 +00:00
Christophe Dumez
9d2f2230ee - Fix bugs with new feature: "Add trackers from duplicate torrent" 2010-02-09 08:06:49 +00:00
Christophe Dumez
81c6958428 - Bump to beta3 2010-02-08 19:06:21 +00:00
Christophe Dumez
f976eda6a9 - Updated French translation 2010-02-08 19:05:41 +00:00
Christophe Dumez
fe8d5a3528 - Fix file prioritizing in a torrent 2010-02-08 18:49:04 +00:00
Christophe Dumez
240c3508fe Fix possible crash when changing torrents label 2010-02-07 18:37:26 +00:00
Christophe Dumez
1065f5fb86 FEATURE: If 2 torrents have the same hash, add new trackers to the existin
g torrent
2010-02-07 14:31:45 +00:00
Christophe Dumez
2b37986007 Updated Spanish/Catalan translations 2010-02-06 21:45:47 +00:00
Christophe Dumez
22d0c4a241 - Fix possible crash when removing a torrent 2010-02-06 21:31:51 +00:00
Christophe Dumez
dd47ce6767 Fix font size of two torrent addition dialog buttons (Patch by Mariusz Fik) 2010-02-05 19:06:11 +00:00
Christophe Dumez
5c80ce42e0 Cosmetic fix to usage display (--help)
Usage display is now localized
2010-02-05 19:02:27 +00:00
Christophe Dumez
adb727d282 Make sure seeding torrents display a progress of 100% 2010-02-04 20:18:58 +00:00
Christophe Dumez
e17ca355ae Startup optimization 2010-02-04 19:16:04 +00:00
Christophe Dumez
b80940ac4f - Optimize startup speed (do not resave fastresume data for torrents that were seeded in the previous session) 2010-02-04 17:19:00 +00:00
Christophe Dumez
1eca139db9 Fix new "Automatically recheck torrents on completion" feature (would keep on rechecking) 2010-02-03 19:44:19 +00:00
Christophe Dumez
25278beb2f Minor code optimization 2010-02-03 19:31:13 +00:00
Christophe Dumez
5922ffff62 Fix to Spanish and catalan translations 2010-02-03 18:55:49 +00:00
Christophe Dumez
ff084e9681 - Fixes to German translation 2010-02-03 07:59:36 +00:00
Christophe Dumez
86e5d219d2 Updated Ukranian translation
Added Oleh Prypin as Ukrainian translator
2010-02-02 20:24:52 +00:00
Christophe Dumez
b78e0a54ed Updated spanish and catalan translations 2010-02-02 20:05:47 +00:00
Christophe Dumez
4bfacb8b91 - Clear torrent errors when starting a torrent 2010-01-31 19:03:34 +00:00
Christophe Dumez
e9ad58a373 Improved application style handling 2010-01-31 17:46:21 +00:00
Christophe Dumez
09c48539ad - COSMETIC: Improved style management 2010-01-31 17:30:17 +00:00
Christophe Dumez
3693ecdd30 Moved peer resolution settings to advanced settings 2010-01-31 16:43:19 +00:00
Christophe Dumez
ddc66e6005 - Cosmetic changes to advanced preferences 2010-01-31 16:34:38 +00:00
Christophe Dumez
fd0b1f8931 - Did not mean to commit that 2010-01-31 16:27:05 +00:00
Christophe Dumez
1a4f638ff6 - Moved "Transfer list refresh interval" to advanced settings 2010-01-31 16:25:04 +00:00
Christophe Dumez
77239db3c5 FEATURE: Torrents can be automatically rechecked on completion 2010-01-31 16:14:56 +00:00
Christophe Dumez
0ea59c8d58 Bump to beta2 2010-01-31 16:00:50 +00:00
Christophe Dumez
54e2a8c7fe - Update language files 2010-01-31 16:00:14 +00:00
Christophe Dumez
245a8e0a3a FEATURE: User can choose to include the protocol overhead in transfer limits 2010-01-31 15:57:07 +00:00
Christophe Dumez
51e474c893 FEATURE: User can choose to apply transfer limits on LAN too 2010-01-31 15:42:24 +00:00
Christophe Dumez
81d3e64518 - Advanced preferences: Property column should not be editable 2010-01-31 15:31:41 +00:00
Christophe Dumez
95da161be3 FEATURE: Outgoing ports range can be customized (for QoS) 2010-01-31 15:27:54 +00:00
Christophe Dumez
8618f13b7a - Created "Advanced settings" tab in program preferences and moved "Disk cache" there 2010-01-31 15:11:15 +00:00
Christophe Dumez
e24e7578f2 Added "Export .torrent files to..." feature to the Web UI
Fix Scan dir preferences in Web UI
2010-01-31 13:47:57 +00:00
Christophe Dumez
a03ad3de23 FEATURE: Torrent files can be exported to a given directory
BUGFIX: Fix crash when double-clicking on a torrent that has no metadata to open its save path
2010-01-31 13:09:46 +00:00
Christophe Dumez
9bd40a9b79 - Updated language files 2010-01-30 18:17:27 +00:00
Christophe Dumez
b4b61b9b7d - Launch directly the new search instead of stopping the current one if the user changed the search pattern 2010-01-30 18:15:25 +00:00
Christophe Dumez
5656fe9a9b FEATURE: Added "Upload/Download limit" columns to transfer list 2010-01-30 17:47:01 +00:00
Christophe Dumez
fb79146ae6 FEATURE: Added "Added/Completed On" columns to transfer list 2010-01-30 16:28:07 +00:00
Christophe Dumez
ba27191b2a - Fix compilation error when geoip database is embedded 2010-01-29 19:01:32 +00:00
Christophe Dumez
dc87aa3d5c - Download thread now supports HTTP redirection 2010-01-29 18:37:47 +00:00
Christophe Dumez
83cf3aebab Clean up URL seed code
Center bandwidth limiting dialogs
2010-01-27 20:34:53 +00:00
Christophe Dumez
dedd9bd03c - Add more RSS and tracker debug 2010-01-27 12:21:14 +00:00
Christophe Dumez
ab36a358b7 - Fix "Append .!qB extension to incomplete files". The extension would stay under certain conditions 2010-01-26 08:02:15 +00:00
Christophe Dumez
6ea97f09cf - Updated spanish and catalan translations 2010-01-25 20:06:22 +00:00
Christophe Dumez
5f7822d202 Fix alternative upload speed limit overwriting standard upload speed limit. 2010-01-25 19:54:46 +00:00
Christophe Dumez
6a87225dd0 - Fix typo in src.pro 2010-01-24 19:19:58 +00:00
Christophe Dumez
b6f56c0812 - Bump to v2.2.0beta1 2010-01-24 18:16:42 +00:00
Christophe Dumez
c4ce2a2549 Improved user friendlyness of size units (Use 1KiB/s instead of 1024B/s)
Optimized transfer list repainting
2010-01-24 18:06:51 +00:00
Christophe Dumez
41650da297 - I should not have to call repaint() manually 2010-01-24 17:16:20 +00:00
Christophe Dumez
74c61e6805 - Fix for translations 2010-01-24 17:03:57 +00:00
Christophe Dumez
e8dd7bbcc9 - Fix possible race condition in RSS that could cause crash on startup (bug #511441) 2010-01-24 16:46:10 +00:00
Christophe Dumez
335d012d55 - Updated a field that should not be translatable 2010-01-24 15:55:55 +00:00
Christophe Dumez
17fc58840a - Updated language files 2010-01-24 15:37:58 +00:00
Christophe Dumez
0e8c55b9f5 FEATURE: Added back file prioritizing in a torrent (it seems users were using it after all) 2010-01-24 15:26:29 +00:00
Christophe Dumez
d581f653c6 Nox compilation fix 2010-01-24 12:07:07 +00:00
Christophe Dumez
48dbaf05ae FEATURE: Bandwidth scheduler (automatically use alternative speed limits for a given period) 2010-01-24 11:57:15 +00:00
Christophe Dumez
540da69d61 - Remember alternative speeds state on restart 2010-01-23 20:45:14 +00:00
Christophe Dumez
06efd64a80 FEATURE: User can set alternative speed limits for fast toggling
Bandwidth scheduler is not functional yet (but appears in program preferences)
2010-01-23 20:44:09 +00:00
Christophe Dumez
62d872984b Make sure invalid torrent are removed from the transfer list 2010-01-23 19:15:00 +00:00
Christophe Dumez
1dd11dd8f8 Fix possible issue where torrents would not be displayed in the transfer list 2010-01-23 19:01:10 +00:00
Christophe Dumez
2ce375d8eb - Improved date handling in RSS 2010-01-23 16:16:42 +00:00
Christophe Dumez
8ed0e58d63 - "Open destination folder" now opens torrent root folder (if it contains one) instead of the parent folder 2010-01-23 09:54:50 +00:00
Christophe Dumez
660a6929fd Apply patch from Elrond to improve transfer speed display in peers list 2010-01-21 23:59:55 +00:00
Christophe Dumez
44f6c972d4 Moved screenCenter function to misc.h to avoid code duplication
Make sure torrent deletion dialog is now centered on screen
2010-01-21 22:23:13 +00:00
Christophe Dumez
6a6077bf1d Improved previous patch: Force recheck only if we detected that renaming overwrote an existing file 2010-01-21 21:14:54 +00:00
Christophe Dumez
30234a4e78 - Force recheck after renaming files 2010-01-21 20:27:59 +00:00
Christophe Dumez
dc9edf7538 - Fix overwrite check when renaming a folder in a torrent 2010-01-21 18:33:53 +00:00
Christophe Dumez
92574458d0 "Add in pause" setting is no longer ignored if torrent is loaded from a watched directory 2010-01-20 18:53:11 +00:00
Christophe Dumez
c35ef9ad15 - Fix opening on torrent folder in explorer when path contains special characters or spaces 2010-01-20 18:41:12 +00:00
Christophe Dumez
4059bcc0fa Updated Russian translation 2010-01-20 18:38:38 +00:00
Christophe Dumez
1840d1c49f - Paused torrents can now be rechecked 2010-01-20 18:02:26 +00:00
Christophe Dumez
cbd948f6f3 Updated hungarian translation 2010-01-20 16:02:56 +00:00
Christophe Dumez
454c093033 - qBittorrent can now listen on ports < 1024 (must be root) 2010-01-20 09:54:51 +00:00
Christophe Dumez
45eaf7ce58 - Updated Simplified chinese translation (legal notice was missing) 2010-01-20 09:44:45 +00:00
Christophe Dumez
04b7af4df5 - Fix renaming of files with unicode characters 2010-01-20 08:45:31 +00:00
Christophe Dumez
8c6978be82 - Exceptions to "Add Torrent is paused" setting can now be set in torrent addition dialog 2010-01-20 08:35:36 +00:00
Christophe Dumez
6c9e7156f7 - Fix magnet link support 2010-01-19 23:43:29 +00:00
Christophe Dumez
bc89845523 - Improve configure file output 2010-01-19 23:12:13 +00:00
Christophe Dumez
9ffe9c2006 - Configure file now checks for pkg-config executable since it is required to detect libtorrent-rasterbar 2010-01-19 22:55:49 +00:00
Christophe Dumez
1d598d7772 - Nox version should not require libqtxml 2010-01-19 22:40:23 +00:00
Christophe Dumez
7f576ccc82 - Fix folder renaming (would misbehave under certain conditions) 2010-01-19 22:35:54 +00:00
Christophe Dumez
d5da8a6277 - Save torrent file as soon as we get the torrent metadata so that it does not have to be redownloaded on restart 2010-01-19 21:47:53 +00:00
Christophe Dumez
a297204b27 Updated spanish and catalan translations 2010-01-19 09:42:55 +00:00
Christophe Dumez
e0182bb03e - Enabling debug in trunk 2010-01-19 00:32:53 +00:00
Christophe Dumez
ca5bf5e9d7 Removed useless include in project file 2010-01-18 23:52:05 +00:00
Christophe Dumez
5475d730ff - Actual Qt4.4 compilation fix 2010-01-18 22:09:28 +00:00
Christophe Dumez
7796520580 - Attempt to fix compilation with Qt 4.4 2010-01-18 21:46:04 +00:00
Christophe Dumez
340500c351 - Fix compilation warning in nox mode (introduced in v2.2.0alpha) 2010-01-18 21:28:54 +00:00
Christophe Dumez
043d33ff91 - Updated language files 2010-01-18 19:29:02 +00:00
Christophe Dumez
baf991b342 - The user must now press 'y' to accept the legal notice in nox mode (other keys will refuse and stop the program). Thanks Mariusz Fik 2010-01-18 19:20:59 +00:00
Christophe Dumez
dc47e90126 Applied legal notice patch for Mariusz Fik 2010-01-18 19:16:18 +00:00
Christophe Dumez
67e3f9e686 - Trunk is now v2.2.0alpha 2010-01-18 19:14:33 +00:00
150 changed files with 23995 additions and 15633 deletions

View File

@@ -6,6 +6,7 @@ Contributors:
* Ishan Arora <ishan@qbittorrent.org>
* Arnaud Demaizière <arnaud@qbittorrent.org>
* Grigis Gaëtan <cipher16@gmail.com>
* Christian Kandeler <zambesi@users.sourceforge.net>
Code from other projects:
* files src/ico.cpp src/ico.h
@@ -60,7 +61,7 @@ Translations authors:
* files: src/lang/*.ts
copyright:
- Brazilian: Nick Marinho (nickmarinho@gmail.com)
- Bulgarian: Tsvetan & Boiko Bankov (emerge_life@users.sourceforge.net)
- Bulgarian: Tsvetan & Boyko Bankoff (emerge_life@users.sourceforge.net)
- Catalan: Francisco Luque Contreras (frannoe@ya.com)
- Chinese (Simplified): Guo Yue (yue.guo0418@gmail.com)
- Chinese (Traditional): Yi-Shun Wang (dnextstep@gmail.com)
@@ -86,5 +87,5 @@ Translations authors:
- Spanish: Francisco Luque Contreras (frannoe@ya.com)
- Swedish: Daniel Nylander (po@danielnylander.se)
- Turkish: Hasan Yilmaz (iletisim@hedefturkce.com)
- Ukrainian: Andrey Shpachenko (masterfix@users.sourceforge.net)
- Ukrainian: Andrey Shpachenko (masterfix@users.sourceforge.net) and Oleh Prypin (blaxpirit@gmail.com)
license: GPLv2

View File

@@ -1,45 +1,51 @@
* Mon Feb 8 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.1.4
- BUGFIX: Fix file prioritizing in a torrent
- BUGFIX: Make sure seeding torrents display a progress of 100%
- BUGFIX: Usage display was improved and localized (--help)
- BUGFIX: Fix possible crash when deleting a torrent
- BUGFIX: Fix possible crash when changing torrents label
* Sun Apr 04 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.2.3
- BUGFIX: Fix possible crash when deleting a torrent just after pausing it
- BUGFIX: Enable Apply button when alternative rate limits are changed
- BUGFIX: Source compatibility with Windows (Thanks Ishan Arora)
- BUGFIX: Source compatibility with eCS (OS/2) (Thanks Silvan Scherrer)
- BUGFIX: Cleaner binutils gold linker support
- BUGFIX: Clean fix for progress display with cleanlooks style
* Sun Jan 31 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.1.3
- BUGFIX: Fix "Append .!qB extension to complete files" (libtorrent v0.15)
- BUGFIX: Make sure bandwidth limiting dialogs are centered on screen
- BUGFIX: Added support for HTTP redirection
- BUGFIX: Fix compilation error when geoip database is embedded
- BUGFIX: Fix crash when double-clicking on a torrent that has no metadata to open its save path
- BUGFIX: Fix Scan directory preferences in Web UI
- BUGFIX: Clear torrent error state when resuming it
* Mon Mar 22 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.2.2
- FEATURE: DHT port can be set from Web UI
- BUGFIX: Fix possible crash with folder scanning
- BUGFIX: Fix Mac compilation
- BUGFIX: Save fast resume data every 3 minutes (for robustness)
- I18N: Updated Polish translation (thanks Szymon Świerkosz)
* Sun Jan 24 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.1.2
- FEATURE: Added back file prioritizing in a torrent
- BUGFIX: Fix issue causing torrents not to be displayed in the list
- BUGFIX: Make sure invalid torrent are removed from the transfer list
- BUGFIX: Fix overwrite check when renaming a folder in a torrent
- BUGFIX: Force a recheck after renaming files to avoid overwriting
- BUGFIX: Improve "Open destination folder" behavior
- BUGFIX: Fix race condition in RSS that could cause a crash on startup
- BUGFIX: Improved user friendlyness of size units
- BUGFIX: Optimized transfer list repainting
- COSMETIC: Improved transfer speed display in peers list
* Sat Mar 20 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.2.1
- FEATURE: Display pieces that are being downloaded
- FEATURE: Added back folder watching in Web UI
- FEATURE: Added back file prioritizing in Web UI
- BUGFIX: Fix compilation with Qt 4.4
- BUGFIX: Fix Web UI compatibility with Safari
- BUGFIX: Fix progress display with cleanlook style
- BUGFIX: Fix file filtering in complex torrents
- BUGFIX: Ask for user confirmation for recursive torrent download
- BUGFIX: Fix "add file" dialog in torrent creation tool
- BUGFIX: Fix "Ctrl+A" in Web UI
* Wed Jan 20 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.1.1
- BUGFIX: Fix compilation with Qt4.4
- BUGFIX: Save torrent metadata so that it does not have to be re-downloaded on restart (Magnet links)
- BUGFIX: Fix folder renaming in a torrent (would rename children under certain conditions)
- BUGFIX: Nox version no longer requires libQtXml
- BUGFIX: Configure file now checks for pkg-config executable which is required
- BUGFIX: Torrents added from magnet links were not remembered on restart
- BUGFIX: "Add in pause" setting can be ignored from torrent addition dialog
- BUGFIX: Fix renaming of files with unicode characters in their name
- BUGFIX: Fix typo in legal notice (startup)
- BUGFIX: Can listen on ports < 1024 (must be root)
- BUGFIX: Paused torrents can now be rechecked
- BUGFIX: Fix "open torrent destination" feature when path contains spaces
- I18N: Updated translations (Hungarian, Chinese, Russian)
* Sun Mar 14 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.2.0
- FEATURE: User can set alternative speed limits for fast toggling
- FEATURE: Bandwidth scheduler (automatically use alternative speed limits for a given period)
- FEATURE: Added "Added/Completed On" columns to transfer list
- FEATURE: Added "Upload/Download limit" columns to transfer list
- FEATURE: Torrent files can be exported to a given directory
- FEATURE: Outgoing ports range can be customized (for QoS)
- FEATURE: User can choose to apply transfer limits on LAN too
- FEATURE: User can choose to include the protocol overhead in transfer limits
- FEATURE: Torrents can be automatically rechecked on completion
- FEATURE: If 2 torrents have the same hash, add new trackers/URL seeds to the existing torrent
- FEATURE: Trackers can be added from Web UI
- FEATURE: Global transfer information are displayed in the new Web UI status bar
- FEATURE: Allow to change the priority of several files at once
- FEATURE: Support for multiple scan folders (Patch by Christian Kandeler)
- BUGFIX: Only one log window can be opened at a time
- BUGFIX: Optimized RSS module memory usage
- BUGFIX: Consider HTTP downloads >1MB as invalid .torrent files and abort
- BUGFIX: Fix Web UI authentication with some browsers
- BUGFIX: Set Web UI ban period to 1 hour
- COSMETIC: Improved style management
* Mon Jan 18 2010 - Christophe Dumez <chris@qbittorrent.org> - v2.1.0
- FEATURE: Graphical User Interface can be disabled at compilation time (headless running)

49
configure vendored
View File

@@ -21,6 +21,7 @@ Dependency options:
--disable-gui Disable qBittorrent Graphical user
interface for headless running
--with-libboost-inc=[path] Path to libboost include files
--with-libboost-lib=[path] Path to libboost library files
--disable-libnotify Disable use of libnotify
--disable-geoip-database Disable use of geoip-database
--with-geoip-database-embedded Geoip Database will be embedded in
@@ -152,6 +153,11 @@ while [ $# -gt 0 ]; do
shift
;;
--with-libboost-lib=*)
QC_WITH_LIBBOOST_LIB=$optarg
shift
;;
--disable-libnotify)
QC_DISABLE_libnotify="Y"
shift
@@ -190,6 +196,7 @@ echo DATADIR=$DATADIR
echo EX_QTDIR=$EX_QTDIR
echo QC_DISABLE_GUI=$QC_DISABLE_GUI
echo QC_WITH_LIBBOOST_INC=$QC_WITH_LIBBOOST_INC
echo QC_WITH_LIBBOOST_LIB=$QC_WITH_LIBBOOST_LIB
echo QC_DISABLE_libnotify=$QC_DISABLE_libnotify
echo QC_DISABLE_geoip_database=$QC_DISABLE_geoip_database
echo QC_WITH_GEOIP_DATABASE_EMBEDDED=$QC_WITH_GEOIP_DATABASE_EMBEDDED
@@ -312,11 +319,7 @@ public:
if(!conf->getenv("QC_DISABLE_GUI").isEmpty()) {
conf->addDefine("DISABLE_GUI");
}
if(QT_VERSION >= 0x040500) {
conf->addDefine("QT_4_5");
}
return(QT_VERSION >= 0x040400);
}
};
#line 1 "pkg-config.qcm"
@@ -359,12 +362,20 @@ public:
return false;
for(int n = 0; n < incs.count(); ++n)
conf->addIncludePath(incs[n]);
if(!libs.isEmpty())
conf->addLib(libs);
//if(!libs.isEmpty())
// conf->addLib(libs);
if(!conf->findPkgConfig("libtorrent-rasterbar", mode, adv_ver, &version, &incs, &libs, &other))
printf("\nWarning: libtorrent-rasterbar v%s was detected. Some feature will be disabled because they require v%s.\n", version.toLocal8Bit().data(), adv_ver.toUtf8().data());
else
conf->addDefine("LIBTORRENT_0_15");
// Get linking parameters
//QStringList params;
//QByteArray staticlibs;
//params << "--static" << "--libs" << "libtorrent-rasterbar";
//conf->doCommand("pkg-config", params, &staticlibs);
//conf->addLib(staticlibs.trimmed());
//libcrypto
conf->addLib("-lcrypto");
return true;
}
};
@@ -373,6 +384,7 @@ public:
-----BEGIN QCMOD-----
name: libboost
arg: with-libboost-inc=[path], Path to libboost include files
arg: with-libboost-lib=[path], Path to libboost library files
-----END QCMOD-----
*/
class qc_libboost : public ConfObj
@@ -422,6 +434,30 @@ public:
}
}
conf->addIncludePath(s);
// Find library
s = conf->getenv("QC_WITH_LIBBOOST_LIB");
if(!s.isEmpty()) {
if(!conf->checkLibrary(s, "boost_system-mt")) {
return false;
}
}else{
QStringList sl;
sl << "/usr/lib/";
sl << "/usr/lib64/";
sl << "/usr/local/lib/";
sl << "/usr/local/lib64/";
bool found = false;
foreach(s, sl){
if(conf->checkLibrary(s, "boost_system-mt")) {
found = true;
break;
}
}
if(!found)
return false;
}
conf->addLib(QString("-L") + s);
conf->addLib("-lboost_system-mt -lboost_filesystem-mt -lboost_thread-mt");
return true;
}
};
@@ -1481,6 +1517,7 @@ export DATADIR
export EX_QTDIR
export QC_DISABLE_GUI
export QC_WITH_LIBBOOST_INC
export QC_WITH_LIBBOOST_LIB
export QC_DISABLE_libnotify
export QC_DISABLE_geoip_database
export QC_WITH_GEOIP_DATABASE_EMBEDDED

View File

@@ -2,6 +2,7 @@
-----BEGIN QCMOD-----
name: libboost
arg: with-libboost-inc=[path], Path to libboost include files
arg: with-libboost-lib=[path], Path to libboost library files
-----END QCMOD-----
*/
class qc_libboost : public ConfObj
@@ -51,6 +52,30 @@ public:
}
}
conf->addIncludePath(s);
// Find library
s = conf->getenv("QC_WITH_LIBBOOST_LIB");
if(!s.isEmpty()) {
if(!conf->checkLibrary(s, "boost_system-mt")) {
return false;
}
}else{
QStringList sl;
sl << "/usr/lib/";
sl << "/usr/lib64/";
sl << "/usr/local/lib/";
sl << "/usr/local/lib64/";
bool found = false;
foreach(s, sl){
if(conf->checkLibrary(s, "boost_system-mt")) {
found = true;
break;
}
}
if(!found)
return false;
}
conf->addLib(QString("-L") + s);
conf->addLib("-lboost_system-mt -lboost_filesystem-mt -lboost_thread-mt");
return true;
}
};

View File

@@ -20,12 +20,20 @@ public:
return false;
for(int n = 0; n < incs.count(); ++n)
conf->addIncludePath(incs[n]);
if(!libs.isEmpty())
conf->addLib(libs);
//if(!libs.isEmpty())
// conf->addLib(libs);
if(!conf->findPkgConfig("libtorrent-rasterbar", mode, adv_ver, &version, &incs, &libs, &other))
printf("\nWarning: libtorrent-rasterbar v%s was detected. Some feature will be disabled because they require v%s.\n", version.toLocal8Bit().data(), adv_ver.toUtf8().data());
else
conf->addDefine("LIBTORRENT_0_15");
// Get linking parameters
//QStringList params;
//QByteArray staticlibs;
//params << "--static" << "--libs" << "libtorrent-rasterbar";
//conf->doCommand("pkg-config", params, &staticlibs);
//conf->addLib(staticlibs.trimmed());
//libcrypto
conf->addLib("-lcrypto");
return true;
}
};

View File

@@ -15,10 +15,6 @@ public:
if(!conf->getenv("QC_DISABLE_GUI").isEmpty()) {
conf->addDefine("DISABLE_GUI");
}
if(QT_VERSION >= 0x040500) {
conf->addDefine("QT_4_5");
}
return(QT_VERSION >= 0x040400);
}
};

File diff suppressed because it is too large Load Diff

105
src/GUI.h
View File

@@ -55,43 +55,28 @@ class TransferListFiltersWidget;
class QSplitter;
class PropertiesWidget;
class StatusBar;
class consoleDlg;
class about;
class createtorrent;
class downloadFromURL;
class GUI : public QMainWindow, private Ui::MainWindow{
Q_OBJECT
private:
// Bittorrent
Bittorrent *BTSession;
QList<QPair<QTorrentHandle,QString> > unauthenticated_trackers; // Still needed?
// GUI related
QTimer *guiUpdater;
QTabWidget *tabs;
StatusBar *status_bar;
QPointer<options_imp> options;
QPointer<QSystemTrayIcon> systrayIcon;
QPointer<QTimer> systrayCreator;
QMenu *myTrayIconMenu;
TransferListWidget *transferList;
TransferListFiltersWidget *transferListFilters;
PropertiesWidget *properties;
bool displaySpeedInTitle;
bool force_exit;
// Keyboard shortcuts
QShortcut *switchSearchShortcut;
QShortcut *switchSearchShortcut2;
QShortcut *switchTransferShortcut;
QShortcut *switchRSSShortcut;
// Widgets
QAction *prioSeparator;
QAction *prioSeparator2;
QSplitter *hSplitter;
QSplitter *vSplitter;
// Search
SearchEngine *searchEngine;
// RSS
QPointer<RSSImp> rssWidget;
// Misc
QLocalServer *localServer;
public:
// Construct / Destruct
GUI(QWidget *parent=0, QStringList torrentCmdLine=QStringList());
~GUI();
// Methods
int getCurrentTabIndex() const;
TransferListWidget* getTransferList() const { return transferList; }
public slots:
void trackerAuthenticationRequired(QTorrentHandle& h);
void setTabText(int index, QString text) const;
void showNotificationBaloon(QString title, QString msg) const;
void downloadFromURLList(const QStringList& urls);
void updateAltSpeedsBtn(bool alternative);
protected slots:
// GUI related slots
@@ -128,35 +113,59 @@ protected slots:
void loadPreferences(bool configure_session=true);
void processParams(const QStringList& params);
void addTorrent(QString path);
void addUnauthenticatedTracker(QPair<QTorrentHandle,QString> tracker);
void addUnauthenticatedTracker(const QPair<QTorrentHandle,QString> &tracker);
void processDownloadedFiles(QString path, QString url);
void finishedTorrent(QTorrentHandle& h) const;
void askRecursiveTorrentDownloadConfirmation(QTorrentHandle &h);
// Options slots
void on_actionOptions_triggered();
void optionsSaved();
// HTTP slots
void on_actionDownload_from_URL_triggered();
public slots:
void trackerAuthenticationRequired(QTorrentHandle& h);
void setTabText(int index, QString text) const;
void showNotificationBaloon(QString title, QString msg) const;
void downloadFromURLList(const QStringList& urls);
protected:
void closeEvent(QCloseEvent *);
void showEvent(QShowEvent *);
bool event(QEvent * event);
void displayRSSTab(bool enable);
public:
// Construct / Destruct
GUI(QWidget *parent=0, QStringList torrentCmdLine=QStringList());
~GUI();
// Methods
int getCurrentTabIndex() const;
TransferListWidget* getTransferList() const { return transferList; }
private:
// Bittorrent
Bittorrent *BTSession;
QList<QPair<QTorrentHandle,QString> > unauthenticated_trackers; // Still needed?
// GUI related
QTimer *guiUpdater;
QTabWidget *tabs;
StatusBar *status_bar;
QPointer<options_imp> options;
QPointer<consoleDlg> console;
QPointer<about> aboutDlg;
QPointer<createtorrent> createTorrentDlg;
QPointer<downloadFromURL> downloadFromURLDialog;
QPointer<QSystemTrayIcon> systrayIcon;
QPointer<QTimer> systrayCreator;
QMenu *myTrayIconMenu;
TransferListWidget *transferList;
TransferListFiltersWidget *transferListFilters;
PropertiesWidget *properties;
bool displaySpeedInTitle;
bool force_exit;
// Keyboard shortcuts
QShortcut *switchSearchShortcut;
QShortcut *switchSearchShortcut2;
QShortcut *switchTransferShortcut;
QShortcut *switchRSSShortcut;
// Widgets
QAction *prioSeparator;
QAction *prioSeparator2;
QSplitter *hSplitter;
QSplitter *vSplitter;
// Search
SearchEngine *searchEngine;
// RSS
QPointer<RSSImp> rssWidget;
// Misc
QLocalServer *localServer;
};
#endif

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.0 KiB

BIN
src/Icons/oxygen/gear32.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@@ -1,6 +1,6 @@
[Desktop Entry]
Categories=Qt;Network;P2P;
Comment=V2.1.4
Comment=V2.2.3
Exec=qbittorrent %f
GenericName=Bittorrent client
GenericName[bg]=Торент клиент

Binary file not shown.

Before

Width:  |  Height:  |  Size: 78 KiB

After

Width:  |  Height:  |  Size: 79 KiB

BIN
src/Icons/slow.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 910 B

BIN
src/Icons/slow48.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

BIN
src/Icons/slow_off.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 680 B

View File

@@ -63,7 +63,7 @@ class about : public QDialog, private Ui::AboutDlg{
te_translation->append(tr("I would like to thank the following people who volunteered to translate qBittorrent:")+QString::fromUtf8("<br>"));
te_translation->append(QString::fromUtf8(
"<i>- <u>Brazilian:</u> Nick Marinho (nickmarinho@gmail.com)<br>\
- <u>Bulgarian:</u> Tsvetan & Boiko Bankov (emerge_life@users.sourceforge.net)<br>\
- <u>Bulgarian:</u> Tsvetan & Boyko Bankoff (emerge_life@users.sourceforge.net)<br>\
- <u>Catalan:</u> Francisco Luque Contreras (frannoe@ya.com)<br>\
- <u>Chinese (Simplified):</u> Guo Yue (yue.guo0418@gmail.com)<br>\
- <u>Chinese (Traditional):</u> Yi-Shun Wang (dnextstep@gmail.com)<br>\
@@ -87,11 +87,14 @@ class about : public QDialog, private Ui::AboutDlg{
- <u>Spanish:</u> Francisco Luque Contreras (frannoe@ya.com)<br>\
- <u>Swedish:</u> Daniel Nylander (po@danielnylander.se)<br>\
- <u>Turkish:</u> Hasan YILMAZ (iletisim@hedefturkce.com) and Erdem Bingöl (erdem84@gmail.com)<br>\
- <u>Ukrainian:</u> Andrey Shpachenko (masterfix@users.sourceforge.net)<br><br>"));
- <u>Ukrainian:</u> Andrey Shpachenko (masterfix@users.sourceforge.net) and Oleh Prypin (blaxpirit@gmail.com)<br><br>"));
te_translation->append(tr("Please contact me if you would like to translate qBittorrent into your own language."));
te_translation->scrollToAnchor(QString::fromUtf8("top"));
// License
te_license->append(QString::fromUtf8("<a name='top'></a>"));
#ifdef Q_WS_WIN
te_license->append(QString::fromUtf8("qBittorrent is licensed under the GNU General Public License version 2."));
#else
te_license->append(QString::fromUtf8("qBittorrent is licensed under the GNU General Public License version 2 with the\
addition of the following special exception:\
<br><br>\
@@ -438,6 +441,7 @@ exception statement from your version.</i>\
consider it more useful to permit linking proprietary applications with the<br>\
library. If this is what you want to do, use the GNU Library General<br>\
Public License instead of this License.<br>"));
#endif
te_license->scrollToAnchor(QString::fromUtf8("top"));
show();
}

146
src/advancedsettings.h Normal file
View File

@@ -0,0 +1,146 @@
#ifndef ADVANCEDSETTINGS_H
#define ADVANCEDSETTINGS_H
#include <QTableWidget>
#include <QHeaderView>
#include <QSpinBox>
#include <QCheckBox>
#include "preferences.h"
enum AdvSettingsCols {PROPERTY, VALUE};
enum AdvSettingsRows {DISK_CACHE, OUTGOING_PORT_MIN, OUTGOING_PORT_MAX, IGNORE_LIMIT_LAN, COUNT_OVERHEAD, RECHECK_COMPLETED, LIST_REFRESH, RESOLVE_COUNTRIES, RESOLVE_HOSTS };
#define ROW_COUNT 9
class AdvancedSettings: public QTableWidget {
Q_OBJECT
private:
QSpinBox *spin_cache, *outgoing_ports_min, *outgoing_ports_max, *spin_list_refresh;
QCheckBox *cb_ignore_limits_lan, *cb_count_overhead, *cb_recheck_completed, *cb_resolve_countries, *cb_resolve_hosts;
public:
AdvancedSettings(QWidget *parent=0): QTableWidget(parent) {
// Set visual appearance
setEditTriggers(QAbstractItemView::NoEditTriggers);
setAlternatingRowColors(true);
setColumnCount(2);
QStringList header;
header << tr("Property") << tr("Value");
setHorizontalHeaderLabels(header);
setColumnWidth(0, width()/2);
horizontalHeader()->setStretchLastSection(true);
verticalHeader()->setVisible(false);
setRowCount(ROW_COUNT);
// Load settings
loadAdvancedSettings();
}
~AdvancedSettings() {
delete spin_cache;
delete outgoing_ports_min;
delete outgoing_ports_max;
delete cb_ignore_limits_lan;
delete cb_count_overhead;
delete cb_recheck_completed;
delete spin_list_refresh;
delete cb_resolve_countries;
delete cb_resolve_hosts;
}
public slots:
void saveAdvancedSettings() {
// Disk write cache
Preferences::setDiskCacheSize(spin_cache->value());
// Outgoing ports
Preferences::setOutgoingPortsMin(outgoing_ports_min->value());
Preferences::setOutgoingPortsMax(outgoing_ports_max->value());
// Ignore limits on LAN
Preferences::ignoreLimitsOnLAN(cb_ignore_limits_lan->isChecked());
// Include protocol overhead in transfer limits
Preferences::includeOverheadInLimits(cb_count_overhead->isChecked());
// Recheck torrents on completion
Preferences::recheckTorrentsOnCompletion(cb_recheck_completed->isChecked());
// Transfer list refresh interval
Preferences::setRefreshInterval(spin_list_refresh->value());
// Peer resolution
Preferences::resolvePeerCountries(cb_resolve_countries->isChecked());
Preferences::resolvePeerHostNames(cb_resolve_hosts->isChecked());
}
protected slots:
void loadAdvancedSettings() {
// Disk write cache
setItem(DISK_CACHE, PROPERTY, new QTableWidgetItem(tr("Disk write cache size")));
spin_cache = new QSpinBox();
connect(spin_cache, SIGNAL(valueChanged(int)), this, SLOT(emitSettingsChanged()));
spin_cache->setMinimum(1);
spin_cache->setMaximum(200);
spin_cache->setValue(Preferences::diskCacheSize());
spin_cache->setSuffix(tr(" MiB"));
setCellWidget(DISK_CACHE, VALUE, spin_cache);
// Outgoing port Min
setItem(OUTGOING_PORT_MIN, PROPERTY, new QTableWidgetItem(tr("Outgoing ports (Min) [0: Disabled]")));
outgoing_ports_min = new QSpinBox();
connect(outgoing_ports_min, SIGNAL(valueChanged(int)), this, SLOT(emitSettingsChanged()));
outgoing_ports_min->setMinimum(0);
outgoing_ports_min->setMaximum(65535);
outgoing_ports_min->setValue(Preferences::outgoingPortsMin());
setCellWidget(OUTGOING_PORT_MIN, VALUE, outgoing_ports_min);
// Outgoing port Min
setItem(OUTGOING_PORT_MAX, PROPERTY, new QTableWidgetItem(tr("Outgoing ports (Max) [0: Disabled]")));
outgoing_ports_max = new QSpinBox();
connect(outgoing_ports_max, SIGNAL(valueChanged(int)), this, SLOT(emitSettingsChanged()));
outgoing_ports_max->setMinimum(0);
outgoing_ports_max->setMaximum(65535);
outgoing_ports_max->setValue(Preferences::outgoingPortsMax());
setCellWidget(OUTGOING_PORT_MAX, VALUE, outgoing_ports_max);
// Ignore transfer limits on local network
setItem(IGNORE_LIMIT_LAN, PROPERTY, new QTableWidgetItem(tr("Ignore transfer limits on local network")));
cb_ignore_limits_lan = new QCheckBox();
connect(cb_ignore_limits_lan, SIGNAL(toggled(bool)), this, SLOT(emitSettingsChanged()));
cb_ignore_limits_lan->setChecked(Preferences::ignoreLimitsOnLAN());
setCellWidget(IGNORE_LIMIT_LAN, VALUE, cb_ignore_limits_lan);
// Consider protocol overhead in transfer limits
setItem(COUNT_OVERHEAD, PROPERTY, new QTableWidgetItem(tr("Include TCP/IP overhead in transfer limits")));
cb_count_overhead = new QCheckBox();
connect(cb_count_overhead, SIGNAL(toggled(bool)), this, SLOT(emitSettingsChanged()));
cb_count_overhead->setChecked(Preferences::includeOverheadInLimits());
setCellWidget(COUNT_OVERHEAD, VALUE, cb_count_overhead);
// Recheck completed torrents
setItem(RECHECK_COMPLETED, PROPERTY, new QTableWidgetItem(tr("Recheck torrents on completion")));
cb_recheck_completed = new QCheckBox();
connect(cb_recheck_completed, SIGNAL(toggled(bool)), this, SLOT(emitSettingsChanged()));
cb_recheck_completed->setChecked(Preferences::recheckTorrentsOnCompletion());
setCellWidget(RECHECK_COMPLETED, VALUE, cb_recheck_completed);
// Transfer list refresh interval
setItem(LIST_REFRESH, PROPERTY, new QTableWidgetItem(tr("Transfer list refresh interval")));
spin_list_refresh = new QSpinBox();
connect(spin_list_refresh, SIGNAL(valueChanged(int)), this, SLOT(emitSettingsChanged()));
spin_list_refresh->setMinimum(30);
spin_list_refresh->setMaximum(99999);
spin_list_refresh->setValue(Preferences::getRefreshInterval());
spin_list_refresh->setSuffix(tr(" ms", " milliseconds"));
setCellWidget(LIST_REFRESH, VALUE, spin_list_refresh);
// Resolve Peer countries
setItem(RESOLVE_COUNTRIES, PROPERTY, new QTableWidgetItem(tr("Resolve peer countries (GeoIP)")));
cb_resolve_countries = new QCheckBox();
connect(cb_resolve_countries, SIGNAL(toggled(bool)), this, SLOT(emitSettingsChanged()));
cb_resolve_countries->setChecked(Preferences::resolvePeerCountries());
setCellWidget(RESOLVE_COUNTRIES, VALUE, cb_resolve_countries);
// Resolve peer hosts
setItem(RESOLVE_HOSTS, PROPERTY, new QTableWidgetItem(tr("Resolve peer host names")));
cb_resolve_hosts = new QCheckBox();
connect(cb_resolve_hosts, SIGNAL(toggled(bool)), this, SLOT(emitSettingsChanged()));
cb_resolve_hosts->setChecked(Preferences::resolvePeerHostNames());
setCellWidget(RESOLVE_HOSTS, VALUE, cb_resolve_hosts);
}
void emitSettingsChanged() {
emit settingsChanged();
}
signals:
void settingsChanged();
};
#endif // ADVANCEDSETTINGS_H

111
src/bandwidthscheduler.h Normal file
View File

@@ -0,0 +1,111 @@
#ifndef BANDWIDTHSCHEDULER_H
#define BANDWIDTHSCHEDULER_H
#include <QTimer>
#include <QTime>
#include <QDateTime>
#include "preferences.h"
#include <iostream>
class BandwidthScheduler: public QTimer {
Q_OBJECT
private:
bool in_alternative_mode;
public:
BandwidthScheduler(QObject *parent): QTimer(parent), in_alternative_mode(false) {
Q_ASSERT(Preferences::isSchedulerEnabled());
// Signal shot, we call start() again manually
setSingleShot(true);
// Connect Signals/Slots
connect(this, SIGNAL(timeout()), this, SLOT(switchMode()));
}
public slots:
void start() {
Q_ASSERT(Preferences::isSchedulerEnabled());
QTime startAltSpeeds = Preferences::getSchedulerStartTime();
QTime endAltSpeeds = Preferences::getSchedulerEndTime();
if(startAltSpeeds == endAltSpeeds) {
std::cerr << "Error: bandwidth scheduler have the same start time and end time." << std::endl;
std::cerr << "The bandwidth scheduler will be disabled" << std::endl;
stop();
emit switchToAlternativeMode(false);
return;
}
// Determine what the closest QTime is
QTime now = QTime::currentTime();
uint time_to_start = secsTo(now, startAltSpeeds);
uint time_to_end = secsTo(now, endAltSpeeds);
if(time_to_end < time_to_start) {
// We should be in alternative mode
in_alternative_mode = true;
// Start counting
QTimer::start(time_to_end*1000);
} else {
// We should be in normal mode
in_alternative_mode = false;
// Start counting
QTimer::start(time_to_start*1000);
}
// Send signal to notify BTSession
emit switchToAlternativeMode(in_alternative_mode);
}
void switchMode() {
// Get the day this mode was started (either today or yesterday)
QDate current_date = QDateTime::currentDateTime().toLocalTime().date();
int day = current_date.dayOfWeek();
if(in_alternative_mode) {
// It is possible that starttime was yesterday
if(QTime::currentTime().secsTo(Preferences::getSchedulerStartTime()) > 0) {
current_date.addDays(-1); // Go to yesterday
day = current_date.day();
}
}
// Check if the day is in scheduler days
// Notify BTSession only if necessary
switch(Preferences::getSchedulerDays()) {
case EVERY_DAY:
emit switchToAlternativeMode(!in_alternative_mode);
break;
case WEEK_ENDS:
if(day == Qt::Saturday || day == Qt::Sunday)
emit switchToAlternativeMode(!in_alternative_mode);
break;
case WEEK_DAYS:
if(day != Qt::Saturday && day != Qt::Sunday)
emit switchToAlternativeMode(!in_alternative_mode);
break;
default:
// Convert our enum index to Qt enum index
int scheduler_day = ((int)Preferences::getSchedulerDays()) - 2;
if(day == scheduler_day)
emit switchToAlternativeMode(!in_alternative_mode);
break;
}
// Call start again
start();
}
signals:
void switchToAlternativeMode(bool alternative);
private:
// Qt function can return negative values and we
// don't want that
uint secsTo(QTime now, QTime t) {
int diff = now.secsTo(t);
if(diff < 0) {
// 86400 seconds in a day
diff += 86400;
}
Q_ASSERT(diff >= 0);
return diff;
}
};
#endif // BANDWIDTHSCHEDULER_H

File diff suppressed because it is too large Load Diff

View File

@@ -41,6 +41,7 @@
#include <QPalette>
#endif
#include <QPointer>
#include <QTimer>
#include <libtorrent/session.hpp>
#include <libtorrent/ip_filter.hpp>
@@ -52,9 +53,10 @@ using namespace libtorrent;
class downloadThread;
class QTimer;
class FileSystemWatcher;
class FilterParserThread;
class HttpServer;
class BandwidthScheduler;
class ScanFoldersModel;
class TrackerInfos {
public:
@@ -88,60 +90,6 @@ public:
class Bittorrent : public QObject {
Q_OBJECT
private:
// Bittorrent
session *s;
QPointer<QTimer> timerAlerts;
QMap<QUrl, QString> savepath_fromurl;
QHash<QString, QHash<QString, TrackerInfos> > trackersInfos;
QStringList torrentsToPausedAfterChecking;
// Ratio
QPointer<QTimer> BigRatioTimer;
// HTTP
QPointer<downloadThread> downloader;
// File System
QPointer<FileSystemWatcher> FSWatcher;
// Console / Log
QStringList consoleMessages;
QStringList peerBanMessages;
// Settings
bool preAllocateAll;
bool addInPause;
float ratio_limit;
bool UPnPEnabled;
bool NATPMPEnabled;
bool LSDEnabled;
bool DHTEnabled;
int current_dht_port;
bool PeXEnabled;
bool queueingEnabled;
bool appendLabelToSavePath;
#ifdef LIBTORRENT_0_15
bool appendqBExtension;
#endif
QString defaultSavePath;
QString defaultTempPath;
// GeoIP
#ifndef DISABLE_GUI
bool resolve_countries;
bool geoipDBLoaded;
#endif
// ETA Computation
QPointer<QTimer> timerETA;
QHash<QString, QList<int> > ETA_samples;
// IP filtering
QPointer<FilterParserThread> filterParser;
QString filterPath;
// Web UI
QPointer<HttpServer> httpServer;
QList<QUrl> url_skippingDlg;
// Fast exit (async)
bool exiting;
protected:
QString getSavePath(QString hash);
bool initWebUi(QString username, QString password, int port);
public:
// Constructor / Destructor
Bittorrent();
@@ -168,13 +116,11 @@ public:
qlonglong getETA(QString hash);
bool useTemporaryFolder() const;
QString getDefaultSavePath() const;
ScanFoldersModel* getScanFoldersModel() const;
public slots:
QTorrentHandle addTorrent(QString path, bool fromScanDir = false, QString from_url = QString(), bool resumed = false);
QTorrentHandle addMagnetUri(QString magnet_uri, bool resumed=false);
void importOldTorrents();
void applyFormerAttributeFiles(QTorrentHandle h);
void importOldTempData(QString torrent_path);
void loadSessionState();
void saveSessionState();
void downloadFromUrl(QString url);
@@ -182,6 +128,7 @@ public slots:
void startUpTorrents();
session_proxy asyncDeletion();
void recheckTorrent(QString hash);
void useAlternativeSpeedsLimit(bool alternative);
/* Needed by Web UI */
void pauseAllTorrents();
void pauseTorrent(QString hash);
@@ -191,8 +138,6 @@ public slots:
void saveDHTEntry();
void preAllocateAllFiles(bool b);
void saveFastResumeData();
void enableDirectoryScanning(QString scan_dir);
void disableDirectoryScanning();
void enableIPFilter(QString filter);
void disableIPFilter();
void setQueueingEnabled(bool enable);
@@ -208,9 +153,9 @@ public slots:
void setGlobalRatio(float ratio);
void setDeleteRatio(float ratio);
void setDHTPort(int dht_port);
void setPeerProxySettings(proxy_settings proxySettings);
void setHTTPProxySettings(proxy_settings proxySettings);
void setSessionSettings(session_settings sessionSettings);
void setPeerProxySettings(const proxy_settings &proxySettings);
void setHTTPProxySettings(const proxy_settings &proxySettings);
void setSessionSettings(const session_settings &sessionSettings);
void startTorrentsInPause(bool b);
void setDefaultTempPath(QString temppath);
void setAppendLabelToSavePath(bool append);
@@ -238,12 +183,19 @@ public slots:
void downloadFromURLList(const QStringList& urls);
void configureSession();
void banIP(QString ip);
void recursiveTorrentDownload(const QTorrentHandle &h);
protected:
QString getSavePath(QString hash, bool fromScanDir = false, QString filePath = QString());
bool initWebUi(QString username, QString password, int port);
protected slots:
void addTorrentsFromScanFolder(QStringList&);
void readAlerts();
void deleteBigRatios();
void takeETASamples();
void exportTorrentFiles(QString path);
void saveTempFastResumeData();
signals:
void addedTorrent(QTorrentHandle& h);
@@ -261,6 +213,62 @@ signals:
void metadataReceived(QTorrentHandle &h);
void savePathChanged(QTorrentHandle &h);
void newConsoleMessage(QString msg);
void alternativeSpeedsModeChanged(bool alternative);
void recursiveTorrentDownloadPossible(QTorrentHandle &h);
private:
// Bittorrent
session *s;
QPointer<QTimer> timerAlerts;
QPointer<BandwidthScheduler> bd_scheduler;
QMap<QUrl, QString> savepath_fromurl;
QHash<QString, QHash<QString, TrackerInfos> > trackersInfos;
QStringList torrentsToPausedAfterChecking;
QTimer resumeDataTimer;
// Ratio
QPointer<QTimer> BigRatioTimer;
// HTTP
QPointer<downloadThread> downloader;
// File System
ScanFoldersModel *m_scanFolders;
// Console / Log
QStringList consoleMessages;
QStringList peerBanMessages;
// Settings
bool preAllocateAll;
bool addInPause;
float ratio_limit;
bool UPnPEnabled;
bool NATPMPEnabled;
bool LSDEnabled;
bool DHTEnabled;
int current_dht_port;
bool PeXEnabled;
bool queueingEnabled;
bool appendLabelToSavePath;
bool torrentExport;
#ifdef LIBTORRENT_0_15
bool appendqBExtension;
#endif
QString defaultSavePath;
QString defaultTempPath;
// ETA Computation
QPointer<QTimer> timerETA;
QHash<QString, QList<int> > ETA_samples;
// IP filtering
QPointer<FilterParserThread> filterParser;
QString filterPath;
// Web UI
QPointer<HttpServer> httpServer;
QList<QUrl> url_skippingDlg;
// Fast exit (async)
bool exiting;
// GeoIP
#ifndef DISABLE_GUI
bool geoipDBLoaded;
bool resolve_countries;
#endif
};
#endif

View File

@@ -46,6 +46,7 @@ class consoleDlg : public QDialog, private Ui_ConsoleDlg{
consoleDlg(QWidget *parent, Bittorrent* _BTSession) : QDialog(parent) {
setupUi(this);
setAttribute(Qt::WA_DeleteOnClose);
setModal(true);
BTSession = _BTSession;
textConsole->setHtml(BTSession->getConsoleMessages().join("<br>"));
textBannedPeers->setHtml(BTSession->getPeerBanMessages().join("<br>"));

View File

@@ -65,6 +65,7 @@ bool file_filter(boost::filesystem::path const& filename)
createtorrent::createtorrent(QWidget *parent): QDialog(parent){
setupUi(this);
setAttribute(Qt::WA_DeleteOnClose);
setModal(true);
creatorThread = new torrentCreatorThread(this);
connect(creatorThread, SIGNAL(creationSuccess(QString, const char*)), this, SLOT(handleCreationSuccess(QString, const char*)));
connect(creatorThread, SIGNAL(creationFailure(QString)), this, SLOT(handleCreationFailure(QString)));
@@ -84,7 +85,7 @@ void createtorrent::on_addFolder_button_clicked(){
}
void createtorrent::on_addFile_button_clicked(){
QString file = QFileDialog::getOpenFileName(this, tr("Select a file to add to the torrent"), QDir::homePath(), QString(), 0, QFileDialog::ShowDirsOnly);
QString file = QFileDialog::getOpenFileName(this, tr("Select a file to add to the torrent"), QDir::homePath());
if(!file.isEmpty())
textInputPath->setText(file);
}

View File

@@ -53,34 +53,49 @@ public:
setFixedHeight(BAR_HEIGHT);
}
void setProgress(bitfield pieces) {
void setProgress(const bitfield &pieces, const bitfield &downloading_pieces) {
if(pieces.empty()) {
// Empty bar
QPixmap pix = QPixmap(1, 1);
pix.fill();
pixmap = pix;
} else {
int nb_pieces = pieces.size();
const int nb_pieces = pieces.size();
// Reduce the number of pieces before creating the pixmap
// otherwise it can crash when there are too many pieces
if(nb_pieces > width()) {
int ratio = floor(nb_pieces/(double)width());
QVector<bool> scaled_pieces;
const int ratio = floor(nb_pieces/(double)width());
std::vector<bool> scaled_pieces;
std::vector<bool> scaled_downloading;
for(int i=0; i<nb_pieces; i+= ratio) {
bool have = true;
for(int j=i; j<qMin(i+ratio, nb_pieces); ++j) {
if(!pieces[i]) { have = false; break; }
}
scaled_pieces << have;
scaled_pieces.push_back(have);
if(have) {
scaled_downloading.push_back(false);
} else {
bool downloading = false;
for(int j=i; j<qMin(i+ratio, nb_pieces); ++j) {
if(downloading_pieces[i]) { downloading = true; break; }
}
scaled_downloading.push_back(downloading);
}
}
QPixmap pix = QPixmap(scaled_pieces.size(), 1);
pix.fill();
QPainter painter(&pix);
for(int i=0; i<scaled_pieces.size(); ++i) {
if(scaled_pieces[i])
for(uint i=0; i<scaled_pieces.size(); ++i) {
if(scaled_pieces[i]) {
painter.setPen(Qt::blue);
else
painter.setPen(Qt::white);
} else {
if(scaled_downloading[i]) {
painter.setPen(Qt::yellow);
} else {
painter.setPen(Qt::white);
}
}
painter.drawPoint(i,0);
}
pixmap = pix;
@@ -89,10 +104,15 @@ public:
pix.fill();
QPainter painter(&pix);
for(uint i=0; i<pieces.size(); ++i) {
if(pieces[i])
if(pieces[i]) {
painter.setPen(Qt::blue);
else
painter.setPen(Qt::white);
} else {
if(downloading_pieces[i]) {
painter.setPen(Qt::yellow);
} else {
painter.setPen(Qt::white);
}
}
painter.drawPoint(i,0);
}
pixmap = pix;

View File

@@ -47,6 +47,7 @@ class downloadFromURL : public QDialog, private Ui::downloadFromURL{
setupUi(this);
setAttribute(Qt::WA_DeleteOnClose);
icon_lbl->setPixmap(QPixmap(QString::fromUtf8(":/Icons/skin/url.png")));
setModal(true);
show();
// Paste clipboard if there is an URL in it
QString clip_txt = qApp->clipboard()->text();

View File

@@ -59,7 +59,7 @@ void downloadThread::processDlFinished(QNetworkReply* reply) {
QVariant redirection = reply->attribute(QNetworkRequest::RedirectionTargetAttribute);
if(redirection.isValid()) {
// We should redirect
qDebug("Redirecting from %s to %s", url.toLocal8Bit().data(), redirection.toUrl().toString().toLocal8Bit().data());
qDebug("Redirecting from %s to %s", qPrintable(url), qPrintable(redirection.toUrl().toString()));
redirect_mapping.insert(redirection.toUrl().toString(), url);
downloadUrl(redirection.toUrl().toString());
return;
@@ -74,8 +74,9 @@ void downloadThread::processDlFinished(QNetworkReply* reply) {
tmpfile.setAutoRemove(false);
if (tmpfile.open()) {
filePath = tmpfile.fileName();
qDebug("Temporary filename is: %s", filePath.toLocal8Bit().data());
qDebug("Temporary filename is: %s", qPrintable(filePath));
if(reply->open(QIODevice::ReadOnly)) {
// TODO: Support GZIP compression
tmpfile.write(reply->readAll());
reply->close();
tmpfile.close();
@@ -94,7 +95,12 @@ void downloadThread::processDlFinished(QNetworkReply* reply) {
reply->deleteLater();
}
void downloadThread::downloadUrl(QString url){
void downloadThread::downloadTorrentUrl(QString url){
QNetworkReply *reply = downloadUrl(url);
connect(reply, SIGNAL(downloadProgress(qint64,qint64)), this, SLOT(checkDownloadSize(qint64,qint64)));
}
QNetworkReply* downloadThread::downloadUrl(QString url){
// Update proxy settings
applyProxySettings();
// Process download request
@@ -103,8 +109,27 @@ void downloadThread::downloadUrl(QString url){
// Spoof Firefox 3.5 user agent to avoid
// Web server banning
request.setRawHeader("User-Agent", "Mozilla/5.0 (X11; U; Linux i686 (x86_64); en-US; rv:1.9.1.5) Gecko/20091102 Firefox/3.5.5");
qDebug("Downloading %s...", request.url().toString().toLocal8Bit().data());
networkManager->get(request);
qDebug("Downloading %s...", qPrintable(request.url().toString()));
return networkManager->get(request);
}
void downloadThread::checkDownloadSize(qint64 bytesReceived, qint64 bytesTotal) {
if(bytesTotal > 0) {
QNetworkReply *reply = static_cast<QNetworkReply*>(sender());
// Total number of bytes is available
if(bytesTotal > 1048576) {
// More than 1MB, this is probably not a torrent file, aborting...
reply->abort();
} else {
disconnect(reply, SIGNAL(downloadProgress(qint64,qint64)), this, SLOT(checkDownloadSize(qint64,qint64)));
}
} else {
if(bytesReceived > 1048576) {
// More than 1MB, this is probably not a torrent file, aborting...
QNetworkReply *reply = static_cast<QNetworkReply*>(sender());
reply->abort();
}
}
}
void downloadThread::applyProxySettings() {
@@ -116,7 +141,7 @@ void downloadThread::applyProxySettings() {
QString IP = settings.value(QString::fromUtf8("Preferences/Connection/HTTPProxy/IP"), "0.0.0.0").toString();
proxy.setHostName(IP);
QString port = settings.value(QString::fromUtf8("Preferences/Connection/HTTPProxy/Port"), 8080).toString();
qDebug("Using proxy: %s", (IP+QString(":")+port).toLocal8Bit().data());
qDebug("Using proxy: %s", qPrintable(IP));
proxy.setPort(port.toUShort());
// Default proxy type is HTTP, we must change if it is SOCKS5
if(intValue == SOCKS5 || intValue == SOCKS5_PW) {

View File

@@ -51,7 +51,8 @@ signals:
public:
downloadThread(QObject* parent);
~downloadThread();
void downloadUrl(QString url);
QNetworkReply* downloadUrl(QString url);
void downloadTorrentUrl(QString url);
//void setProxy(QString IP, int port, QString username, QString password);
protected:
@@ -60,6 +61,7 @@ protected:
protected slots:
void processDlFinished(QNetworkReply* reply);
void checkDownloadSize(qint64 bytesReceived, qint64 bytesTotal);
};

View File

@@ -81,7 +81,7 @@ void engineSelectDlg::dropEvent(QDropEvent *event) {
QStringList files=event->mimeData()->text().split(QString::fromUtf8("\n"));
QString file;
foreach(file, files) {
qDebug("dropped %s", file.toLocal8Bit().data());
qDebug("dropped %s", qPrintable(file));
file = file.replace("file://", "");
if(file.startsWith("http://", Qt::CaseInsensitive) || file.startsWith("https://", Qt::CaseInsensitive) || file.startsWith("ftp://", Qt::CaseInsensitive)) {
downloader->downloadUrl(file);
@@ -99,7 +99,7 @@ void engineSelectDlg::dropEvent(QDropEvent *event) {
void engineSelectDlg::dragEnterEvent(QDragEnterEvent *event) {
QString mime;
foreach(mime, event->mimeData()->formats()){
qDebug("mimeData: %s", mime.toLocal8Bit().data());
qDebug("mimeData: %s", qPrintable(mime));
}
if (event->mimeData()->hasFormat(QString::fromUtf8("text/plain")) || event->mimeData()->hasFormat(QString::fromUtf8("text/uri-list"))) {
event->acceptProposedAction();
@@ -251,12 +251,12 @@ bool engineSelectDlg::isUpdateNeeded(QString plugin_name, float new_version) con
}
void engineSelectDlg::installPlugin(QString path, QString plugin_name) {
qDebug("Asked to install plugin at %s", path.toLocal8Bit().data());
qDebug("Asked to install plugin at %s", qPrintable(path));
float new_version = SearchEngine::getPluginVersion(path);
qDebug("Version to be installed: %.2f", new_version);
if(!isUpdateNeeded(plugin_name, new_version)) {
qDebug("Apparently update is not needed, we have a more recent version");
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("A more recent version of %1 search engine plugin is already installed.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("A more recent version of %1 search engine plugin is already installed.", "%1 is the name of the search engine").arg(plugin_name));
return;
}
// Process with install
@@ -280,12 +280,12 @@ void engineSelectDlg::installPlugin(QString path, QString plugin_name) {
// restore backup
QFile::copy(dest_path+".bak", dest_path);
QFile::remove(dest_path+".bak");
QMessageBox::warning(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin could not be updated, keeping old version.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::warning(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin could not be updated, keeping old version.", "%1 is the name of the search engine").arg(plugin_name));
return;
} else {
// Remove broken file
QFile::remove(dest_path);
QMessageBox::warning(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin could not be installed.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::warning(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin could not be installed.", "%1 is the name of the search engine").arg(plugin_name));
return;
}
}
@@ -294,10 +294,10 @@ void engineSelectDlg::installPlugin(QString path, QString plugin_name) {
QFile::remove(dest_path+".bak");
}
if(update) {
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin was successfully updated.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin was successfully updated.", "%1 is the name of the search engine").arg(plugin_name));
return;
} else {
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin was successfully installed.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::information(this, tr("Search plugin install")+" -- "+tr("qBittorrent"), tr("%1 search engine plugin was successfully installed.", "%1 is the name of the search engine").arg(plugin_name));
return;
}
}
@@ -390,17 +390,17 @@ bool engineSelectDlg::parseVersionsFile(QString versions_file) {
plugin_name.chop(1); // remove trailing ':'
bool ok;
float version = list.last().toFloat(&ok);
qDebug("read line %s: %.2f", plugin_name.toLocal8Bit().data(), version);
qDebug("read line %s: %.2f", qPrintable(plugin_name), version);
if(!ok) continue;
file_correct = true;
if(isUpdateNeeded(plugin_name, version)) {
qDebug("Plugin: %s is outdated", plugin_name.toLocal8Bit().data());
qDebug("Plugin: %s is outdated", qPrintable(plugin_name));
// Downloading update
downloader->downloadUrl(UPDATE_URL+plugin_name+".py");
//downloader->downloadUrl(UPDATE_URL+plugin_name+".png");
updated = true;
}else {
qDebug("Plugin: %s is up to date", plugin_name.toLocal8Bit().data());
qDebug("Plugin: %s is up to date", qPrintable(plugin_name));
}
}
// Close file
@@ -414,7 +414,7 @@ bool engineSelectDlg::parseVersionsFile(QString versions_file) {
}
void engineSelectDlg::processDownloadedFile(QString url, QString filePath) {
qDebug("engineSelectDlg received %s", url.toLocal8Bit().data());
qDebug("engineSelectDlg received %s", qPrintable(url));
if(url.endsWith("favicon.ico", Qt::CaseInsensitive)){
// Icon downloaded
QImage fileIcon;
@@ -456,7 +456,7 @@ void engineSelectDlg::processDownloadedFile(QString url, QString filePath) {
void engineSelectDlg::handleDownloadFailure(QString url, QString reason) {
if(url.endsWith("favicon.ico", Qt::CaseInsensitive)){
qDebug("Could not download favicon: %s, reason: %s", url.toLocal8Bit().data(), reason.toLocal8Bit().data());
qDebug("Could not download favicon: %s, reason: %s", qPrintable(url), qPrintable(reason));
return;
}
if(url.endsWith("versions.txt")) {
@@ -467,6 +467,6 @@ void engineSelectDlg::handleDownloadFailure(QString url, QString reason) {
// a plugin update download has been failed
QString plugin_name = url.split('/').last();
plugin_name.replace(".py", "", Qt::CaseInsensitive);
QMessageBox::warning(this, tr("Search plugin update")+" -- "+tr("qBittorrent"), tr("Sorry, %1 search plugin install failed.", "%1 is the name of the search engine").arg(plugin_name.toLocal8Bit().data()));
QMessageBox::warning(this, tr("Search plugin update")+" -- "+tr("qBittorrent"), tr("Sorry, %1 search plugin install failed.", "%1 is the name of the search engine").arg(plugin_name));
}
}

View File

@@ -31,6 +31,7 @@
#include "eventmanager.h"
#include "bittorrent.h"
#include "scannedfoldersmodel.h"
#include "misc.h"
#include "preferences.h"
//#include "proplistdelegate.h"
@@ -129,8 +130,31 @@ void EventManager::setGlobalPreferences(QVariantMap m) const {
Preferences::setTempPathEnabled(m["temp_path_enabled"].toBool());
if(m.contains("temp_path"))
Preferences::setTempPath(m["temp_path"].toString());
if(m.contains("scan_dir"))
Preferences::setScanDir(m["scan_dir"].toString());
if(m.contains("scan_dirs") && m.contains("download_in_scan_dirs")) {
QVariantList download_at_path = m["download_in_scan_dirs"].toList();
QStringList old_folders = Preferences::getScanDirs();
QStringList new_folders = m["scan_dirs"].toStringList();
if(download_at_path.size() == new_folders.size()) {
Preferences::setScanDirs(new_folders);
Preferences::setDownloadInScanDirs(download_at_path);
foreach(const QString &old_folder, old_folders) {
// Update deleted folders
if(!new_folders.contains(old_folder)) {
BTSession->getScanFoldersModel()->removePath(old_folder);
}
}
int i = 0;
foreach(const QString &new_folder, new_folders) {
// Update new folders
if(!old_folders.contains(new_folder)) {
BTSession->getScanFoldersModel()->addPath(new_folder, download_at_path.at(i).toBool());
}
++i;
}
}
}
if(m.contains("export_dir"))
Preferences::setExportDir(m["export_dir"].toString());
if(m.contains("preallocate_all"))
Preferences::preAllocateAllFiles(m["preallocate_all"].toBool());
if(m.contains("queueing_enabled"))
@@ -165,6 +189,10 @@ void EventManager::setGlobalPreferences(QVariantMap m) const {
// Bittorrent
if(m.contains("dht"))
Preferences::setDHTEnabled(m["dht"].toBool());
if(m.contains("dhtSameAsBT"))
Preferences::setDHTPortSameAsBT(m["dhtSameAsBT"].toBool());
if(m.contains("dht_port"))
Preferences::setDHTPort(m["dht_port"].toInt());
if(m.contains("pex"))
Preferences::setPeXEnabled(m["pex"].toBool());
qDebug("Pex support: %d", (int)m["pex"].toBool());
@@ -227,8 +255,10 @@ QVariantMap EventManager::getGlobalPreferences() const {
data["save_path"] = Preferences::getSavePath();
data["temp_path_enabled"] = Preferences::isTempPathEnabled();
data["temp_path"] = Preferences::getTempPath();
data["scan_dir_enabled"] = Preferences::isDirScanEnabled();
data["scan_dir"] = Preferences::getScanDir();
data["scan_dirs"] = Preferences::getScanDirs();
data["download_in_scan_dirs"] = Preferences::getDownloadInScanDirs();
data["export_dir_enabled"] = Preferences::isTorrentExportEnabled();
data["export_dir"] = Preferences::getExportDir();
data["preallocate_all"] = Preferences::preAllocateAllFiles();
data["queueing_enabled"] = Preferences::isQueueingSystemEnabled();
data["max_active_downloads"] = Preferences::getMaxActiveDownloads();
@@ -248,6 +278,8 @@ QVariantMap EventManager::getGlobalPreferences() const {
data["max_uploads_per_torrent"] = Preferences::getMaxUploadsPerTorrent();
// Bittorrent
data["dht"] = Preferences::isDHTEnabled();
data["dhtSameAsBT"] = Preferences::isDHTPortSameAsBT();
data["dht_port"] = Preferences::getDHTPort();
data["pex"] = Preferences::isPeXEnabled();
data["lsd"] = Preferences::isLSDEnabled();
data["encryption"] = Preferences::getEncryptionSetting();
@@ -282,28 +314,30 @@ QVariantMap EventManager::getPropGeneralInfo(QString hash) const {
QTorrentHandle h = BTSession->getTorrentHandle(hash);
if(h.is_valid() && h.has_metadata()) {
// Save path
data["save_path"] = TorrentPersistentData::getSavePath(hash);
QString p = TorrentPersistentData::getSavePath(hash);
if(p.isEmpty()) p = h.save_path();
data["save_path"] = p;
// Creation date
data["creation_date"] = h.creation_date();
// Comment
data["comment"] = h.comment();
data["total_wasted"] = misc::friendlyUnit(h.total_failed_bytes()+h.total_redundant_bytes());
data["total_uploaded"] = misc::friendlyUnit(h.all_time_upload()) + " ("+misc::friendlyUnit(h.total_payload_upload())+" "+tr("this session")+")";
data["total_downloaded"] = misc::friendlyUnit(h.all_time_download()) + " ("+misc::friendlyUnit(h.total_payload_download())+" "+tr("this session")+")";
data["total_wasted"] = QVariant(misc::friendlyUnit(h.total_failed_bytes()+h.total_redundant_bytes()));
data["total_uploaded"] = QVariant(misc::friendlyUnit(h.all_time_upload()) + " ("+misc::friendlyUnit(h.total_payload_upload())+" "+tr("this session")+")");
data["total_downloaded"] = QVariant(misc::friendlyUnit(h.all_time_download()) + " ("+misc::friendlyUnit(h.total_payload_download())+" "+tr("this session")+")");
if(h.upload_limit() <= 0)
data["up_limit"] = QString::fromUtf8("∞");
else
data["up_limit"] = misc::friendlyUnit(h.upload_limit())+tr("/s", "/second (i.e. per second)");
data["up_limit"] = QVariant(misc::friendlyUnit(h.upload_limit())+tr("/s", "/second (i.e. per second)"));
if(h.download_limit() <= 0)
data["dl_limit"] = QString::fromUtf8("∞");
else
data["dl_limit"] = misc::friendlyUnit(h.download_limit())+tr("/s", "/second (i.e. per second)");
data["dl_limit"] = QVariant(misc::friendlyUnit(h.download_limit())+tr("/s", "/second (i.e. per second)"));
QString elapsed_txt = misc::userFriendlyDuration(h.active_time());
if(h.is_seed()) {
elapsed_txt += " ("+tr("Seeded for %1", "e.g. Seeded for 3m10s").arg(misc::userFriendlyDuration(h.seeding_time()))+")";
}
data["time_elapsed"] = elapsed_txt;
data["nb_connections"] = QString::number(h.num_connections())+" ("+tr("%1 max", "e.g. 10 max").arg(QString::number(h.connections_limit()))+")";
data["nb_connections"] = QVariant(QString::number(h.num_connections())+" ("+tr("%1 max", "e.g. 10 max").arg(QString::number(h.connections_limit()))+")");
// Update ratio info
double ratio = BTSession->getRealRatio(h.hash());
if(ratio > 100.)

View File

@@ -28,15 +28,16 @@ public:
setColumnCount(1);
QTreeWidgetItem *___qtreewidgetitem = headerItem();
___qtreewidgetitem->setText(0, QApplication::translate("RSS", "RSS feeds", 0, QApplication::UnicodeUTF8));
connect(this, SIGNAL(currentItemChanged(QTreeWidgetItem*,QTreeWidgetItem*)), this, SLOT(updateCurrentFeed(QTreeWidgetItem*)));
unread_item = new QTreeWidgetItem(this);
unread_item->setText(0, tr("Unread") + QString::fromUtf8(" (") + QString::number(rssmanager->getNbUnRead(), 10)+ QString(")"));
unread_item->setData(0,Qt::DecorationRole, QVariant(QIcon(":/Icons/oxygen/mail-folder-inbox.png")));
itemAdded(unread_item, rssmanager);
connect(this, SIGNAL(currentItemChanged(QTreeWidgetItem*,QTreeWidgetItem*)), this, SLOT(updateCurrentFeed(QTreeWidgetItem*)));
setCurrentItem(unread_item);
}
~FeedList() {
disconnect(this, SIGNAL(currentItemChanged(QTreeWidgetItem*,QTreeWidgetItem*)), this, SLOT(updateCurrentFeed(QTreeWidgetItem*)));
delete unread_item;
}
@@ -121,19 +122,19 @@ public:
}
RssFile* getRSSItem(QTreeWidgetItem *item) const {
return mapping[item];
return mapping.value(item, 0);
}
RssFile::FileType getItemType(QTreeWidgetItem *item) const {
return mapping[item]->getType();
return mapping.value(item)->getType();
}
QString getItemID(QTreeWidgetItem *item) const {
return mapping[item]->getID();
return mapping.value(item)->getID();
}
QTreeWidgetItem* getTreeItemFromUrl(QString url) const{
return feeds_items[url];
return feeds_items.value(url, 0);
}
RssStream* getRSSItemFromUrl(QString url) const {

View File

@@ -46,7 +46,7 @@
#include "bittorrent.h"
#include "ui_feeddownloader.h"
#ifdef QT_4_5
#if QT_VERSION >= 0x040500
#include <QHash>
#else
#include <QMap>
@@ -64,11 +64,9 @@ public:
bool matches(QString s) {
QStringList match_tokens = getMatchingTokens();
//qDebug("Checking matching tokens: \"%s\"", getMatchingTokens_str().toLocal8Bit().data());
foreach(const QString& token, match_tokens) {
if(token.isEmpty() || token == "")
continue;
//qDebug("Token: %s", token.toLocal8Bit().data());
QRegExp reg(token, Qt::CaseInsensitive, QRegExp::Wildcard);
//reg.setMinimal(false);
if(reg.indexIn(s) < 0) return false;
@@ -226,7 +224,7 @@ public:
void save() {
QSettings qBTRSS("qBittorrent", "qBittorrent-rss");
QHash<QString, QVariant> all_feeds_filters = qBTRSS.value("feed_filters", QHash<QString, QVariant>()).toHash();
qDebug("Saving filters for feed: %s (%d filters)", feed_url.toLocal8Bit().data(), (*this).size());
qDebug("Saving filters for feed: %s (%d filters)", qPrintable(feed_url), (*this).size());
all_feeds_filters[feed_url] = *this;
qBTRSS.setValue("feed_filters", all_feeds_filters);
}
@@ -261,7 +259,6 @@ public:
// Restore saved info
enableDl_cb->setChecked(filters.isDownloadingEnabled());
fillFiltersList();
filtersList->sortItems(Qt::AscendingOrder);
if(filters.size() > 0) {
// Select first filter
filtersList->setCurrentItem(filtersList->item(0));
@@ -388,7 +385,6 @@ protected slots:
if(selected_filter == current_name)
selected_filter = new_name;
item->setText(new_name);
filtersList->sortItems(Qt::AscendingOrder);
}
}
@@ -442,7 +438,6 @@ protected slots:
}
}while(!validated);
QListWidgetItem *it = new QListWidgetItem(filter_name, filtersList);
filtersList->sortItems(Qt::AscendingOrder);
filtersList->setCurrentItem(it);
//showFilterSettings(it);
}

View File

@@ -34,12 +34,14 @@
class FileSystemWatcher: public QFileSystemWatcher {
Q_OBJECT
#ifndef Q_WS_WIN
private:
QDir watched_folder;
#ifndef Q_WS_WIN
QList<QDir> watched_folders;
QPointer<QTimer> watch_timer;
#endif
QStringList filters;
#ifndef Q_WS_WIN
protected:
bool isNetworkFileSystem(QString path) {
QString file = path;
@@ -47,10 +49,10 @@ protected:
file += QDir::separator();
file += ".";
struct statfs buf;
if(!statfs(file.toLocal8Bit().data(), &buf)) {
if(!statfs(file.toLocal8Bit().constData(), &buf)) {
return (buf.f_type == (long)CIFS_MAGIC_NUMBER || buf.f_type == (long)NFS_SUPER_MAGIC);
} else {
std::cerr << "Error: statfs() call failed for " << file.toLocal8Bit().data() << ". Supposing it is a local folder..." << std::endl;
std::cerr << "Error: statfs() call failed for " << qPrintable(file) << ". Supposing it is a local folder..." << std::endl;
switch(errno) {
case EACCES:
std::cerr << "Search permission is denied for a component of the path prefix of the path" << std::endl;
@@ -98,13 +100,7 @@ protected:
public:
FileSystemWatcher(QObject *parent): QFileSystemWatcher(parent) {
filters << "*.torrent";
connect(this, SIGNAL(directoryChanged(QString)), this, SLOT(scanFolder()));
}
FileSystemWatcher(QString path, QObject *parent): QFileSystemWatcher(parent) {
filters << "*.torrent";
connect(this, SIGNAL(directoryChanged(QString)), this, SLOT(scanFolder()));
addPath(path);
connect(this, SIGNAL(directoryChanged(QString)), this, SLOT(scanLocalFolder(QString)));
}
~FileSystemWatcher() {
@@ -115,33 +111,40 @@ public:
}
QStringList directories() const {
QStringList dirs;
#ifndef Q_WS_WIN
if(watch_timer)
return QStringList(watched_folder.path());
if(watch_timer) {
foreach (const QDir &dir, watched_folders)
dirs << dir.canonicalPath();
}
#endif
return QFileSystemWatcher::directories();
dirs << QFileSystemWatcher::directories();
return dirs;
}
void addPath(const QString & path) {
#ifndef Q_WS_WIN
watched_folder = QDir(path);
if(!watched_folder.exists()) return;
QDir dir(path);
if (!dir.exists())
return;
// Check if the path points to a network file system or not
if(isNetworkFileSystem(path)) {
// Network mode
Q_ASSERT(!watch_timer);
qDebug("Network folder detected: %s", path.toLocal8Bit().data());
qDebug("Network folder detected: %s", qPrintable(path));
qDebug("Using file polling mode instead of inotify...");
watched_folders << dir;
// Set up the watch timer
watch_timer = new QTimer(this);
connect(watch_timer, SIGNAL(timeout()), this, SLOT(scanFolder()));
watch_timer->start(5000); // 5 sec
if (!watch_timer) {
watch_timer = new QTimer(this);
connect(watch_timer, SIGNAL(timeout()), this, SLOT(scanNetworkFolders()));
watch_timer->start(5000); // 5 sec
}
} else {
#endif
// Normal mode
qDebug("FS Watching is watching %s in normal mode", path.toLocal8Bit().data());
qDebug("FS Watching is watching %s in normal mode", qPrintable(path));
QFileSystemWatcher::addPath(path);
scanFolder();
scanLocalFolder(path);
#ifndef Q_WS_WIN
}
#endif
@@ -149,38 +152,58 @@ public:
void removePath(const QString & path) {
#ifndef Q_WS_WIN
if(watch_timer) {
// Network mode
if(QDir(path) == watched_folder) {
delete watch_timer;
QDir dir(path);
for (int i = 0; i < watched_folders.count(); ++i) {
if (QDir(watched_folders.at(i)) == dir) {
watched_folders.removeAt(i);
if (watched_folders.isEmpty())
delete watch_timer;
return;
}
} else {
#endif
// Normal mode
QFileSystemWatcher::removePath(path);
#ifndef Q_WS_WIN
}
#endif
// Normal mode
QFileSystemWatcher::removePath(path);
}
protected slots:
// XXX: Does not detect file size changes to improve performance.
void scanFolder() {
qDebug("Scan folder was called");
void scanLocalFolder(QString path) {
qDebug("scanLocalFolder(%s) called", qPrintable(path));
QStringList torrents;
if(watch_timer) {
torrents = watched_folder.entryList(filters, QDir::Files, QDir::Unsorted);
} else {
torrents = QDir(QFileSystemWatcher::directories().first()).entryList(filters, QDir::Files, QDir::Unsorted);
qDebug("FSWatcher: Polling manually folder %s", QFileSystemWatcher::directories().first().toLocal8Bit().data());
}
if(!torrents.empty())
// Local folders scan
addTorrentsFromDir(QDir(path), torrents);
// Report detected torrent files
if(!torrents.empty()) {
qDebug("The following files are being reported: %s", qPrintable(torrents.join("\n")));
emit torrentsAdded(torrents);
}
}
void scanNetworkFolders() {
qDebug("scanNetworkFolders() called");
QStringList torrents;
// Network folders scan
foreach (const QDir &dir, watched_folders) {
//qDebug("FSWatcher: Polling manually folder %s", qPrintable(dir.path()));
addTorrentsFromDir(dir, torrents);
}
// Report detected torrent files
if(!torrents.empty()) {
qDebug("The following files are being reported: %s", qPrintable(torrents.join("\n")));
emit torrentsAdded(torrents);
}
}
signals:
void torrentsAdded(QStringList &pathList);
private:
void addTorrentsFromDir(const QDir &dir, QStringList &torrents) {
const QStringList &files = dir.entryList(filters, QDir::Files, QDir::Unsorted);
foreach(const QString &file, files)
torrents << dir.canonicalPath() + '/' + file;
}
};
#endif // FILESYSTEMWATCHER_H

View File

@@ -86,9 +86,9 @@ public:
exportEmbeddedDb();
#endif
if(QFile::exists(geoipDBpath(false))) {
qDebug("Loading GeoIP database from %s...", geoipDBpath(false).toLocal8Bit().data());
if(!s->load_country_db(geoipDBpath(false).toLocal8Bit().data())) {
std::cerr << "Failed to load Geoip Database at " << geoipDBpath(false).toLocal8Bit().data() << std::endl;
qDebug("Loading GeoIP database from %s...", qPrintable(geoipDBpath(false)));
if(!s->load_country_db(geoipDBpath(false).toLocal8Bit().constData())) {
std::cerr << "Failed to load Geoip Database at " << qPrintable(geoipDBpath(false)) << std::endl;
}
} else {
qDebug("ERROR: Impossible to find local Geoip Database");

Some files were not shown because too many files have changed in this diff Show More