diff --git a/Transmission.xcodeproj/project.pbxproj b/Transmission.xcodeproj/project.pbxproj index fccd3a58b..b8700fe6c 100644 --- a/Transmission.xcodeproj/project.pbxproj +++ b/Transmission.xcodeproj/project.pbxproj @@ -83,6 +83,7 @@ A21DFF100A292B2B007C5F76 /* Transfers.png in Resources */ = {isa = PBXBuildFile; fileRef = A21DFF0F0A292B2B007C5F76 /* Transfers.png */; }; A22180980D148A71007D09ED /* GroupsWindowController.m in Sources */ = {isa = PBXBuildFile; fileRef = A22180970D148A71007D09ED /* GroupsWindowController.m */; }; A22180B60D148F0F007D09ED /* GroupsWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = A22180B50D148F0F007D09ED /* GroupsWindow.xib */; }; + A222E9870E6B21D9009FB003 /* BlocklistDownloaderViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = A222E9860E6B21D9009FB003 /* BlocklistDownloaderViewController.m */; }; A224D2640DAAC55F000954EA /* Peers.png in Resources */ = {isa = PBXBuildFile; fileRef = A224D2630DAAC55F000954EA /* Peers.png */; }; A2265F420B5EF5F40093DDA5 /* FileNameCell.m in Sources */ = {isa = PBXBuildFile; fileRef = A2265F400B5EF5F40093DDA5 /* FileNameCell.m */; }; A226FDAC0D0CDF20005A7F71 /* libnatpmp.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 3C7A118D0D0B2EB800B5701F /* libnatpmp.a */; }; @@ -493,6 +494,8 @@ A22180960D148A71007D09ED /* GroupsWindowController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = GroupsWindowController.h; path = macosx/GroupsWindowController.h; sourceTree = ""; }; A22180970D148A71007D09ED /* GroupsWindowController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = GroupsWindowController.m; path = macosx/GroupsWindowController.m; sourceTree = ""; }; A22180B50D148F0F007D09ED /* GroupsWindow.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = GroupsWindow.xib; path = macosx/GroupsWindow.xib; sourceTree = ""; }; + A222E9850E6B21D9009FB003 /* BlocklistDownloaderViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = BlocklistDownloaderViewController.h; path = macosx/BlocklistDownloaderViewController.h; sourceTree = ""; }; + A222E9860E6B21D9009FB003 /* BlocklistDownloaderViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = BlocklistDownloaderViewController.m; path = macosx/BlocklistDownloaderViewController.m; sourceTree = ""; }; A223AA7D0D220CEB00840069 /* nl */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = nl; path = macosx/nl.lproj/Creator.xib; sourceTree = ""; }; A223AA7E0D220CEB00840069 /* nl */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = nl; path = macosx/nl.lproj/InfoPlist.strings; sourceTree = ""; }; A223AA7F0D220CEB00840069 /* nl */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = nl; path = macosx/nl.lproj/InfoWindow.xib; sourceTree = ""; }; @@ -962,6 +965,8 @@ A2FB701B0D95CAEA0001F331 /* GroupsController.m */, A2D307A20D9EC6870051FD27 /* BlocklistDownloader.h */, A2D307A30D9EC6870051FD27 /* BlocklistDownloader.m */, + A222E9850E6B21D9009FB003 /* BlocklistDownloaderViewController.h */, + A222E9860E6B21D9009FB003 /* BlocklistDownloaderViewController.m */, A2DF567C0DE323D3000795D5 /* QuickLook.h */, A2DF57720DE46A6A000795D5 /* QuickLookController.h */, A2DF57730DE46A6A000795D5 /* QuickLookController.m */, @@ -2002,6 +2007,7 @@ A2725D5D0DE7507C003445E7 /* TrackerTableView.m in Sources */, A28F4F770E085BDC003A3882 /* ColorTextField.m in Sources */, A27F0F330E19AD9800B2DB97 /* TorrentGroup.m in Sources */, + A222E9870E6B21D9009FB003 /* BlocklistDownloaderViewController.m in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/macosx/BlocklistDownloader.h b/macosx/BlocklistDownloader.h index 32a25fe35..712a5b678 100644 --- a/macosx/BlocklistDownloader.h +++ b/macosx/BlocklistDownloader.h @@ -25,25 +25,24 @@ #import #import -@class PrefsController; +@class BlocklistDownloaderViewController; @interface BlocklistDownloader : NSObject -{ - PrefsController * fPrefsController; - - IBOutlet NSWindow * fStatusWindow; - IBOutlet NSProgressIndicator * fProgressBar; - IBOutlet NSTextField * fTextField; - IBOutlet NSButton * fButton; - +{ NSURLDownload * fDownload; + #warning have to store??? + tr_handle * fHandle; + + BlocklistDownloaderViewController * fViewController; + NSUInteger fCurrentSize; long long fExpectedSize; } -+ (void) downloadWithPrefsController: (PrefsController *) prefsController; //only use when no other blocklist is downloading ++ (BlocklistDownloader *) downloader: (tr_handle *) handle; +- (void) setViewController: (BlocklistDownloaderViewController *) viewController; -- (void) cancelDownload: (id) sender; +- (void) cancelDownload; @end diff --git a/macosx/BlocklistDownloader.m b/macosx/BlocklistDownloader.m index 994e72577..08e1b5012 100644 --- a/macosx/BlocklistDownloader.m +++ b/macosx/BlocklistDownloader.m @@ -23,8 +23,7 @@ *****************************************************************************/ #import "BlocklistDownloader.h" -#import "PrefsController.h" -#import "NSStringAdditions.h" +#import "BlocklistDownloaderViewController.h" #import "NSApplicationAdditions.h" #define LIST_URL @"http://download.m0k.org/transmission/files/level1.gz" @@ -32,36 +31,34 @@ @interface BlocklistDownloader (Private) -- (id) initWithPrefsController: (PrefsController *) prefsController; +- (id) initWithHandle: (tr_handle *) handle; - (void) startDownload; - (void) finishDownloadSuccess; -- (void) updateProcessString; -- (void) failureSheetClosed: (NSAlert *) alert returnCode: (int) code contextInfo: (void *) info; @end @implementation BlocklistDownloader -+ (void) downloadWithPrefsController: (PrefsController *) prefsController +BlocklistDownloader * fDownloader = nil; ++ (BlocklistDownloader *) downloader: (tr_handle *) handle { - BlocklistDownloader * downloader = [[BlocklistDownloader alloc] initWithPrefsController: prefsController]; - [downloader startDownload]; + if (!fDownloader) + { + fDownloader = [[BlocklistDownloader alloc] initWithHandle: handle]; + [fDownloader startDownload]; + } + + return fDownloader; } -- (void) awakeFromNib +- (void) setViewController: (BlocklistDownloaderViewController *) viewController { - [fButton setTitle: NSLocalizedString(@"Cancel", "Blocklist -> cancel button")]; - - float oldWidth = [fButton frame].size.width; - [fButton sizeToFit]; - NSRect buttonFrame = [fButton frame]; - buttonFrame.origin.x -= buttonFrame.size.width - oldWidth; - [fButton setFrame: buttonFrame]; - - [fTextField setStringValue: [NSLocalizedString(@"Connecting to site", "Blocklist -> message") stringByAppendingEllipsis]]; - - [fProgressBar setUsesThreadedAnimation: YES]; - [fProgressBar startAnimation: self]; + fViewController = viewController; + if (fViewController) + { + #warning set actual status + [fViewController setStatusStarting]; + } } - (void) dealloc @@ -70,12 +67,13 @@ [super dealloc]; } -- (void) cancelDownload: (id) sender +- (void) cancelDownload { + [fViewController setFinished]; + [fDownload cancel]; - [NSApp endSheet: fStatusWindow]; - [fStatusWindow orderOut: self]; + fDownloader = nil; [self release]; } @@ -84,34 +82,22 @@ fCurrentSize = 0; fExpectedSize = [response expectedContentLength]; - //change from indeterminate to progress - [fProgressBar setIndeterminate: fExpectedSize == NSURLResponseUnknownLength]; - [self updateProcessString]; + [fViewController setStatusProgressForCurrentSize: fCurrentSize expectedSize: fExpectedSize]; } - (void) download: (NSURLDownload *) download didReceiveDataOfLength: (NSUInteger) length { fCurrentSize += length; - [self updateProcessString]; + [fViewController setStatusProgressForCurrentSize: fCurrentSize expectedSize: fExpectedSize]; } +#warning release? - (void) download: (NSURLDownload *) download didFailWithError: (NSError *) error { - [fProgressBar setHidden: YES]; + [fViewController setFailed: [error localizedDescription]]; - [NSApp endSheet: fStatusWindow]; - [fStatusWindow orderOut: self]; - - NSAlert * alert = [[[NSAlert alloc] init] autorelease]; - [alert addButtonWithTitle: NSLocalizedString(@"OK", "Blocklist -> button")]; - [alert setMessageText: NSLocalizedString(@"Download of the blocklist failed.", "Blocklist -> message")]; - [alert setAlertStyle: NSWarningAlertStyle]; - - [alert setInformativeText: [NSString stringWithFormat: @"%@ - %@", NSLocalizedString(@"Error", "Blocklist -> message"), - [error localizedDescription]]]; - - [alert beginSheetModalForWindow: [fPrefsController window] modalDelegate: self - didEndSelector: @selector(failureSheetClosed:returnCode:contextInfo:) contextInfo: nil]; + fDownloader = nil; + [self release]; } - (void) downloadDidFinish: (NSURLDownload *) download @@ -126,11 +112,11 @@ @implementation BlocklistDownloader (Private) -- (id) initWithPrefsController: (PrefsController *) prefsController +- (id) initWithHandle: (tr_handle *) handle { if ((self = [super init])) { - fPrefsController = prefsController; + fHandle = handle; } return self; @@ -138,11 +124,6 @@ - (void) startDownload { - //load window and show as sheet - [NSBundle loadNibNamed: @"BlocklistStatusWindow" owner: self]; - [NSApp beginSheet: fStatusWindow modalForWindow: [fPrefsController window] modalDelegate: nil didEndSelector: nil contextInfo: nil]; - - //start the download NSURLRequest * request = [NSURLRequest requestWithURL: [NSURL URLWithString: LIST_URL]]; fDownload = [[NSURLDownload alloc] initWithRequest: request delegate: self]; @@ -153,16 +134,10 @@ { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; - //change to indeterminate while processing - [fProgressBar setIndeterminate: YES]; - [fProgressBar startAnimation: self]; - - [fTextField setStringValue: [NSLocalizedString(@"Processing blocklist", "Blocklist -> message") stringByAppendingEllipsis]]; - [fButton setEnabled: NO]; - [fStatusWindow display]; //force window to be updated + [fViewController setStatusProcessing]; //process data - tr_blocklistSetContent([fPrefsController handle], [DESTINATION UTF8String]); + tr_blocklistSetContent(fHandle, [DESTINATION UTF8String]); //delete downloaded file if ([NSApp isOnLeopardOrBetter]) @@ -170,32 +145,14 @@ else [[NSFileManager defaultManager] removeFileAtPath: DESTINATION handler: nil]; - [fPrefsController updateBlocklistFields]; + [fViewController setFinished]; - [NSApp endSheet: fStatusWindow]; - [fStatusWindow orderOut: self]; + #warning update date + [[NSNotificationCenter defaultCenter] postNotificationName: @"BlocklistUpdated" object: nil]; [pool release]; - [self release]; -} - -- (void) updateProcessString -{ - NSString * string = NSLocalizedString(@"Downloading blocklist", "Blocklist -> message"); - if (fExpectedSize != NSURLResponseUnknownLength) - { - NSString * substring = [NSString stringWithFormat: NSLocalizedString(@"%@ of %@", "Blocklist -> message"), - [NSString stringForFileSize: fCurrentSize], [NSString stringForFileSize: fExpectedSize]]; - string = [string stringByAppendingFormat: @" (%@)", substring]; - [fProgressBar setDoubleValue: (double)fCurrentSize / fExpectedSize]; - } - [fTextField setStringValue: string]; -} - -- (void) failureSheetClosed: (NSAlert *) alert returnCode: (int) code contextInfo: (void *) info -{ - [[alert window] orderOut: nil]; + fDownloader = nil; [self release]; } diff --git a/macosx/BlocklistDownloaderViewController.h b/macosx/BlocklistDownloaderViewController.h new file mode 100644 index 000000000..b2657d13f --- /dev/null +++ b/macosx/BlocklistDownloaderViewController.h @@ -0,0 +1,53 @@ +/****************************************************************************** + * $Id$ + * + * Copyright (c) 2008 Transmission authors and contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + *****************************************************************************/ + +#import +#import + +@class PrefsController; +@class BlocklistDownloader; + +@interface BlocklistDownloaderViewController : NSObject +{ + PrefsController * fPrefsController; + BlocklistDownloader * fDownloader; + + IBOutlet NSWindow * fStatusWindow; + IBOutlet NSProgressIndicator * fProgressBar; + IBOutlet NSTextField * fTextField; + IBOutlet NSButton * fButton; +} + ++ (void) downloadWithPrefsController: (PrefsController *) prefsController; + +- (void) cancelDownload: (id) sender; + +- (void) setStatusStarting; +- (void) setStatusProgressForCurrentSize: (NSUInteger) currentSize expectedSize: (long long) expectedSize; +- (void) setStatusProcessing; + +- (void) setFinished; +- (void) setFailed: (NSString *) error; + +@end diff --git a/macosx/BlocklistDownloaderViewController.m b/macosx/BlocklistDownloaderViewController.m new file mode 100644 index 000000000..3831e6831 --- /dev/null +++ b/macosx/BlocklistDownloaderViewController.m @@ -0,0 +1,159 @@ +/****************************************************************************** + * $Id$ + * + * Copyright (c) 2008 Transmission authors and contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + *****************************************************************************/ + +#import "BlocklistDownloaderViewController.h" +#import "BlocklistDownloader.h" +#import "PrefsController.h" +#import "NSStringAdditions.h" +#import "NSApplicationAdditions.h" + +@interface BlocklistDownloaderViewController (Private) + +- (id) initWithPrefsController: (PrefsController *) prefsController; +- (void) startDownload; +- (void) failureSheetClosed: (NSAlert *) alert returnCode: (int) code contextInfo: (void *) info; + +@end + +@implementation BlocklistDownloaderViewController + ++ (void) downloadWithPrefsController: (PrefsController *) prefsController +{ + BlocklistDownloaderViewController * downloader = [[BlocklistDownloaderViewController alloc] initWithPrefsController: prefsController]; + [downloader startDownload]; +} + +- (void) awakeFromNib +{ + [fButton setTitle: NSLocalizedString(@"Cancel", "Blocklist -> cancel button")]; + + float oldWidth = [fButton frame].size.width; + [fButton sizeToFit]; + NSRect buttonFrame = [fButton frame]; + buttonFrame.origin.x -= buttonFrame.size.width - oldWidth; + [fButton setFrame: buttonFrame]; + + [fProgressBar setUsesThreadedAnimation: YES]; + [fProgressBar startAnimation: self]; +} + +- (void) cancelDownload: (id) sender +{ + [fDownloader cancelDownload]; +} + +- (void) setStatusStarting +{ + [fTextField setStringValue: [NSLocalizedString(@"Connecting to site", "Blocklist -> message") stringByAppendingEllipsis]]; + [fProgressBar setIndeterminate: YES]; +} + +- (void) setStatusProgressForCurrentSize: (NSUInteger) currentSize expectedSize: (long long) expectedSize +{ + NSString * string = NSLocalizedString(@"Downloading blocklist", "Blocklist -> message"); + if (expectedSize != NSURLResponseUnknownLength) + { + [fProgressBar setIndeterminate: NO]; + + NSString * substring = [NSString stringWithFormat: NSLocalizedString(@"%@ of %@", "Blocklist -> message"), + [NSString stringForFileSize: currentSize], [NSString stringForFileSize: expectedSize]]; + string = [string stringByAppendingFormat: @" (%@)", substring]; + [fProgressBar setDoubleValue: (double)currentSize / expectedSize]; + } + else + string = [string stringByAppendingFormat: @" (%@)", [NSString stringForFileSize: expectedSize]]; + + [fTextField setStringValue: string]; +} + +- (void) setStatusProcessing +{ + //change to indeterminate while processing + [fProgressBar setIndeterminate: YES]; + [fProgressBar startAnimation: self]; + + [fTextField setStringValue: [NSLocalizedString(@"Processing blocklist", "Blocklist -> message") stringByAppendingEllipsis]]; + [fButton setEnabled: NO]; + [fStatusWindow display]; //force window to be updated +} + +- (void) setFinished +{ + [NSApp endSheet: fStatusWindow]; + [fStatusWindow orderOut: self]; + + [self release]; +} + +- (void) setFailed: (NSString *) error +{ + #warning remove? + //[fProgressBar setHidden: YES]; + + [NSApp endSheet: fStatusWindow]; + [fStatusWindow orderOut: self]; + + NSAlert * alert = [[[NSAlert alloc] init] autorelease]; + [alert addButtonWithTitle: NSLocalizedString(@"OK", "Blocklist -> button")]; + [alert setMessageText: NSLocalizedString(@"Download of the blocklist failed.", "Blocklist -> message")]; + [alert setAlertStyle: NSWarningAlertStyle]; + + [alert setInformativeText: [NSString stringWithFormat: @"%@ - %@", NSLocalizedString(@"Error", "Blocklist -> message"), + error]]; + + [alert beginSheetModalForWindow: [fPrefsController window] modalDelegate: self + didEndSelector: @selector(failureSheetClosed:returnCode:contextInfo:) contextInfo: nil]; +} + +@end + +@implementation BlocklistDownloaderViewController (Private) + +- (id) initWithPrefsController: (PrefsController *) prefsController +{ + if ((self = [super init])) + { + fPrefsController = prefsController; + } + + return self; +} + +- (void) startDownload +{ + //load window and show as sheet + [NSBundle loadNibNamed: @"BlocklistStatusWindow" owner: self]; + [NSApp beginSheet: fStatusWindow modalForWindow: [fPrefsController window] modalDelegate: nil didEndSelector: nil contextInfo: nil]; + + fDownloader = [BlocklistDownloader downloader: [fPrefsController handle]]; + [fDownloader setViewController: self]; +} + +- (void) failureSheetClosed: (NSAlert *) alert returnCode: (int) code contextInfo: (void *) info +{ + [[alert window] orderOut: nil]; + [self release]; +} + +@end diff --git a/macosx/Controller.m b/macosx/Controller.m index 80ccac5b2..52f4d08ab 100644 --- a/macosx/Controller.m +++ b/macosx/Controller.m @@ -559,6 +559,8 @@ static void sleepCallback(void * controller, io_service_t y, natural_t messageTy - (void) applicationWillTerminate: (NSNotification *) notification { + #warning stop blocklist download + //stop timers and notification checking [[NSNotificationCenter defaultCenter] removeObserver: self]; diff --git a/macosx/PrefsController.m b/macosx/PrefsController.m index 59b9ea913..8f5f98b9e 100644 --- a/macosx/PrefsController.m +++ b/macosx/PrefsController.m @@ -23,7 +23,7 @@ *****************************************************************************/ #import "PrefsController.h" -#import "BlocklistDownloader.h" +#import "BlocklistDownloaderViewController.h" #import "NSApplicationAdditions.h" #import "NSStringAdditions.h" #import "UKKQueue.h" @@ -127,6 +127,7 @@ return self; } +#warning still needed? make class method? - (tr_handle *) handle { return fHandle; @@ -134,6 +135,8 @@ - (void) dealloc { + [[NSNotificationCenter defaultCenter] removeObserver: self]; + [fPortStatusTimer invalidate]; if (fPortChecker) { @@ -222,6 +225,8 @@ //set blocklist [self updateBlocklistFields]; + [[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(updateBlocklistFields) + name: @"BlocklistUpdated" object: nil]; //set rpc port [fRPCPortField setIntValue: [fDefaults integerForKey: @"RPCPort"]]; @@ -446,7 +451,7 @@ - (void) updateBlocklist: (id) sender { - [BlocklistDownloader downloadWithPrefsController: self]; + [BlocklistDownloaderViewController downloadWithPrefsController: self]; } - (void) updateBlocklistFields