iPhone TCP / IP套接字服务器/客户端程序(iPhone TCP/IP Socket S

2019-07-18 08:40发布

我已经读了很多关于这个网站关于这个问题的问题,但他们并没有安静回答我的问题。 如果你不能###关于我的目标或背景跳到问题。

我的目标

就是把它构建一个可以在Mac OS X 10.4以上运行,后来的服务器,端口到Windows XP / Vista的(不知道如何做到这一点呢,但是这是一个问题为更高版本)。

然后让iPhone是能够看到正在运行的服务器(通过WiFi)的计算机名客户端。 那么iPhone的用户可以选择计算机名连接到该计算机上的服务器。

之后,他们可以发送简单的文本消息给对方。 例如,iPhone发送“敲敲”和服务器响应“谁在那里?”。 或一个简单的客户端:“平”,服务器响应“傍”会做得很好。

背景

我已经在过去插座的工作,但只有在Visual Basic 6与WINSOCKET.dll这是非常容易地创建一个TCP / IP服务器。

server.host = localhost;
server.port = 12203;
server.listen(); 

随着客户端我只需要做到以下几点进行连接。

client.connect(localhost, 12203);

有一些回调可像连接,关闭,DataArrival事件,等等,我可以用做任何事情我想要的。

也许对于iPhone有它编写的库,但它是那么难自己创建这个简单的应用程序? 做一些研究之后,我明白,我在CFNetwork的,CFHost,CFSocket,CFStream面积看。

是否有任何人能指导我的教程或张贴,你必须在iPhone上的两个按钮的代码。 [启动服务器]和[连接到服务器],其中第一个将启动一个特定端口上的TCP / IP服务器和第二连接到它。

一个连接已经完成之后,也许也该代码发送一个简单的“Ping'消息发送给服务器后,服务器收到此回应一个” Pong'消息发送给客户端。

那真的是有帮助的。 但是,也许我要求太多到这里。

Answer 1:

本教程创建一个聊天示例应用程序工作得很好,是非常简单的(任何iphone小白,像我这样,可以使其工作,即使是在模拟模式它连接到外部插槽服务器)。

我适应它讲我的socket服务器,它就像一个魅力。 这是测试代码,所以有与有始有终没有真正的关注。 它仅发送一个消息(您的登录ID)和接收应答返回,它显示在控制台中。

//
//  ViewController.m
//  zdelSocketTest01a
//
//

#import "ViewController.h"



@implementation ViewController
@synthesize inputNameField;
@synthesize joinView;

- (void)initNetworkCommunication {

    uint portNo = 5555;
    CFReadStreamRef readStream;
    CFWriteStreamRef writeStream;
    CFStreamCreatePairWithSocketToHost(NULL, (CFStringRef)@"227.3.4.56", portNo, &readStream, &writeStream);
    inputStream = (__bridge NSInputStream *)readStream;
    outputStream = (__bridge NSOutputStream *)writeStream;

    [inputStream setDelegate:self];
    [outputStream setDelegate:self];

    [inputStream scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    [outputStream scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    [inputStream open];
    [outputStream open];
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Release any cached data, images, etc that aren't in use.
}

#pragma mark - View lifecycle

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.
    [self initNetworkCommunication];
    messages = [[NSMutableArray alloc] init];
}

- (void)viewDidUnload
{
    [self setInputNameField:nil];
    [self setJoinView:nil];
    [self setJoinView:nil];
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
}

- (void)viewDidAppear:(BOOL)animated
{
    [super viewDidAppear:animated];
}

- (void)viewWillDisappear:(BOOL)animated
{
    [super viewWillDisappear:animated];
}

- (void)viewDidDisappear:(BOOL)animated
{
    [super viewDidDisappear:animated];
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    // Return YES for supported orientations
    return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}

- (IBAction)joinChat:(id)sender {

    NSString *response  = [NSString stringWithFormat:@"logon,%@", inputNameField.text];
    NSData *data = [[NSData alloc] initWithData:[response dataUsingEncoding:NSASCIIStringEncoding]];
    [outputStream write:[data bytes] maxLength:[data length]];

}
/*
 - (void)stream:(NSStream *)theStream handleEvent:(NSStreamEvent)streamEvent {
 NSLog(@"stream event %i", streamEvent);
 }
 */

- (void)stream:(NSStream *)theStream handleEvent:(NSStreamEvent)streamEvent {
    typedef enum {
        NSStreamEventNone = 0,
        NSStreamEventOpenCompleted = 1 << 0,
        NSStreamEventHasBytesAvailable = 1 << 1,
        NSStreamEventHasSpaceAvailable = 1 << 2,
        NSStreamEventErrorOccurred = 1 << 3,
        NSStreamEventEndEncountered = 1 << 4
    };
    uint8_t buffer[1024];
    int len;

    switch (streamEvent) {

        case NSStreamEventOpenCompleted:
            NSLog(@"Stream opened now");
            break;
        case NSStreamEventHasBytesAvailable:
            NSLog(@"has bytes");
            if (theStream == inputStream) {
                while ([inputStream hasBytesAvailable]) {
                    len = [inputStream read:buffer maxLength:sizeof(buffer)];
                    if (len > 0) {

                        NSString *output = [[NSString alloc] initWithBytes:buffer length:len encoding:NSASCIIStringEncoding];

                        if (nil != output) {
                            NSLog(@"server said: %@", output);
                        }
                    }
                }
            } else {
                NSLog(@"it is NOT theStream == inputStream");
            }
            break;
        case NSStreamEventHasSpaceAvailable:
            NSLog(@"Stream has space available now");
            break;


        case NSStreamEventErrorOccurred:
            NSLog(@"Can not connect to the host!");
            break;


        case NSStreamEventEndEncountered:

            [theStream close];
            [theStream removeFromRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];

            break;

        default:
            NSLog(@"Unknown event %i", streamEvent);
    }

}
/*
 - (void) messageReceived:(NSString *)message {

 [messages addObject:message];
 [self.tView reloadData];

 }
 */

@end

您ViewController.h文件将包含

#import <UIKit/UIKit.h>

@interface ViewController : UIViewController <NSStreamDelegate>
@property (weak, nonatomic) IBOutlet UITextField *inputNameField;
@property (weak, nonatomic) IBOutlet UIView *joinView;
- (IBAction)joinChat:(id)sender;


@end
NSInputStream *inputStream;
NSOutputStream *outputStream;
NSMutableArray * messages;

菜鸟ONLY:你必须通过按Ctrl并拖动对象到代码窗口中的链接按钮和文本字段。 当你这样做时,上面的属性将自动创建。 检查这个视频教程 ,如果你难倒

菜鸟只有2:在Xcode的控制台窗格中该插槽输出。 在您的Xcode窗口的右上角,单击隐藏或显示DEBUG区域(如果有必要寻求帮助)。

构建和测试(模拟器和设备)上2GB内存在MacBook,使用的xcode 4.2雪豹。



Answer 2:

我建议如下: 可可异步套接字

还有在网站上一个基本的例子项目让你开始。 我有很好的成功与框架内工作。



Answer 3:

我希望你会希望你的服务器已经启动,然后你只需要一个“连接到服务器”按钮,然后你的“平”。 否则,您必须对您的服务器框中一个单独的进程,其响应“启动服务器”的消息,并启动服务器。



文章来源: iPhone TCP/IP Socket Server/Client Program