浏览代码

server browsing for HTTP, Plex, SAP and DSM.
TODO: playback, login

Tobias Conradi 9 年之前
父节点
当前提交
8a88529949

+ 3 - 1
SharedSources/ServerBrowsing/HTTP/VLCLocalNetworkServiceBrowserHTTP.m

@@ -50,7 +50,9 @@
 
 - (void)sharedLibraryFound:(NSNotification *)aNotification {
     NSNetService *netService = [aNotification.userInfo objectForKey:@"aNetService"];
-    [self addResolvedLocalNetworkService:[self localServiceForNetService:netService]];
+    [[NSOperationQueue mainQueue] addOperationWithBlock:^{
+        [self addResolvedLocalNetworkService:[self localServiceForNetService:netService]];
+    }];
 }
 
 - (VLCLocalNetworkServiceNetService *)localServiceForNetService:(NSNetService *)netService {

+ 2 - 1
VLC for Apple TV/AppleTVAppDelegate.m

@@ -70,7 +70,8 @@
     _mainViewController.tabBar.backgroundColor = [UIColor VLCOrangeTintColor];
 
     _mainViewController.viewControllers = @[[[UINavigationController alloc] initWithRootViewController:_sharesVC],
-                                            _localNetworkVC, _cloudServicesVC, _openNetworkVC, _aboutSettingsVC];
+                                            [[UINavigationController alloc] initWithRootViewController:_localNetworkVC],
+                                            _cloudServicesVC, _openNetworkVC, _aboutSettingsVC];
 
     VLCPlayerDisplayController *playerDisplayController = [VLCPlayerDisplayController sharedInstance];
     playerDisplayController.childViewController = _mainViewController;

+ 2 - 1
VLC for Apple TV/VLCLocalNetworkTVViewController.h

@@ -10,7 +10,8 @@
  *****************************************************************************/
 
 #import <UIKit/UIKit.h>
+#import "VLCServerListTVTableViewController.h"
 
-@interface VLCLocalNetworkTVViewController : UIViewController
+@interface VLCLocalNetworkTVViewController : VLCServerListTVTableViewController
 
 @end

+ 17 - 7
VLC for Apple TV/VLCLocalNetworkTVViewController.m

@@ -11,6 +11,13 @@
 
 #import "VLCLocalNetworkTVViewController.h"
 
+#import "VLCLocalNetworkServiceBrowserManualConnect.h"
+#import "VLCLocalNetworkServiceBrowserPlex.h"
+//#import "VLCLocalNetworkServiceBrowserFTP.h"
+//#import "VLCLocalNetworkServiceBrowserUPnP.h"
+#import "VLCLocalNetworkServiceBrowserSAP.h"
+#import "VLCLocalNetworkServiceBrowserDSM.h"
+
 @interface VLCLocalNetworkTVViewController ()
 
 @end
@@ -19,14 +26,17 @@
 
 - (void)viewDidLoad {
     [super viewDidLoad];
-    // Do any additional setup after loading the view.
-}
-
-- (void)didReceiveMemoryWarning {
-    [super didReceiveMemoryWarning];
-    // Dispose of any resources that can be recreated.
+    NSArray *classes = @[
+                         [VLCLocalNetworkServiceBrowserManualConnect class],
+//                         [VLCLocalNetworkServiceBrowserUPnP class],
+                         [VLCLocalNetworkServiceBrowserPlex class],
+//                         [VLCLocalNetworkServiceBrowserFTP class],
+                         [VLCLocalNetworkServiceBrowserSAP class],
+                         [VLCLocalNetworkServiceBrowserDSM class],
+                         ];
+    self.discoveryController = [[VLCLocalServerDiscoveryController alloc] initWithServiceBrowserClasses:classes];
+    self.discoveryController.delegate = self;
 }
-
 - (NSString *)title {
     return NSLocalizedString(@"LOCAL_NETWORK", nil);
 }

+ 6 - 19
VLC for Apple TV/VLCLocalNetworkTVViewController.xib

@@ -6,28 +6,15 @@
     <objects>
         <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="VLCLocalNetworkTVViewController">
             <connections>
-                <outlet property="view" destination="iN0-l3-epB" id="Eym-vH-oyN"/>
+                <outlet property="view" destination="Ysv-ad-ZDr" id="dLe-dW-9wX"/>
             </connections>
         </placeholder>
-        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
-        <view contentMode="scaleToFill" id="iN0-l3-epB">
+        <tableView clipsSubviews="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" style="plain" separatorStyle="default" rowHeight="66" sectionHeaderHeight="40" sectionFooterHeight="40" id="Ysv-ad-ZDr">
             <rect key="frame" x="0.0" y="0.0" width="1920" height="1080"/>
-            <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
-            <subviews>
-                <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Local Network" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Vjg-kr-rER">
-                    <rect key="frame" x="905" y="530" width="110" height="21"/>
-                    <animations/>
-                    <fontDescription key="fontDescription" type="system" pointSize="17"/>
-                    <color key="textColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
-                    <nil key="highlightedColor"/>
-                </label>
-            </subviews>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
             <animations/>
-            <color key="backgroundColor" white="0.33333333333333331" alpha="1" colorSpace="calibratedWhite"/>
-            <constraints>
-                <constraint firstItem="Vjg-kr-rER" firstAttribute="centerX" secondItem="iN0-l3-epB" secondAttribute="centerX" id="0f4-Tq-f3X"/>
-                <constraint firstItem="Vjg-kr-rER" firstAttribute="centerY" secondItem="iN0-l3-epB" secondAttribute="centerY" id="600-th-yGQ"/>
-            </constraints>
-        </view>
+            <color key="backgroundColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
+        </tableView>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
     </objects>
 </document>

+ 14 - 0
VLC for Apple TV/VLCServerBrowsingTVTableViewController.h

@@ -0,0 +1,14 @@
+//
+//  VLCServerBrowsingTVTableViewController.h
+//  VLC for iOS
+//
+//  Created by Tobias Conradi on 27.10.15.
+//  Copyright © 2015 VideoLAN. All rights reserved.
+//
+
+#import <UIKit/UIKit.h>
+#import "VLCNetworkServerBrowser-Protocol.h"
+@interface VLCServerBrowsingTVTableViewController : UITableViewController <VLCNetworkServerBrowserDelegate>
+
+- (instancetype)initWithServerBrowser:(id<VLCNetworkServerBrowser>)serverBrowser;
+@end

+ 145 - 0
VLC for Apple TV/VLCServerBrowsingTVTableViewController.m

@@ -0,0 +1,145 @@
+//
+//  VLCServerBrowsingTVTableViewController.m
+//  VLC for iOS
+//
+//  Created by Tobias Conradi on 27.10.15.
+//  Copyright © 2015 VideoLAN. All rights reserved.
+//
+
+#import "VLCServerBrowsingTVTableViewController.h"
+
+@interface VLCServerBrowsingTVTableViewController ()
+@property (nonatomic, readonly) id<VLCNetworkServerBrowser>serverBrowser;
+@property (nonatomic) NSByteCountFormatter *byteCounterFormatter;
+
+@end
+static NSString *const cellIdentifier = @"cell";
+
+@implementation VLCServerBrowsingTVTableViewController
+
+- (instancetype)initWithServerBrowser:(id<VLCNetworkServerBrowser>)serverBrowser
+{
+    self = [super init];
+    if (self) {
+        _serverBrowser = serverBrowser;
+        serverBrowser.delegate = self;
+        self.title = serverBrowser.title;
+    }
+    return self;
+}
+
+- (void)viewDidLoad {
+    [super viewDidLoad];
+    [self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:cellIdentifier];
+}
+
+- (void)viewDidAppear:(BOOL)animated {
+    [super viewDidAppear:animated];
+    [self.serverBrowser update];
+}
+
+#pragma mark -
+
+- (void)networkServerBrowserDidUpdate:(id<VLCNetworkServerBrowser>)networkBrowser {
+    self.title = networkBrowser.title;
+    [self.tableView reloadData];
+}
+
+- (void)networkServerBrowser:(id<VLCNetworkServerBrowser>)networkBrowser requestDidFailWithError:(NSError *)error {
+
+    UIAlertController *alertController = [UIAlertController alertControllerWithTitle:NSLocalizedString(@"LOCAL_SERVER_CONNECTION_FAILED_TITLE", nil)
+                                                                             message:NSLocalizedString(@"LOCAL_SERVER_CONNECTION_FAILED_MESSAGE", nil)
+                                                                      preferredStyle:UIAlertControllerStyleAlert];
+
+
+    [alertController addAction:[UIAlertAction actionWithTitle:NSLocalizedString(@"BUTTON_CANCEL", nil)
+                                                        style:UIAlertActionStyleCancel
+                                                      handler:nil]];
+    [self presentViewController:alertController animated:YES completion:nil];
+}
+
+#pragma mark -
+- (NSByteCountFormatter *)byteCounterFormatter {
+    if (!_byteCounterFormatter) {
+        _byteCounterFormatter = [[NSByteCountFormatter alloc] init];
+    }
+    return _byteCounterFormatter;
+}
+
+
+#pragma mark - Table view data source
+
+- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
+    return [self.serverBrowser items].count;
+}
+
+
+- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
+    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier forIndexPath:indexPath];
+
+    if (cell) {
+        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellIdentifier];
+    }
+
+    id<VLCNetworkServerBrowserItem> item = self.serverBrowser.items[indexPath.row];
+
+    cell.textLabel.text = item.name;
+
+    if (item.isContainer) {
+//        cell.isDirectory = YES;
+        cell.imageView.image = [UIImage imageNamed:@"folder"];
+    } else {
+//        cell.isDirectory = NO;
+        cell.imageView.image = [UIImage imageNamed:@"blank"];
+
+        NSString *sizeString = item.fileSizeBytes ? [self.byteCounterFormatter stringFromByteCount:item.fileSizeBytes.longLongValue] : nil;
+
+        NSString *duration = nil;
+        if ([item respondsToSelector:@selector(duration)]) {
+            duration = item.duration;
+        }
+
+        NSString *subtitle = nil;
+        if (sizeString && duration) {
+            subtitle = [NSString stringWithFormat:@"%@ (%@)",sizeString, duration];
+        } else if (sizeString) {
+            subtitle = sizeString;
+        } else if (duration) {
+            subtitle = duration;
+        }
+        cell.detailTextLabel.text = sizeString;
+//        cell.isDownloadable = YES;
+//        cell.delegate = self;
+
+        NSURL *thumbnailURL = nil;
+        if ([item respondsToSelector:@selector(thumbnailURL)]) {
+            thumbnailURL = item.thumbnailURL;
+        }
+
+//        if (thumbnailURL) {
+//            dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0);
+//            dispatch_async(queue, ^{
+//                UIImage *img = [self getCachedImage:thumbnailURL];
+//                dispatch_async(dispatch_get_main_queue(), ^{
+//                    if (img) {
+//                        [cell setIcon:img];
+//                    }
+//                });
+//            });
+//        }
+
+    }
+    
+    return cell;
+}
+
+- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
+    id<VLCNetworkServerBrowserItem> item = self.serverBrowser.items[indexPath.row];
+
+    if (item.isContainer) {
+        VLCServerBrowsingTVTableViewController *browsingViewController = [[VLCServerBrowsingTVTableViewController alloc] initWithServerBrowser:[item containerBrowser]];
+        [self showViewController:browsingViewController sender:nil];
+    }
+}
+
+@end

+ 44 - 1
VLC for Apple TV/VLCServerListTVTableViewController.m

@@ -8,6 +8,7 @@
 
 #import "VLCServerListTVTableViewController.h"
 #import "VLCLocalNetworkServerTVCell.h"
+#import "VLCServerBrowsingTVTableViewController.h"
 
 @interface VLCServerListTVTableViewController ()
 
@@ -36,6 +37,14 @@
     return self.discoveryController.numberOfSections;
 }
 
+- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
+    VLCLocalServerDiscoveryController *discoverer = self.discoveryController;
+    if (discoverer.numberOfSections > 1 && [discoverer numberOfItemsInSection:section] > 0) {
+        return [self.discoveryController titleForSection:section];
+    }
+    return nil;
+}
+
 - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
     return [self.discoveryController numberOfItemsInSection:section];
 }
@@ -48,8 +57,42 @@
     return cell;
 }
 
+- (void)showWIP:(NSString *)todo {
+    UIAlertController *alertController = [UIAlertController alertControllerWithTitle:@"Work in Progress\nFeature not (yet) implemented."
+                                                                             message:todo
+                                                                      preferredStyle:UIAlertControllerStyleAlert];
+
+    [alertController addAction:[UIAlertAction actionWithTitle:@"Please fix this!"
+                                                        style:UIAlertActionStyleDefault
+                                                      handler:nil]];
+
+    [alertController addAction:[UIAlertAction actionWithTitle:@"Nevermind"
+                                                        style:UIAlertActionStyleCancel
+                                                      handler:nil]];
+    [self presentViewController:alertController animated:YES completion:nil];
+}
+
 - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
-    NSLog(@"%s",__PRETTY_FUNCTION__);
+
+    id<VLCLocalNetworkService> service = [self.discoveryController networkServiceForIndexPath:indexPath];
+    if ([service respondsToSelector:@selector(serverBrowser)]) {
+        id <VLCNetworkServerBrowser> browser = [service serverBrowser];
+        if (browser) {
+            VLCServerBrowsingTVTableViewController *browsingViewController = [[VLCServerBrowsingTVTableViewController alloc] initWithServerBrowser:browser];
+            [self showViewController:browsingViewController sender:nil];
+            return;
+        }
+    }
+
+    if ([service respondsToSelector:@selector(loginInformation)]) {
+        [self showWIP:@"Login"];
+        return;
+    }
+    if ([service respondsToSelector:@selector(directPlaybackURL)]) {
+        [self showWIP:@"Direct playback form URL"];
+        return;
+    }
+
 }
 
 #pragma mark - VLCLocalServerDiscoveryController

+ 6 - 0
VLC for iOS.xcodeproj/project.pbxproj

@@ -318,6 +318,7 @@
 		DDB7C6A41BAEB28200E6570E /* WKInterfaceController+VLCConnectionAlert.m in Sources */ = {isa = PBXBuildFile; fileRef = DD9FBE761BAD6BB600FFE77A /* WKInterfaceController+VLCConnectionAlert.m */; };
 		DDB959421AFBB30500BB8CFF /* MappingModel_2_5_to_2_6.xcmappingmodel in Sources */ = {isa = PBXBuildFile; fileRef = DDB959411AFBB30500BB8CFF /* MappingModel_2_5_to_2_6.xcmappingmodel */; };
 		DDC10BE41AEE8EA700890DC3 /* VLCTimeNavigationTitleView.m in Sources */ = {isa = PBXBuildFile; fileRef = DDC10BE31AEE8EA700890DC3 /* VLCTimeNavigationTitleView.m */; };
+		DDDEA6AF1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = DDDEA6AE1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.m */; };
 		DDEAECBE1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m in Sources */ = {isa = PBXBuildFile; fileRef = DDEAECBD1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m */; };
 		DDEAECBF1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m in Sources */ = {isa = PBXBuildFile; fileRef = DDEAECBD1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m */; };
 		DDEAECC61BDEC79D00756C83 /* VLCLocalNetworkServiceBrowserSAP.m in Sources */ = {isa = PBXBuildFile; fileRef = DDEAECC51BDEC79D00756C83 /* VLCLocalNetworkServiceBrowserSAP.m */; };
@@ -977,6 +978,8 @@
 		DDB959411AFBB30500BB8CFF /* MappingModel_2_5_to_2_6.xcmappingmodel */ = {isa = PBXFileReference; lastKnownFileType = wrapper.xcmappingmodel; name = MappingModel_2_5_to_2_6.xcmappingmodel; path = ImportedSources/MediaLibraryKit/MappingModel_2_5_to_2_6.xcmappingmodel; sourceTree = "<group>"; };
 		DDC10BE21AEE8EA700890DC3 /* VLCTimeNavigationTitleView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLCTimeNavigationTitleView.h; path = Sources/VLCTimeNavigationTitleView.h; sourceTree = SOURCE_ROOT; };
 		DDC10BE31AEE8EA700890DC3 /* VLCTimeNavigationTitleView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = VLCTimeNavigationTitleView.m; path = Sources/VLCTimeNavigationTitleView.m; sourceTree = SOURCE_ROOT; };
+		DDDEA6AD1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = VLCServerBrowsingTVTableViewController.h; sourceTree = "<group>"; };
+		DDDEA6AE1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = VLCServerBrowsingTVTableViewController.m; sourceTree = "<group>"; };
 		DDE1BCE51B676B8800A4B9CE /* tr */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = tr; path = tr.lproj/Localizable.strings; sourceTree = "<group>"; };
 		DDEAECBC1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = VLCNetworkServerLoginInformation.h; sourceTree = "<group>"; };
 		DDEAECBD1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = VLCNetworkServerLoginInformation.m; sourceTree = "<group>"; };
@@ -1804,6 +1807,8 @@
 				7DC71D1F1BC83058001FACAA /* VLCAppSharesTVViewController.m */,
 				DDEAECEB1BDFE99200756C83 /* VLCServerListTVTableViewController.h */,
 				DDEAECEC1BDFE99200756C83 /* VLCServerListTVTableViewController.m */,
+				DDDEA6AD1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.h */,
+				DDDEA6AE1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.m */,
 				7DC71D231BC830A5001FACAA /* VLCLocalNetworkTVViewController.h */,
 				7DC71D241BC830A5001FACAA /* VLCLocalNetworkTVViewController.m */,
 				7D7EF3D71BD56B5900CD4CEE /* VLCOpenNetworkStreamTVViewController.h */,
@@ -2621,6 +2626,7 @@
 				DDEAECBF1BDEBF6700756C83 /* VLCNetworkServerLoginInformation.m in Sources */,
 				DD3EFF381BDEBCE500B68579 /* VLCLocalNetworkServiceNetService.m in Sources */,
 				DDEAECF71BDFEB0200756C83 /* VLCLocalNetworkServerTVCell.m in Sources */,
+				DDDEA6AF1BE027FA000BB7A2 /* VLCServerBrowsingTVTableViewController.m in Sources */,
 				DD3EFF461BDEBCE500B68579 /* VLCLocalNetworkServiceBrowserManualConnect.m in Sources */,
 				DD3EFF4A1BDEBCE500B68579 /* VLCLocalNetworkServiceBrowserPlex.m in Sources */,
 				7DEC8BED1BD68D6A006E1093 /* VLCAboutTVViewController.m in Sources */,