]> git.saurik.com Git - cydia.git/blobdiff - Cydia.mm
We don't want a compile-time flag for RotationEnabled: we want it to work that way...
[cydia.git] / Cydia.mm
index ba5cb322e2b0adb4cb99250725b6055b3515857a..c8e2c1bc239f71050aa0acbf55cf11c2951ccfd9 100644 (file)
--- a/Cydia.mm
+++ b/Cydia.mm
 #define USE_SYSTEM_MALLOC 1
 
 /* #include Directives {{{ */
-#import "UICaboodle/UCPlatform.h"
-#import "UICaboodle/UCLocalize.h"
+#include "UICaboodle/UCPlatform.h"
+#include "UICaboodle/UCLocalize.h"
 
 #include <objc/objc.h>
 #include <objc/runtime.h>
 
 #include <CoreGraphics/CoreGraphics.h>
-#include <GraphicsServices/GraphicsServices.h>
 #include <Foundation/Foundation.h>
 
 #if 0
 #include <CoreFoundation/CFPriv.h>
 #include <CoreFoundation/CFUniChar.h>
 
-#import <UIKit/UIKit.h>
+#include <UIKit/UIKit.h>
+#include "iPhonePrivate.h"
+
+#include <IOKit/IOKitLib.h>
 
 #include <WebCore/WebCoreThread.h>
-#import <WebKit/WebDefaultUIKitDelegate.h>
 
 #include <algorithm>
 #include <iomanip>
 #include <sys/param.h>
 #include <sys/mount.h>
 
+#include <fcntl.h>
 #include <notify.h>
 #include <dlfcn.h>
 
@@ -116,55 +118,13 @@ extern "C" {
 
 #include <ext/hash_map>
 
-#include <notify.h>
-
-#import "UICaboodle/BrowserView.h"
-#import "UICaboodle/ResetView.h"
+#include "UICaboodle/BrowserView.h"
+#include "UICaboodle/ResetView.h"
 
-#import "substrate.h"
+#include "substrate.h"
 
 // Apple's sample Reachability code, ASPL licensed.
-#import "Reachability.h"
-/* }}} */
-
-/* Header Fixes and Updates {{{ */
-typedef enum {
-   UIModalPresentationFullScreen = 0,
-   UIModalPresentationPageSheet,
-   UIModalPresentationFormSheet,
-   UIModalPresentationCurrentContext,
-} UIModalPresentationStyle;
-
-@interface UIAlertView (Private)
-- (void)setNumberOfRows:(int)rows;
-- (void)setContext:(id)context;
-- (id)context;
-@end
-
-@interface UIViewController (UIKit)
-- (id)navigationItem;
-- (id)navigationController;
-- (id)tabBarItem;
-@end
-
-@interface UITabBarController : UIViewController {
-    id _tabBar;
-    id _containerView;
-    id _viewControllerTransitionView;
-    id _viewControllers;
-    id _tabBarItemsToViewControllers;
-    id _selectedViewController;
-    id _moreNavigationController;
-    id _customizableViewControllers;
-    id _delegate;
-    id _selectedViewControllerDuringWillAppear;
-    id _transientViewController;
-    unsigned int isShowingMoreItem:1;
-    unsigned int needsToRebuildItems:1;
-    unsigned int isBarHidden:1;
-    unsigned int editButtonOnLeft:1;
-}
-@end
+#include "Reachability.h"
 /* }}} */
 
 /* Profiler {{{ */
@@ -415,7 +375,7 @@ static const CFStringCompareFlags LaxCompareFlags_ = kCFCompareCaseInsensitive |
 
 #define lprintf(args...) fprintf(stderr, args)
 
-#define ForRelease 0
+#define ForRelease 1
 #define TraceLogging (1 && !ForRelease)
 #define HistogramInsertionSort (0 && !ForRelease)
 #define ProfileTimes (0 && !ForRelease)
@@ -686,10 +646,6 @@ NSUInteger DOMNodeList$countByEnumeratingWithState$objects$count$(DOMNodeList *s
     return length;
 }
 
-@interface NSString (UIKit)
-- (NSString *) stringByAddingPercentEscapes;
-@end
-
 /* Cydia NSString Additions {{{ */
 @interface NSString (Cydia)
 + (NSString *) stringWithUTF8BytesNoCopy:(const char *)bytes length:(int)length;
@@ -755,7 +711,7 @@ NSUInteger DOMNodeList$countByEnumeratingWithState$objects$count$(DOMNodeList *s
 
 - (NSString *) stringByAddingPercentEscapesIncludingReserved {
     return [(id)CFURLCreateStringByAddingPercentEscapes(
-        kCFAllocatorDefault, 
+        kCFAllocatorDefault,
         (CFStringRef) self,
         NULL,
         CFSTR(";/?:@&=+$,"),
@@ -1250,14 +1206,18 @@ bool isSectionVisible(NSString *section) {
 - (void) installPackage:(Package *)package;
 - (void) installPackages:(NSArray *)packages;
 - (void) removePackage:(Package *)package;
+- (void) beginUpdate;
+- (BOOL) updating;
 - (void) distUpgrade;
+- (void) loadData;
 - (void) updateData;
 - (void) syncData;
 - (void) showSettings;
 - (UIProgressHUD *) addProgressHUD;
 - (void) removeProgressHUD:(UIProgressHUD *)hud;
-- (UIViewController *) pageForPackage:(NSString *)name;
+- (UCViewController *) pageForPackage:(NSString *)name;
 - (PackageController *) packageController;
+- (void) showActionSheet:(UIActionSheet *)sheet fromItem:(UIBarButtonItem *)item;
 @end
 /* }}} */
 
@@ -1448,7 +1408,7 @@ typedef std::map< unsigned long, _H<Source> > SourceMap;
 @end
 /* }}} */
 /* Delegate Helpers {{{ */
-@implementation NSObject(ProgressDelegate)
+@implementation NSObject (ProgressDelegate)
 
 - (void) _setProgressErrorPackage:(NSArray *)args {
     [self performSelector:@selector(setProgressError:forPackage:)
@@ -1474,7 +1434,7 @@ typedef std::map< unsigned long, _H<Source> > SourceMap;
 - (void) setProgressError:(NSString *)error forPackage:(NSString *)id {
     Package *package = id == nil ? nil : [[Database sharedInstance] packageWithName:id];
     // XXX: holy typecast batman!
-    [self setProgressError:error withTitle:(package == nil ? id : [package name])];
+    [(id<ProgressDelegate>)self setProgressError:error withTitle:(package == nil ? id : [package name])];
 }
 
 @end
@@ -2522,11 +2482,13 @@ struct PackageNameOrdering :
     UIImage *icon(nil);
     if (!icon_.empty())
         if ([icon_ hasPrefix:@"file:///"])
+            // XXX: correct escaping
             icon = [UIImage imageAtPath:[icon_ substringFromIndex:7]];
     if (icon == nil) if (section != nil)
         icon = [UIImage imageAtPath:[NSString stringWithFormat:@"%@/Sections/%@.png", App_, section]];
     if (icon == nil) if (source_ != nil) if (NSString *dicon = [source_ defaultIcon])
         if ([dicon hasPrefix:@"file:///"])
+            // XXX: correct escaping
             icon = [UIImage imageAtPath:[dicon substringFromIndex:7]];
     if (icon == nil)
         icon = [UIImage applicationImageNamed:@"unknown.png"];
@@ -3909,7 +3871,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @implementation CYViewController
 @end
 /* }}} */
-
+/* Cydia Browser Controller {{{ */
 @interface CYBrowserController : BrowserController {
     CydiaObject *cydia_;
 }
@@ -3975,7 +3937,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 }
 
 - (id) init {
-    if ((self = [super initWithWidth:[[self view] bounds].size.width ofClass:[CYBrowserController class]]) != nil) {
+    if ((self = [super initWithWidth:0 ofClass:[CYBrowserController class]]) != nil) {
         cydia_ = [[CydiaObject alloc] initWithDelegate:indirect_];
 
         WebView *webview([document_ webView]);
@@ -3999,7 +3961,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 }
 
 @end
+/* }}} */
 
+/* Confirmation {{{ */
 @protocol ConfirmationControllerDelegate
 - (void) cancelAndClear:(bool)clear;
 - (void) confirmWithNavigationController:(UINavigationController *)navigation;
@@ -4055,7 +4019,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 - (id) invokeDefaultMethodWithArguments:(NSArray *)args {
     [self dismissModalViewControllerAnimated:YES];
     [delegate_ cancelAndClear:NO];
-    
+
     return nil;
 }
 
@@ -4177,7 +4141,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     if (issues_ == nil && ![self isLoading]) [[self navigationItem] setRightBarButtonItem:rightItem];
     else [super applyRightButton];
 #else
-       [[self navigationItem] setRightBarButtonItem:nil];
+    [[self navigationItem] setRightBarButtonItem:nil];
 #endif
     [rightItem release];
 }
@@ -4292,7 +4256,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         [database_ setDelegate:self];
         delegate_ = delegate;
 
-        [[self view] setBackgroundColor:(CGColor *)[UIColor colorWithRed:0.0f green:0.0f blue:0.0f alpha:1.0f]];
+        [[self view] setBackgroundColor:[UIColor colorWithRed:0.0f green:0.0f blue:0.0f alpha:1.0f]];
 
         progress_ = [[UIProgressBar alloc] init];
         [progress_ setAutoresizingMask:(UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleTopMargin)];
@@ -4338,7 +4302,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         (bounds.size.width - prgsize.width) / 2,
         bounds.size.height - prgsize.height - 64
     }, prgsize};
-    
+
     float closewidth = bounds.size.width - 20;
     if (closewidth > 300) closewidth = 300;
 
@@ -4366,8 +4330,8 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 - (void) viewWillAppear:(BOOL)animated {
     [super viewDidAppear:animated];
     [[self navigationItem] setHidesBackButton:YES];
-    [[[self navigationController] navigationBar] setBarStyle:1];
-    
+    [[[self navigationController] navigationBar] setBarStyle:UIBarStyleBlack];
+
     [self positionViews];
 }
 
@@ -4649,8 +4613,12 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 /* }}} */
 
 /* Cell Content View {{{ */
+@protocol ContentDelegate
+- (void) drawContentRect:(CGRect)rect;
+@end
+
 @interface ContentView : UIView {
-    _transient id delegate_;
+    _transient id<ContentDelegate> delegate_;
 }
 
 @end
@@ -4663,7 +4631,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     } return self;
 }
 
-- (void) setDelegate:(id)delegate {
+- (void) setDelegate:(id<ContentDelegate>)delegate {
     delegate_ = delegate;
 }
 
@@ -4674,7 +4642,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 /* Package Cell {{{ */
-@interface PackageCell : UITableViewCell {
+@interface PackageCell : UITableViewCell <
+    ContentDelegate
+> {
     UIImage *icon_;
     NSString *name_;
     NSString *description_;
@@ -4865,12 +4835,12 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
     if (!selected)
         UISetColor(commercial_ ? Purple_ : Black_);
-    [name_ drawAtPoint:CGPointMake(48, 8) forWidth:(width - (placard_ == nil ? 80 : 106)) withFont:Font18Bold_ ellipsis:2];
-    [source_ drawAtPoint:CGPointMake(58, 29) forWidth:(width - 95) withFont:Font12_ ellipsis:2];
+    [name_ drawAtPoint:CGPointMake(48, 8) forWidth:(width - (placard_ == nil ? 80 : 106)) withFont:Font18Bold_ lineBreakMode:UILineBreakModeTailTruncation];
+    [source_ drawAtPoint:CGPointMake(58, 29) forWidth:(width - 95) withFont:Font12_ lineBreakMode:UILineBreakModeTailTruncation];
 
     if (!selected)
         UISetColor(commercial_ ? Purplish_ : Gray_);
-    [description_ drawAtPoint:CGPointMake(12, 46) forWidth:(width - 46) withFont:Font14_ ellipsis:2];
+    [description_ drawAtPoint:CGPointMake(12, 46) forWidth:(width - 46) withFont:Font14_ lineBreakMode:UILineBreakModeTailTruncation];
 
     if (placard_ != nil)
         [placard_ drawAtPoint:CGPointMake(width - 52, 9)];
@@ -4889,7 +4859,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 /* Section Cell {{{ */
-@interface SectionCell : UITableViewCell {
+@interface SectionCell : UITableViewCell <
+    ContentDelegate
+> {
     NSString *basic_;
     NSString *section_;
     NSString *name_;
@@ -4900,7 +4872,6 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     BOOL editing_;
 }
 
-- (id) init;
 - (void) setSection:(Section *)section editing:(BOOL)editing;
 
 @end
@@ -4997,7 +4968,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
             [switch_ setOn:(isSectionVisible(basic_) ? 1 : 0) animated:NO];
     }
 
-    [self setAccessoryType:editing ? 0 : 1 /*UITableViewCellAccessoryDisclosureIndicator*/];
+    [self setAccessoryType:editing ? UITableViewCellAccessoryNone : UITableViewCellAccessoryDisclosureIndicator];
     [content_ setNeedsDisplay];
 }
 
@@ -5010,7 +4981,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (void) drawContentRect:(CGRect)rect {
     BOOL selected = [self isSelected];
-    
+
     [icon_ drawInRect:CGRectMake(8, 7, 32, 32)];
 
     if (selected)
@@ -5023,7 +4994,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     if (editing_)
         width -= 87;
 
-    [name_ drawAtPoint:CGPointMake(48, 9) forWidth:(width - 70) withFont:Font22Bold_ ellipsis:2];
+    [name_ drawAtPoint:CGPointMake(48, 9) forWidth:(width - 70) withFont:Font22Bold_ lineBreakMode:UILineBreakModeTailTruncation];
 
     CGSize size = [count_ sizeWithFont:Font14_];
 
@@ -5036,7 +5007,10 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 /* }}} */
 
 /* File Table {{{ */
-@interface FileTable : CYViewController {
+@interface FileTable : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     Package *package_;
     NSString *name_;
@@ -5078,7 +5052,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         [cell setFont:[UIFont systemFontOfSize:16]];
     }
     [cell setText:[files_ objectAtIndex:indexPath.row]];
-    [cell setSelectionStyle:0 /*UITableViewCellSelectionStyleNone*/];
+    [cell setSelectionStyle:UITableViewCellSelectionStyleNone];
 
     return cell;
 }
@@ -5153,7 +5127,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 /* Package Controller {{{ */
-@interface PackageController : CYBrowserController {
+@interface PackageController : CYBrowserController <
+    UIActionSheetDelegate
+> {
     _transient Database *database_;
     Package *package_;
     NSString *name_;
@@ -5206,10 +5182,8 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
             NSString *buttonName = [buttons_ objectAtIndex:button];
             [self _clickButtonWithName:buttonName];
         }
-        
+
         [sheet dismissWithClickedButtonIndex:-1 animated:YES];
-    } else {
-        [super alertSheet:sheet clickedButtonAtIndex:button];
     }
 }
 
@@ -5227,7 +5201,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 }
 
 #if !AlwaysReload
-- (void) _actionButtonClicked {
+- (void) _customButtonClicked {
     int count([buttons_ count]);
     if (count == 0)
         return;
@@ -5252,15 +5226,18 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
            [sheet setCancelButtonIndex:[sheet numberOfButtons] - 1];
         }
         [sheet setContext:@"modify"];
-    
+
         [delegate_ showActionSheet:sheet fromItem:[[self navigationItem] rightBarButtonItem]];
     }
 }
 
-- (void) actionButtonClicked {
-       // Wait until it's done loading.
-    if (![self isLoading])
-        [self _actionButtonClicked];
+// We don't want to allow non-commercial packages to do custom things to the install button,
+// so it must call customButtonClicked with a custom commercial_ == 1 fallthrough.
+- (void) customButtonClicked {
+    if (commercial_)
+        [super customButtonClicked];
+    else
+        [self _customButtonClicked];
 }
 
 - (void) reloadButtonClicked {
@@ -5270,6 +5247,16 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 - (void) applyLoadingTitle {
     // Don't show "Loading" as the title. Ever.
 }
+
+- (UIBarButtonItem *) rightButton {
+    int count = [buttons_ count];
+    return [[[UIBarButtonItem alloc]
+        initWithTitle:count == 0 ? nil : count != 1 ? UCLocalize("MODIFY") : [buttons_ objectAtIndex:0]
+        style:UIBarButtonItemStylePlain
+        target:self
+        action:@selector(customButtonClicked)
+    ] autorelease];
+}
 #endif
 
 - (id) initWithDatabase:(Database *)database {
@@ -5337,19 +5324,6 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     }
 }
 
-- (void) applyRightButton {
-    int count = [buttons_ count];
-    UIBarButtonItem *actionItem = [[UIBarButtonItem alloc]
-        initWithTitle:count == 0 ? nil : count != 1 ? UCLocalize("MODIFY") : [buttons_ objectAtIndex:0]
-        style:UIBarButtonItemStylePlain
-        target:self
-        action:@selector(actionButtonClicked)
-    ];
-    if (![self isLoading]) [[self navigationItem] setRightBarButtonItem:actionItem];
-       else [super applyRightButton];
-    [actionItem release];
-}
-
 - (bool) isLoading {
     return commercial_ ? [super isLoading] : false;
 }
@@ -5361,7 +5335,10 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 /* Package Table {{{ */
-@interface PackageTable : UIView {
+@interface PackageTable : UIView <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     NSMutableArray *packages_;
     NSMutableArray *sections_;
@@ -5425,7 +5402,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 }
 
 - (UITableViewCell *) tableView:(UITableView *)table cellForRowAtIndexPath:(NSIndexPath *)path {
-    PackageCell *cell([table dequeueReusableCellWithIdentifier:@"Package"]);
+    PackageCell *cell((PackageCell *) [table dequeueReusableCellWithIdentifier:@"Package"]);
     if (cell == nil)
         cell = [[[PackageCell alloc] init] autorelease];
     [cell setPackage:[self packageAtIndexPath:path]];
@@ -5622,13 +5599,13 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 - (id) initWithDatabase:(Database *)database title:(NSString *)title filter:(SEL)filter with:(id)object;
 
 @end
-    
+
 @implementation FilteredPackageController
 
 - (void) dealloc {
     [packages_ release];
     [title_ release];
-    
+
     [super dealloc];
 }
 
@@ -5676,7 +5653,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 }
 
 @end
-    
+
 /* }}} */
 
 /* Add Source Controller {{{ */
@@ -5699,7 +5676,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 /* Source Cell {{{ */
-@interface SourceCell : UITableViewCell {
+@interface SourceCell : UITableViewCell <
+    ContentDelegate
+> {
     UIImage *icon_;
     NSString *origin_;
     NSString *description_;
@@ -5727,7 +5706,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (void) setSource:(Source *)source {
     [self clearSource];
-    
+
     if (icon_ == nil)
         icon_ = [UIImage applicationImageNamed:[NSString stringWithFormat:@"Sources/%@.png", [source host]]];
     if (icon_ == nil)
@@ -5779,21 +5758,24 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
     if (!selected)
         UISetColor(Black_);
-    [origin_ drawAtPoint:CGPointMake(48, 8) forWidth:(width - 80) withFont:Font18Bold_ ellipsis:2];
+    [origin_ drawAtPoint:CGPointMake(48, 8) forWidth:(width - 80) withFont:Font18Bold_ lineBreakMode:UILineBreakModeTailTruncation];
 
     if (!selected)
         UISetColor(Blue_);
-    [label_ drawAtPoint:CGPointMake(58, 29) forWidth:(width - 95) withFont:Font12_ ellipsis:2];
+    [label_ drawAtPoint:CGPointMake(58, 29) forWidth:(width - 95) withFont:Font12_ lineBreakMode:UILineBreakModeTailTruncation];
 
     if (!selected)
         UISetColor(Gray_);
-    [description_ drawAtPoint:CGPointMake(12, 46) forWidth:(width - 40) withFont:Font14_ ellipsis:2];
+    [description_ drawAtPoint:CGPointMake(12, 46) forWidth:(width - 40) withFont:Font14_ lineBreakMode:UILineBreakModeTailTruncation];
 }
 
 @end
 /* }}} */
 /* Source Table {{{ */
-@interface SourceTable : CYViewController {
+@interface SourceTable : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     UITableView *list_;
     NSMutableArray *sources_;
@@ -5814,6 +5796,8 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (id) initWithDatabase:(Database *)database;
 
+- (void) updateButtonsForEditingStatus:(BOOL)editing animated:(BOOL)animated;
+
 @end
 
 @implementation SourceTable
@@ -5895,12 +5879,12 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     SourceCell *cell = (SourceCell *) [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
     if(cell == nil) cell = [[[SourceCell alloc] initWithFrame:CGRectZero reuseIdentifier:cellIdentifier] autorelease];
     [cell setSource:[self sourceAtIndexPath:indexPath]];
-    
+
     return cell;
 }
 
-- (int) tableView:(UITableView *)tableView accessoryTypeForRowWithIndexPath:(NSIndexPath *)indexPath {
-    return 1; //UITableViewCellAccessoryDisclosureIndicator?
+- (UITableViewCellAccessoryType) tableView:(UITableView *)tableView accessoryTypeForRowWithIndexPath:(NSIndexPath *)indexPath {
+    return UITableViewCellAccessoryDisclosureIndicator;
 }
 
 - (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
@@ -6136,7 +6120,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     if ((self = [super init]) != nil) {
         [[self navigationItem] setTitle:UCLocalize("SOURCES")];
         [self updateButtonsForEditingStatus:NO animated:NO];
-    
+
         database_ = database;
         sources_ = [[NSMutableArray arrayWithCapacity:16] retain];
 
@@ -6222,7 +6206,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     ];
     [[self navigationItem] setRightBarButtonItem:rightItem animated:animated];
     [rightItem release];
-    
+
     if (IsWildcat_ && !editing) {
         UIBarButtonItem *settingsItem = [[UIBarButtonItem alloc]
             initWithTitle:UCLocalize("SETTINGS")
@@ -6241,7 +6225,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (void) editButtonClicked {
     [list_ setEditing:![list_ isEditing] animated:YES];
-    
+
     [self updateButtonsForEditingStatus:[list_ isEditing] animated:YES];
 }
 
@@ -6255,6 +6239,9 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (id) initWithDatabase:(Database *)database;
 
+- (void) updateRoleButton;
+- (void) queueStatusDidChange;
+
 @end
 
 @implementation InstalledController
@@ -6386,6 +6373,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @interface ManageController : CYBrowserController {
 }
 
+- (void) queueStatusDidChange;
 @end
 
 @implementation ManageController
@@ -6393,7 +6381,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 - (id) init {
     if ((self = [super init]) != nil) {
         [[self navigationItem] setTitle:UCLocalize("MANAGE")];
-    
+
         UIBarButtonItem *settingsItem = [[UIBarButtonItem alloc]
             initWithTitle:UCLocalize("SETTINGS")
             style:UIBarButtonItemStylePlain
@@ -6402,7 +6390,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         ];
         [[self navigationItem] setLeftBarButtonItem:settingsItem];
         [settingsItem release];
-    
+
         [self queueStatusDidChange];
     } return self;
 }
@@ -6435,7 +6423,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
             action:@selector(queueButtonClicked)
         ];
         [[self navigationItem] setRightBarButtonItem:queueItem];
-        
+
         [queueItem release];
     } else {
         [[self navigationItem] setRightBarButtonItem:nil];
@@ -6467,19 +6455,19 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
     frame.origin.x = [self frame].size.width - frame.size.width - 5;
     frame.origin.y = ([self frame].size.height - frame.size.height) / 2;
     [cancel_ setFrame:frame];
-    
+
     CGSize prgsize = {75, 100};
     CGRect prgrect = {{
         [self frame].size.width - prgsize.width - 10,
         ([self frame].size.height - prgsize.height) / 2
     } , prgsize};
     [progress_ setFrame:prgrect];
-    
+
     CGSize indsize([UIProgressIndicator defaultSizeForStyle:[indicator_ activityIndicatorViewStyle]]);
     unsigned indoffset = ([self frame].size.height - indsize.height) / 2;
     CGRect indrect = {{indoffset, indoffset}, indsize};
     [indicator_ setFrame:indrect];
-    
+
     CGSize prmsize = {215, indsize.height + 4};
     CGRect prmrect = {{
         indoffset * 2 + indsize.width,
@@ -6490,7 +6478,7 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 
 - (void)setFrame:(CGRect)frame {
     [super setFrame:frame];
-    
+
     [self positionViews];
 }
 
@@ -6499,10 +6487,10 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         [self setAutoresizingMask:UIViewAutoresizingFlexibleWidth];
 
         [self setTintColor:[UIColor colorWithRed:0.23 green:0.23 blue:0.23 alpha:1]];
-        [self setBarStyle:1];
+        [self setBarStyle:UIBarStyleBlack];
 
-        int barstyle([self _barStyle:NO]);
-        bool ugly(barstyle == 0);
+        UIBarStyle barstyle([self _barStyle:NO]);
+        bool ugly(barstyle == UIBarStyleDefault);
 
         UIProgressIndicatorStyle style = ugly ?
             UIProgressIndicatorStyleMediumBrown :
@@ -6523,12 +6511,12 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
         [progress_ setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleLeftMargin];
         [progress_ setStyle:0];
         [self addSubview:progress_];
-        
+
         cancel_ = [[UINavigationButton alloc] initWithTitle:UCLocalize("CANCEL") style:UINavigationButtonStyleHighlighted];
         [cancel_ setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin];
         [cancel_ addTarget:delegate action:@selector(cancelPressed) forControlEvents:UIControlEventTouchUpInside];
         [cancel_ setBarStyle:barstyle];
-        
+
         [self positionViews];
     } return self;
 }
@@ -6558,12 +6546,14 @@ bool DepSubstrate(const pkgCache::VerIterator &iterator) {
 @end
 /* }}} */
 
+@class CYNavigationController;
+
 /* Cydia Tab Bar Controller {{{ */
 @interface CYTabBarController : UITabBarController {
     Database *database_;
 }
 
-@end    
+@end
 
 @implementation CYTabBarController
 
@@ -6573,12 +6563,12 @@ freeing the view controllers on tab change */
 - (void) reloadData {
     size_t count([[self viewControllers] count]);
     for (size_t i(0); i != count; ++i) {
-        UIViewController *page([[self viewControllers] objectAtIndex:(count - i - 1)]);
+        CYNavigationController *page([[self viewControllers] objectAtIndex:(count - i - 1)]);
         [page reloadData];
     }
 }
 
-- (id) initWithDatabase: (Database *)database {
+- (id) initWithDatabase:(Database *)database {
     if ((self = [super init]) != nil) {
         database_ = database;
     } return self;
@@ -6588,9 +6578,7 @@ freeing the view controllers on tab change */
 /* }}} */
 
 /* Cydia Navigation Controller {{{ */
-@interface CYNavigationController : UINavigationController <
-    ProgressDelegate
-> {
+@interface CYNavigationController : UINavigationController {
     _transient Database *database_;
     id delegate_;
 }
@@ -6619,7 +6607,7 @@ freeing the view controllers on tab change */
 - (void) reloadData {
     size_t count([[self viewControllers] count]);
     for (size_t i(0); i != count; ++i) {
-        UIViewController *page([[self viewControllers] objectAtIndex:(count - i - 1)]);
+        CYViewController *page([[self viewControllers] objectAtIndex:(count - i - 1)]);
         [page reloadData];
     }
 }
@@ -6738,7 +6726,10 @@ freeing the view controllers on tab change */
 /* }}} */
 
 /* Sections Controller {{{ */
-@interface SectionsController : CYViewController {
+@interface SectionsController : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     NSMutableArray *sections_;
     NSMutableArray *filtered_;
@@ -6751,6 +6742,8 @@ freeing the view controllers on tab change */
 - (void) reloadData;
 - (void) resetView;
 
+- (void) editButtonClicked;
+
 @end
 
 @implementation SectionsController
@@ -6954,7 +6947,7 @@ freeing the view controllers on tab change */
         [list_ reloadData];
     else
         [delegate_ updateData];
-    
+
     [[self navigationItem] setTitle:editing_ ? UCLocalize("SECTION_VISIBILITY") : UCLocalize("SECTIONS")];
     [[[self navigationItem] rightBarButtonItem] setTitle:[sections_ count] == 0 ? nil : editing_ ? UCLocalize("DONE") : UCLocalize("EDIT")];
     [[[self navigationItem] rightBarButtonItem] setStyle:editing_ ? UIBarButtonItemStyleDone : UIBarButtonItemStylePlain];
@@ -6967,7 +6960,10 @@ freeing the view controllers on tab change */
 @end
 /* }}} */
 /* Changes Controller {{{ */
-@interface ChangesController : CYViewController {
+@interface ChangesController : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     NSMutableArray *packages_;
     NSMutableArray *sections_;
@@ -7027,7 +7023,7 @@ freeing the view controllers on tab change */
 }
 
 - (UITableViewCell *) tableView:(UITableView *)table cellForRowAtIndexPath:(NSIndexPath *)path {
-    PackageCell *cell([table dequeueReusableCellWithIdentifier:@"Package"]);
+    PackageCell *cell((PackageCell *) [table dequeueReusableCellWithIdentifier:@"Package"]);
     if (cell == nil)
         cell = [[[PackageCell alloc] init] autorelease];
     [cell setPackage:[self packageAtIndexPath:path]];
@@ -7048,7 +7044,7 @@ freeing the view controllers on tab change */
 }
 
 - (void) refreshButtonClicked {
-    [[UIApplication sharedApplication] beginUpdate];
+    [delegate_ beginUpdate];
     [[self navigationItem] setLeftBarButtonItem:nil];
 }
 
@@ -7187,15 +7183,17 @@ freeing the view controllers on tab change */
         target:self
         action:@selector(refreshButtonClicked)
     ];
-    if (![[UIApplication sharedApplication] updating]) [[self navigationItem] setLeftBarButtonItem:leftItem];
+    if (![delegate_ updating]) [[self navigationItem] setLeftBarButtonItem:leftItem];
     [leftItem release];
 }
 
 @end
 /* }}} */
 /* Search Controller {{{ */
-@interface SearchController : FilteredPackageController {
-    id search_;
+@interface SearchController : FilteredPackageController <
+    UISearchBarDelegate
+> {
+    UISearchBar *search_;
 }
 
 - (id) initWithDatabase:(Database *)database;
@@ -7228,9 +7226,9 @@ freeing the view controllers on tab change */
 }
 
 - (void)viewDidAppear:(BOOL)animated {
-       [super viewDidAppear:animated];
-       if (!search_) {
-        search_ = [[objc_getClass("UISearchBar") alloc] initWithFrame:CGRectMake(0, 0, [[self view] bounds].size.width, 44.0f)];
+    [super viewDidAppear:animated];
+    if (!search_) {
+        search_ = [[UISearchBar alloc] initWithFrame:CGRectMake(0, 0, [[self view] bounds].size.width, 44.0f)];
         [search_ layoutSubviews];
         [search_ setPlaceholder:UCLocalize("SEARCH_EX")];
         UITextField *textField = [search_ searchField];
@@ -7260,15 +7258,18 @@ freeing the view controllers on tab change */
 @end
 /* }}} */
 /* Settings Controller {{{ */
-@interface SettingsController : CYViewController {
+@interface SettingsController : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     NSString *name_;
     Package *package_;
-    UIPreferencesTable *table_;
-    _UISwitchSlider *subscribedSwitch_;
-    _UISwitchSlider *ignoredSwitch_;
-    UIPreferencesControlTableCell *subscribedCell_;
-    UIPreferencesControlTableCell *ignoredCell_;
+    UITableView *table_;
+    id subscribedSwitch_;
+    id ignoredSwitch_;
+    UITableViewCell *subscribedCell_;
+    UITableViewCell *ignoredCell_;
 }
 
 - (id) initWithDatabase:(Database *)database package:(NSString *)package;
@@ -7278,8 +7279,6 @@ freeing the view controllers on tab change */
 @implementation SettingsController
 
 - (void) dealloc {
-    [table_ setDataSource:nil];
-
     [name_ release];
     if (package_ != nil)
         [package_ release];
@@ -7288,64 +7287,32 @@ freeing the view controllers on tab change */
     [ignoredSwitch_ release];
     [subscribedCell_ release];
     [ignoredCell_ release];
+
     [super dealloc];
 }
 
-- (int) numberOfGroupsInPreferencesTable:(UIPreferencesTable *)table {
+- (NSInteger) numberOfSectionsInTableView:(UITableView *)tableView {
     if (package_ == nil)
         return 0;
 
-    return 2;
+    return 1;
 }
 
-- (NSString *) preferencesTable:(UIPreferencesTable *)table titleForGroup:(int)group {
-    if (package_ == nil)
-        return nil;
-
-    switch (group) {
-        case 0: return nil;
-        case 1: return nil;
-
-        _nodefault
-    }
-
-    return nil;
-}
-
-- (BOOL) preferencesTable:(UIPreferencesTable *)table isLabelGroup:(int)group {
-    if (package_ == nil)
-        return NO;
-
-    switch (group) {
-        case 0: return NO;
-        case 1: return YES;
-
-        _nodefault
-    }
-
-    return NO;
-}
-
-- (int) preferencesTable:(UIPreferencesTable *)table numberOfRowsInGroup:(int)group {
+- (NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
     if (package_ == nil)
         return 0;
 
-    switch (group) {
-        case 0: return 1;
-        case 1: return 1;
-
-        _nodefault
-    }
+    return 1;
+}
 
-    return 0;
+- (NSString *) tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section {
+    return UCLocalize("SHOW_ALL_CHANGES_EX");
 }
 
-- (void) onSomething:(UIPreferencesControlTableCell *)cell withKey:(NSString *)key {
+- (void) onSomething:(BOOL)value withKey:(NSString *)key {
     if (package_ == nil)
         return;
 
-    _UISwitchSlider *slider([cell control]);
-    BOOL value([slider value] != 0);
     NSMutableDictionary *metadata([package_ metadata]);
 
     BOOL before;
@@ -7361,37 +7328,21 @@ freeing the view controllers on tab change */
     }
 }
 
-- (void) onSubscribed:(UIPreferencesControlTableCell *)cell {
-    [self onSomething:cell withKey:@"IsSubscribed"];
+- (void) onSubscribed:(id)control {
+    [self onSomething:(int) [control isOn] withKey:@"IsSubscribed"];
 }
 
-- (void) onIgnored:(UIPreferencesControlTableCell *)cell {
-    [self onSomething:cell withKey:@"IsIgnored"];
+- (void) onIgnored:(id)control {
+    [self onSomething:(int) [control isOn] withKey:@"IsIgnored"];
 }
 
-- (id) preferencesTable:(UIPreferencesTable *)table cellForRow:(int)row inGroup:(int)group {
+- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
     if (package_ == nil)
         return nil;
 
-    switch (group) {
-        case 0: switch (row) {
-            case 0:
-                return subscribedCell_;
-            case 1:
-                return ignoredCell_;
-            _nodefault
-        } break;
-
-        case 1: switch (row) {
-            case 0: {
-                UIPreferencesControlTableCell *cell([[[UIPreferencesControlTableCell alloc] init] autorelease]);
-                [cell setShowSelection:NO];
-                [cell setTitle:UCLocalize("SHOW_ALL_CHANGES_EX")];
-                return cell;
-            }
-
-            _nodefault
-        } break;
+    switch ([indexPath row]) {
+        case 0: return subscribedCell_;
+        case 1: return ignoredCell_;
 
         _nodefault
     }
@@ -7408,26 +7359,29 @@ freeing the view controllers on tab change */
 
         [[self navigationItem] setTitle:UCLocalize("SETTINGS")];
 
-        table_ = [[UIPreferencesTable alloc] initWithFrame:[[self view] bounds]];
+        table_ = [[UITableView alloc] initWithFrame:[[self view] bounds] style:UITableViewStyleGrouped];
+        [table_ setAutoresizingMask:UIViewAutoresizingFlexibleBoth];
+        [table_ setAllowsSelection:NO];
         [[self view] addSubview:table_];
 
-        subscribedSwitch_ = [[_UISwitchSlider alloc] initWithFrame:CGRectMake(200, 10, 50, 20)];
-        [subscribedSwitch_ addTarget:self action:@selector(onSubscribed:) forEvents:UIControlEventTouchUpInside];
+        subscribedSwitch_ = [[objc_getClass("UISwitch") alloc] initWithFrame:CGRectMake(0, 0, 50, 20)];
+        [subscribedSwitch_ setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin];
+        [subscribedSwitch_ addTarget:self action:@selector(onSubscribed:) forEvents:UIControlEventValueChanged];
 
-        ignoredSwitch_ = [[_UISwitchSlider alloc] initWithFrame:CGRectMake(200, 10, 50, 20)];
-        [ignoredSwitch_ addTarget:self action:@selector(onIgnored:) forEvents:UIControlEventTouchUpInside];
+        ignoredSwitch_ = [[objc_getClass("UISwitch") alloc] initWithFrame:CGRectMake(0, 0, 50, 20)];
+        [ignoredSwitch_ setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin];
+        [ignoredSwitch_ addTarget:self action:@selector(onIgnored:) forEvents:UIControlEventValueChanged];
 
-        subscribedCell_ = [[UIPreferencesControlTableCell alloc] init];
-        [subscribedCell_ setShowSelection:NO];
-        [subscribedCell_ setTitle:UCLocalize("SHOW_ALL_CHANGES")];
-        [subscribedCell_ setControl:subscribedSwitch_];
+        subscribedCell_ = [[UITableViewCell alloc] init];
+        [subscribedCell_ setText:UCLocalize("SHOW_ALL_CHANGES")];
+        [subscribedCell_ setAccessoryView:subscribedSwitch_];
 
-        ignoredCell_ = [[UIPreferencesControlTableCell alloc] init];
-        [ignoredCell_ setShowSelection:NO];
-        [ignoredCell_ setTitle:UCLocalize("IGNORE_UPGRADES")];
-        [ignoredCell_ setControl:ignoredSwitch_];
+        ignoredCell_ = [[UITableViewCell alloc] init];
+        [ignoredCell_ setText:UCLocalize("IGNORE_UPGRADES")];
+        [ignoredCell_ setAccessoryView:ignoredSwitch_];
 
         [table_ setDataSource:self];
+        [table_ setDelegate:self];
         [self reloadData];
     } return self;
 }
@@ -7438,8 +7392,8 @@ freeing the view controllers on tab change */
     package_ = [database_ packageWithName:name_];
     if (package_ != nil) {
         [package_ retain];
-        [subscribedSwitch_ setValue:([package_ subscribed] ? 1 : 0) animated:NO];
-        [ignoredSwitch_ setValue:([package_ ignored] ? 1 : 0) animated:NO];
+        [subscribedSwitch_ setOn:([package_ subscribed] ? 1 : 0) animated:NO];
+        [ignoredSwitch_ setOn:([package_ ignored] ? 1 : 0) animated:NO];
     }
 
     [table_ reloadData];
@@ -7485,13 +7439,20 @@ freeing the view controllers on tab change */
 @end
 /* }}} */
 /* Role Controller {{{ */
-@interface RoleController : CYViewController {
+@interface RoleController : CYViewController <
+    UITableViewDataSource,
+    UITableViewDelegate
+> {
     _transient Database *database_;
     id roledelegate_;
     UITableView *table_;
     UISegmentedControl *segment_;
     UIView *container_;
 }
+
+- (void) showDoneButton;
+- (void) resizeSegmentedControl;
+
 @end
 
 @implementation RoleController
@@ -7499,7 +7460,7 @@ freeing the view controllers on tab change */
     [table_ release];
     [segment_ release];
     [container_ release];
-    
+
     [super dealloc];
 }
 
@@ -7507,18 +7468,18 @@ freeing the view controllers on tab change */
     if ((self = [super init])) {
         database_ = database;
         roledelegate_ = delegate;
-        
+
         [[self navigationItem] setTitle:UCLocalize("WHO_ARE_YOU")];
-        
+
         NSArray *items = [NSArray arrayWithObjects:
-            UCLocalize("USER"), 
+            UCLocalize("USER"),
             UCLocalize("HACKER"),
             UCLocalize("DEVELOPER"),
         nil];
         segment_ = [[UISegmentedControl alloc] initWithItems:items];
         container_ = [[UIView alloc] initWithFrame:CGRectMake(0, 0, [[self view] frame].size.width, 44.0f)];
         [container_ addSubview:segment_];
-        
+
         int index = -1;
         if ([Role_ isEqualToString:@"User"]) index = 0;
         if ([Role_ isEqualToString:@"Hacker"]) index = 1;
@@ -7527,9 +7488,10 @@ freeing the view controllers on tab change */
             [segment_ setSelectedSegmentIndex:index];
             [self showDoneButton];
         }
-        
+
         [segment_ addTarget:self action:@selector(segmentChanged:) forControlEvents:UIControlEventValueChanged];
-        
+        [self resizeSegmentedControl];
+
         table_ = [[UITableView alloc] initWithFrame:[[self view] bounds] style:UITableViewStyleGrouped];
         [table_ setAutoresizingMask:UIViewAutoresizingFlexibleBoth];
         [table_ setDelegate:self];
@@ -7539,31 +7501,53 @@ freeing the view controllers on tab change */
     } return self;
 }
 
-- (void) viewWillAppear:(BOOL)animated {
-    [super viewWillAppear:animated];
-    
+- (void) resizeSegmentedControl {
     CGFloat width = [[self view] frame].size.width;
     [segment_ setFrame:CGRectMake(width / 32.0f, 0, width - (width / 32.0f * 2.0f), 44.0f)];
 }
 
+- (void) viewWillAppear:(BOOL)animated {
+    [super viewWillAppear:animated];
+
+    [self resizeSegmentedControl];
+}
+
+- (void) willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation duration:(NSTimeInterval)duration {
+    [self resizeSegmentedControl];
+}
+
+- (void) didRotateFromInterfaceOrientation:(UIInterfaceOrientation)fromInterfaceOrientation {
+    [self resizeSegmentedControl];
+}
+
 - (void) save {
+    NSString *role(nil);
+
     switch ([segment_ selectedSegmentIndex]) {
-        case 0: Role_ = @"User"; break;
-        case 1: Role_ = @"Hacker"; break;
-        case 2: Role_ = @"Developer"; break;
+        case 0: role = @"User"; break;
+        case 1: role = @"Hacker"; break;
+        case 2: role = @"Developer"; break;
 
         _nodefault
     }
 
-    Settings_ = [NSMutableDictionary dictionaryWithObjectsAndKeys:
-        Role_, @"Role",
-    nil];
+    if (![role isEqualToString:Role_]) {
+        bool rolling(Role_ == nil);
+        Role_ = role;
 
-    [Metadata_ setObject:Settings_ forKey:@"Settings"];
+        Settings_ = [NSMutableDictionary dictionaryWithObjectsAndKeys:
+            Role_, @"Role",
+        nil];
 
-    Changed_ = true;
-    
-    [delegate_ updateData];
+        [Metadata_ setObject:Settings_ forKey:@"Settings"];
+
+        Changed_ = true;
+
+        if (rolling)
+            [roledelegate_ loadData];
+        else
+            [roledelegate_ updateData];
+    }
 }
 
 - (void) segmentChanged:(UISegmentedControl *)control {
@@ -7587,7 +7571,8 @@ freeing the view controllers on tab change */
 }
 
 - (NSInteger) numberOfSectionsInTableView:(UITableView *)tableView {
-    return 5;
+    // XXX: For not having a single cell in the table, this sure is a lot of sections.
+    return 6;
 }
 
 - (NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
@@ -7599,13 +7584,13 @@ freeing the view controllers on tab change */
 }
 
 - (NSString *) tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section {
-    if (section == 1) 
+    if (section == 1)
         return UCLocalize("ROLE_EX");
-    if (section == 4) 
+    if (section == 4)
         return [NSString stringWithFormat:
             @"%@: %@\n%@: %@\n%@: %@",
-            UCLocalize("USER"), UCLocalize("USER_EX"), 
-            UCLocalize("HACKER"), UCLocalize("HACKER_EX"), 
+            UCLocalize("USER"), UCLocalize("USER_EX"),
+            UCLocalize("HACKER"), UCLocalize("HACKER_EX"),
             UCLocalize("DEVELOPER"), UCLocalize("DEVELOPER_EX")
         ];
     else return nil;
@@ -7632,9 +7617,15 @@ freeing the view controllers on tab change */
     bool dropped_;
     bool updating_;
     id updatedelegate_;
-    UIViewController *root_;
+    UITabBarController *root_;
 }
 
+- (void) setTabBarController:(UITabBarController *)controller;
+
+- (void) dropBar:(BOOL)animated;
+- (void) beginUpdate;
+- (void) raiseBar:(BOOL)animated;
+
 @end
 
 @implementation CYContainer
@@ -7663,10 +7654,10 @@ freeing the view controllers on tab change */
 }
 
 - (BOOL) shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)orientation {
-    return YES; /* XXX: return YES; */
+    return IsWildcat_;
 }
 
-- (void) setRootController:(UIViewController *)controller {
+- (void) setTabBarController:(UITabBarController *)controller {
     root_ = controller;
     [[self view] addSubview:[root_ view]];
 }
@@ -7678,9 +7669,9 @@ freeing the view controllers on tab change */
 - (void) beginUpdate {
     [self dropBar:YES];
     [refreshbar_ start];
-    
+
     updating_ = true;
-    
+
     [NSThread
         detachNewThreadSelector:@selector(performUpdate)
         toTarget:self
@@ -7702,7 +7693,7 @@ freeing the view controllers on tab change */
 
 - (void) completeUpdate {
     updating_ = false;
-    
+
     [self raiseBar:YES];
     [refreshbar_ stop];
     [updatedelegate_ performSelector:@selector(reloadData) withObject:nil afterDelay:0];
@@ -7780,8 +7771,8 @@ freeing the view controllers on tab change */
     if (animated) [UIView beginAnimations:nil context:NULL];
     CGRect barframe = [refreshbar_ frame];
     CGRect viewframe = [[root_ view] frame];
-    viewframe.origin.y += barframe.size.height + 20.0f;
-    viewframe.size.height -= barframe.size.height + 20.0f;
+    viewframe.origin.y += barframe.size.height;
+    viewframe.size.height -= barframe.size.height;
     [[root_ view] setFrame:viewframe];
     if (animated) [UIView commitAnimations];
 
@@ -7802,8 +7793,8 @@ freeing the view controllers on tab change */
     if (animated) [UIView beginAnimations:nil context:NULL];
     CGRect barframe = [refreshbar_ frame];
     CGRect viewframe = [[root_ view] frame];
-    viewframe.origin.y -= barframe.size.height + 20.0f;
-    viewframe.size.height += barframe.size.height + 20.0f;
+    viewframe.origin.y -= barframe.size.height;
+    viewframe.size.height += barframe.size.height;
     [[root_ view] setFrame:viewframe];
     if (animated) [UIView commitAnimations];
 
@@ -7811,8 +7802,7 @@ freeing the view controllers on tab change */
     [[root_ selectedViewController] _updateLayoutForStatusBarAndInterfaceOrientation];
 }
 
-- (void)willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation duration:(NSTimeInterval)duration
-{
+- (void) willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation duration:(NSTimeInterval)duration {
     // XXX: fix Apple's layout bug
     [[root_ selectedViewController] _updateLayoutForStatusBarAndInterfaceOrientation];
 }
@@ -7822,7 +7812,7 @@ freeing the view controllers on tab change */
         [self raiseBar:NO];
         [self dropBar:NO];
     }
-    
+
     // XXX: fix Apple's layout bug
     [[root_ selectedViewController] _updateLayoutForStatusBarAndInterfaceOrientation];
 }
@@ -7890,8 +7880,9 @@ typedef enum {
     bool loaded_;
 }
 
-- (UIViewController *) _pageForURL:(NSURL *)url withClass:(Class)_class;
-- (void) setPage:(UIViewController *)page;
+- (UCViewController *) _pageForURL:(NSURL *)url withClass:(Class)_class;
+- (void) setPage:(UCViewController *)page;
+- (void) loadData;
 
 @end
 
@@ -7973,7 +7964,7 @@ static _finline void _setHomePage(Cydia *self) {
     if (tag_ != 4 && search_ != nil)
         [search_ reloadData];
 
-    [[tabbar_ selectedViewController] reloadData];
+    [(CYNavigationController *)[tabbar_ selectedViewController] reloadData];
 }
 
 - (int)indexOfTabWithTag:(int)tag {
@@ -7982,16 +7973,16 @@ static _finline void _setHomePage(Cydia *self) {
         if ([[controller tabBarItem] tag] == tag) return i;
         i += 1;
     }
-    
+
     return -1;
 }
 
 - (void) _refreshIfPossible {
     NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
-    
+
     Reachability* reachability = [Reachability reachabilityWithHostName:@"cydia.saurik.com"];
     NetworkStatus remoteHostStatus = [reachability currentReachabilityStatus];
-    
+
     if (loaded_ || ManualRefresh || remoteHostStatus == NotReachable) loaded:
         [self performSelectorOnMainThread:@selector(_loaded) withObject:nil waitUntilDone:NO];
     else {
@@ -8016,8 +8007,6 @@ static _finline void _setHomePage(Cydia *self) {
 }
 
 - (void) _reloadData {
-    UIView *block();
-
     UIProgressHUD *hud([self addProgressHUD]);
     [hud setText:(loaded_ ? UCLocalize("RELOADING_DATA") : UCLocalize("LOADING_DATA"))];
 
@@ -8046,7 +8035,7 @@ static _finline void _setHomePage(Cydia *self) {
         NSString *badge([[NSNumber numberWithInt:changes] stringValue]);
         [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kChangesTag]] tabBarItem] setBadgeValue:badge];
         [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kChangesTag]] tabBarItem] setAnimatedBadge:YES];
-    
+
         if ([self respondsToSelector:@selector(setApplicationBadge:)])
             [self setApplicationBadge:badge];
         else
@@ -8054,7 +8043,7 @@ static _finline void _setHomePage(Cydia *self) {
     } else {
         [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kChangesTag]] tabBarItem] setBadgeValue:nil];
         [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kChangesTag]] tabBarItem] setAnimatedBadge:NO];
-    
+
         if ([self respondsToSelector:@selector(removeApplicationBadge)])
             [self removeApplicationBadge];
         else // XXX: maybe use setApplicationBadgeString also?
@@ -8194,7 +8183,7 @@ static _finline void _setHomePage(Cydia *self) {
 
 - (void) confirmWithNavigationController:(UINavigationController *)navigation {
     ProgressController *progress = [[[ProgressController alloc] initWithDatabase:database_ delegate:self] autorelease];
-    
+
     if (navigation != nil) {
         [navigation pushViewController:progress animated:YES];
     } else {
@@ -8202,7 +8191,7 @@ static _finline void _setHomePage(Cydia *self) {
         if (IsWildcat_) [navigation setModalPresentationStyle:UIModalPresentationFormSheet];
         [container_ presentModalViewController:navigation animated:YES];
     }
-    
+
     [progress
         detachNewThreadSelector:@selector(perform)
         toTarget:database_
@@ -8215,17 +8204,17 @@ static _finline void _setHomePage(Cydia *self) {
     [self complete];
 }
 
-- (void) setPage:(UIViewController *)page {
+- (void) setPage:(UCViewController *)page {
     [page setDelegate:self];
 
-    UINavigationController *navController = [tabbar_ selectedViewController];
+    CYNavigationController *navController = (CYNavigationController *) [tabbar_ selectedViewController];
     [navController setViewControllers:[NSArray arrayWithObject:page] animated:NO];
-    for (UIViewController *page in [tabbar_ viewControllers]) {
+    for (CYNavigationController *page in [tabbar_ viewControllers]) {
         if (page != navController) [page setViewControllers:nil];
     }
 }
 
-- (UIViewController *) _pageForURL:(NSURL *)url withClass:(Class)_class {
+- (UCViewController *) _pageForURL:(NSURL *)url withClass:(Class)_class {
     CYBrowserController *browser = [[[_class alloc] init] autorelease];
     [browser loadURL:url];
     return browser;
@@ -8274,10 +8263,10 @@ static _finline void _setHomePage(Cydia *self) {
     return installed_;
 }
 
-- (void) tabBarController:(id)tabBarController didSelectViewController:(UIViewController *)viewController {    
+- (void) tabBarController:(id)tabBarController didSelectViewController:(UIViewController *)viewController {
     int tag = [[viewController tabBarItem] tag];
     if (tag == tag_) {
-        [[tabbar_ selectedViewController] popToRootViewControllerAnimated:YES];
+        [(CYNavigationController *)[tabbar_ selectedViewController] popToRootViewControllerAnimated:YES];
         return;
     } else if (tag_ == 1) {
         [[self sectionsController] resetView];
@@ -8301,7 +8290,7 @@ static _finline void _setHomePage(Cydia *self) {
 
 - (void) showSettings {
     RoleController *role = [[RoleController alloc] initWithDatabase:database_ delegate:self];
-    UINavigationController *nav = [[UINavigationController alloc] initWithRootViewController:role];
+    CYNavigationController *nav = [[CYNavigationController alloc] initWithRootViewController:role];
     if (IsWildcat_) [nav setModalPresentationStyle:UIModalPresentationFormSheet];
     [container_ presentModalViewController:nav animated:YES];
 }
@@ -8352,7 +8341,7 @@ static _finline void _setHomePage(Cydia *self) {
             }
 
             [self updateData];
-            
+
             Queuing_ = false;
             [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kManageTag] != -1 ? [self indexOfTabWithTag:kManageTag] : [self indexOfTabWithTag:kInstalledTag]] tabBarItem] setBadgeValue:nil];
             [queueDelegate_ queueStatusDidChange];*/
@@ -8361,8 +8350,8 @@ static _finline void _setHomePage(Cydia *self) {
             Queuing_ = true;
 
             [[[[tabbar_ viewControllers] objectAtIndex:[self indexOfTabWithTag:kManageTag] != -1 ? [self indexOfTabWithTag:kManageTag] : [self indexOfTabWithTag:kInstalledTag]] tabBarItem] setBadgeValue:UCLocalize("Q_D")];
-            [[tabbar_ selectedViewController] reloadData];
-            
+            [(CYNavigationController *)[tabbar_ selectedViewController] reloadData];
+
             [queueDelegate_ queueStatusDidChange];
         }
     }
@@ -8370,7 +8359,7 @@ static _finline void _setHomePage(Cydia *self) {
 
 - (void) alertView:(UIAlertView *)alert clickedButtonAtIndex:(NSInteger)button {
     NSString *context([alert context]);
-    
+
     if ([context isEqualToString:@"fixhalf"]) {
         if (button == [alert firstOtherButtonIndex]) {
             @synchronized (self) {
@@ -8454,7 +8443,7 @@ static _finline void _setHomePage(Cydia *self) {
     [window_ setUserInteractionEnabled:YES];
 }
 
-- (UIViewController *) pageForPackage:(NSString *)name {
+- (UCViewController *) pageForPackage:(NSString *)name {
     if (Package *package = [database_ packageWithName:name]) {
         PackageController *view([self packageController]);
         [view setPackage:package];
@@ -8466,7 +8455,7 @@ static _finline void _setHomePage(Cydia *self) {
     }
 }
 
-- (UIViewController *) pageForURL:(NSURL *)url hasTag:(int *)tag {
+- (UCViewController *) pageForURL:(NSURL *)url hasTag:(int *)tag {
     if (tag != NULL)
         *tag = -1;
 
@@ -8518,7 +8507,7 @@ static _finline void _setHomePage(Cydia *self) {
 - (void) applicationOpenURL:(NSURL *)url {
     [super applicationOpenURL:url];
     int tag;
-    if (UIViewController *page = [self pageForURL:url hasTag:&tag]) {
+    if (UCViewController *page = [self pageForURL:url hasTag:&tag]) {
         [self setPage:page];
         tag_ = tag;
         [tabbar_ setSelectedViewController:(tag_ == -1 ? nil : [[tabbar_ viewControllers] objectAtIndex:tag_])];
@@ -8528,8 +8517,9 @@ static _finline void _setHomePage(Cydia *self) {
 - (void) applicationWillResignActive:(UIApplication *)application {
     // Stop refreshing if you get a phone call or lock the device.
     if ([container_ updating]) [container_ cancelUpdate];
-    
-    [super applicationWillResignActive:application];
+
+    if ([[self superclass] instancesRespondToSelector:@selector(applicationWillResignActive:)])
+        [super applicationWillResignActive:application];
 }
 
 - (void) applicationDidFinishLaunching:(id)unused {
@@ -8589,36 +8579,28 @@ static _finline void _setHomePage(Cydia *self) {
         return;
     }
 
-    if (Role_ == nil)
-        [self showSettings];
-
     _trace();
 
-    NSMutableArray *controllers = [NSMutableArray array];
-    [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-    [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-    [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-    if (IsWildcat_) [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-    [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-    [controllers addObject:[[CYNavigationController alloc] initWithDatabase:database_]];
-
-    NSMutableArray *items = [NSMutableArray arrayWithObjects:
+    NSMutableArray *items([NSMutableArray arrayWithObjects:
         [[[UITabBarItem alloc] initWithTitle:@"Cydia" image:[UIImage applicationImageNamed:@"home.png"] tag:kCydiaTag] autorelease],
         [[[UITabBarItem alloc] initWithTitle:UCLocalize("SECTIONS") image:[UIImage applicationImageNamed:@"install.png"] tag:kSectionsTag] autorelease],
         [[[UITabBarItem alloc] initWithTitle:UCLocalize("CHANGES") image:[UIImage applicationImageNamed:@"changes.png"] tag:kChangesTag] autorelease],
         [[[UITabBarItem alloc] initWithTitle:UCLocalize("SEARCH") image:[UIImage applicationImageNamed:@"search.png"] tag:kSearchTag] autorelease],
-        nil
-    ];
-    
+    nil]);
+
     if (IsWildcat_) {
         [items insertObject:[[[UITabBarItem alloc] initWithTitle:UCLocalize("SOURCES") image:[UIImage applicationImageNamed:@"source.png"] tag:kSourcesTag] autorelease] atIndex:3];
         [items insertObject:[[[UITabBarItem alloc] initWithTitle:UCLocalize("INSTALLED") image:[UIImage applicationImageNamed:@"manage.png"] tag:kInstalledTag] autorelease] atIndex:3];
     } else {
         [items insertObject:[[[UITabBarItem alloc] initWithTitle:UCLocalize("MANAGE") image:[UIImage applicationImageNamed:@"manage.png"] tag:kManageTag] autorelease] atIndex:3];
     }
-    
-    for (int i = 0; i < [items count]; i++) {
-        [[controllers objectAtIndex:i] setTabBarItem:[items objectAtIndex:i]];
+
+    NSMutableArray *controllers([NSMutableArray array]);
+
+    for (UITabBarItem *item in items) {
+        CYNavigationController *controller([[[CYNavigationController alloc] initWithDatabase:database_] autorelease]);
+        [controller setTabBarItem:item];
+        [controllers addObject:controller];
     }
 
     tabbar_ = [[CYTabBarController alloc] initWithDatabase:database_];
@@ -8628,9 +8610,17 @@ static _finline void _setHomePage(Cydia *self) {
 
     container_ = [[CYContainer alloc] initWithDatabase:database_];
     [container_ setUpdateDelegate:self];
-    [container_ setRootController:tabbar_];
+    [container_ setTabBarController:tabbar_];
     [window_ addSubview:[container_ view]];
-    [[tabbar_ view] setFrame:CGRectMake(0, -20.0f, [window_ bounds].size.width, [window_ bounds].size.height)];
+
+    [self performSelector:@selector(loadData) withObject:nil afterDelay:0];
+}
+
+- (void) loadData {
+    if (Role_ == nil) {
+        [self showSettings];
+        return;
+    }
 
     [UIKeyboard initImplementationNow];
 
@@ -8683,19 +8673,20 @@ static NSNumber *shouldPlayKeyboardSounds;
 
 Class $UIHardware;
 
-MSHook(void, UIHardware$_playSystemSound$, Class self, SEL _cmd, int soundIndex) {
-    switch (soundIndex) {
+MSHook(void, UIHardware$_playSystemSound$, Class self, SEL _cmd, int sound) {
+    switch (sound) {
         case 1104: // Keyboard Button Clicked
         case 1105: // Keyboard Delete Repeated
-            if (!shouldPlayKeyboardSounds) {
-                NSDictionary *dict = [[NSDictionary alloc] initWithContentsOfFile:@"/var/mobile/Library/Preferences/com.apple.preferences.sounds.plist"];
-                shouldPlayKeyboardSounds = [[dict objectForKey:@"keyboard"] ?: (id)kCFBooleanTrue retain];
-                [dict release];
+            if (shouldPlayKeyboardSounds == nil) {
+                NSDictionary *dict([[[NSDictionary alloc] initWithContentsOfFile:@"/var/mobile/Library/Preferences/com.apple.preferences.sounds.plist"] autorelease]);
+                shouldPlayKeyboardSounds = [([dict objectForKey:@"keyboard"] ?: (id) kCFBooleanTrue) retain];
             }
+
             if (![shouldPlayKeyboardSounds boolValue])
                 break;
+
         default:
-            _UIHardware$_playSystemSound$(self, _cmd, soundIndex);
+            _UIHardware$_playSystemSound$(self, _cmd, sound);
     }
 }
 
@@ -8963,10 +8954,10 @@ int main(int argc, char *argv[]) { _pooled
     Warning_ = UCLocalize("WARNING");
 
     _trace();
-    int value = UIApplicationMain(argc, argv, @"Cydia", @"Cydia");
+    int value(UIApplicationMain(argc, argv, @"Cydia", @"Cydia"));
 
     CGColorSpaceRelease(space_);
     CFRelease(Locale_);
 
     return value;
-}
\ No newline at end of file
+}