Introduction to Flash NetConnection/NetStream
- Author:柳大·Poechant(钟超)
- Email:zhongchao.ustc#gmail.com(# -> @)
- Blog:Blog.CSDN.net/Poechant
- Date:May 28th,2012
由于目前在研究 RTMFP 协议,及 OpenRTMFP/Cumulus 开源项目,所以不可避免的要对 Flash 客户端的 NetConnection/NetStream 有所了解。这里把它们相关的 API 做个简要介绍,并简单介绍其基本原理。具体涉及到 Flash Media Server 的部分,请参阅我发布的系列博文《OpenRTMFP/Cumulus Primer》(截至2012年5月29日,该系列博文仍在持续更新中)。
1 Introduction to NetConnection
NetConnection 就是 Flash 客户端与服务器之间进行双工传输的管道。一般来说,充当服务器角色的是 Flash Media Server(一般简称 FMS),比如 Adobe Cirrus、OpenRTMFP/Cumulus 等。当然,也可以从本地文件系统或 Web 服务器中播放视频和 MP3 文件,而不需要特殊的 FMS。
1.1 Overview
使用 NetConnection 类时,请考虑 Flash Player 安全模型,官方文档有如下描述:
如果执行调用的 SWF 文件在网络沙箱中并且要加载的声音文件是本地的,则不允许加载和播放音
频或视频文件。默认情况下,若执行调用的 SWF 是本地的并且试图加载和播放远程文件,则不允
许加载和播放音频或视频文件。 用户必须授予明确许可以允许该操作。
也就是说,SWF 文件和所欲播放的文件,在不同的位置(本地或远程服务器),则都不允许。
1.2 属性详解
1.2.1 回调谁的方法?client
用client
属性来指定所建立的管道(NetConnection)被远程服务器回调时,方法的所属对象。举例如下:
…
nc.client = someGuy;
…
那么之后这个 NetConnection 的远程服务器上回调someFunction
方法时,就是someGuy
这个对象的someFunction
成员方法。其 prototype 为:
public function get client():Object
public function set client(value:Object):void
可能抛出的错误:
TypeError — 必须将 client 属性设置为非空对象。
1.2.2 什么编码方式?
1.2.2.1 默认编码方式defaultObjectEncoding
用defaultObjectEncoding
属性来指定所建立的管道的编码/解码方式,其实就是数据的序列化(对象到二进制)及反序列化(二进制到对象)的方式,在 Flash 中有 ActionScript 3.0 格式 (ObjectEncoding.AMF3) 或 ActionScript 1.0 和 ActionScript 2.0 格式 (ObjectEncoding.AMF0)。
默认值是 ObjectEncoding.AMF3。 更改 NetConnection.defaultObjectEncoding 不会影响现有 NetConnection 实例,只会影响随后创建的实例。
若要单独设置某个对象的编码(而非设置整个 SWF 文件的对象编码),请改为设置 NetConnection 对象的 objectEncoding 属性。请看 1.2.3。
其 prototype 为:
public static function get defaultObjectEncoding():uint
public function set defaultObjectEncoding(value:uint):void
1.2.2.2 对象编码方式objectEncoding
用objectEncoding
。其 prototype 为:
public function get objectEncoding():uint
public function set objectEncoding(value:uint):void
可能抛出的错误:
ReferenceError — 连接 NetConnection 实例时,会尝试设置 objectEncoding 属性值。
ArgumentError — 此属性被设置为 ObjectEncoding.AMF0 或 ObjectEncoding.AMF3 以外的值。
1.3 方法详解
1.3.1?connect()
public function connect(command:String,... arguments):void
NetConnection
支持:RTMP、RTMFP。形如:
rtmfp://127.0.0.1:1935
如果传递的command
参数为null
,则表示连接本地。
1.3.2?call()
NetConnection
调用 FMS 上的命令,在使用这个方法之前,必须先让 Flash 客户端与 FMS 建立连接,即调用connection()
方法。
其 prototype 为:
public function call(command:String,responder:Responder,... arguments):void
主要参数含义:
-
responder:Responder
?— 可选对象,用于处理服务器的返回值。 Responder 对象可以用两个定义的方法来处理返回的结果:result 和 status。 如果返回的结果为错误,则将调用 status;否则,将调用 result。Responder
对象可以处理与特定操作有关的错误,而NetConnection
对象则响应与连接状态有关的错误。
1.3.3?close()
prototype:
public function close():void
1.4 相关事件
在异步引发异常(即来自本机异步代码)时调度:
flash.events.AsyncErrorEvent
在出现输入或输出错误并导致网络操作失败时调度:
flash.events.IOErrorEvent
在 NetConnection 对象报告其状态或错误条件时调度。 netStatus 事件包含一个 info 属性,该属性是一个包含事件特定信息(例如,连接尝试成功还是失败)的信息对象:
flash.events.NetStatusEvent
若对 NetConnection.call() 的调用尝试连接到调用方安全沙箱外部的服务器,则进行调度:
flash.events.SecurityErrorEvent
2 Introduction to NetStream
NetStream 对象是 NetConnection 对象中的一个通道。发布者可以通过此通道可以使用 NetStream.publish() 发布流,订阅者可以使用 NetStream.play() 订阅发布的流并接收数据,发布者还可以通过调用 NetStream.send() 对所有订阅者发布其他信息。
2.1 Overview
2.2 属性详解
2.2.1 缓冲区中的数据描述bufferLength
数据当前存在于缓冲区中的秒数。
prototype:
public function get bufferLength():Number
2.2.2 缓冲区在播放前的缓冲值bufferTime
指定在开始显示流之前需要多长时间将消息存入缓冲区。 例如,若要确保流的最初 15 秒无中断播放,请将 bufferTime 设置为 15;Flash Player 将在把 15 秒的数据存入缓冲区后才开始播放该流。默认值是 0.1(十分之一秒)。
- 在播放录制流时,如果 bufferTime 为 0,Flash 会将其设置为较小的值(大约为 10 毫秒)。
- 播放实时流(例如,从播放列表中),则会永久保留此缓冲时间。 即,流的 bufferTime 始终为非零值。
prototype:
public function get bufferTime():Number
public function set bufferTime(value:Number):void
2.3.3 client
与NetConnection的
client`属性类似,用于指定在其上调用回调方法的对象。 默认对象为 this,将创建 NetStream 对象。 如果将 client 属性设置为另一个对象,则将对该对象调用回调方法。
2.3.4 objectEncoding
与NetConnection
的objectEncoding
类似。
2.3 方法详解
2.3.1 Constructor
创建可用于通过指定的 NetConnection 对象播放视频文件的流。
2.3.2?attachAudio
指定一个通过 NetStream 对象发送的音频流,这次先看 prototype:
public function attachAudio(microphone:Microphone):void
参数:
-
microphone:Microphone
?— 要传输的音频流的源。
要明确:
- 作为源传递的是 Microphone 对象;
-
attachAudio
方法用于 FMS。
- 此方法通常是由从客户端计算机向服务器发送实时音频(或包含音频的实时视频)的用户调用的。
- 可以通过指定的 Microphone 对象的 soundTransform 属性来控制此音频流的声音属性。
2.3.3?attachCamera
开始从摄像头捕获视频,如果将 theCamera 设置为 null,则会停止捕获操作。
prototype:
public function attachCamera(theCamera:Camera,snapshotMilliseconds:int = -1):void
arguments:
-
theCamera:Camera
?— 视频传输的源。 有效值为一个 Camera 对象(可开始捕获视频)和 null。 如果传递 null,则 Flash Player 停止捕获视频,并忽略发送的其它任何参数。
-
snapshotMilliseconds:int (default = -1)
?— 指定视频流是连续、单帧,还是用于创建延时拍摄的一系列单帧。
要明确:
- 在附加了视频源后,必须调用 NetStream.publish() 才能开始传输。
- 想要显示视频的订阅者必须调用 NetStream.play() 和 Video.attachCamera() 方法,才能在舞台上显示视频。
2.3.4?pause
?和?resume
public function pause():void
public function resume():void
如果当前流已暂停,则调用pause
无变化,调用resume
则继续。 如果当前流已在播,则调用resome
无变化,调用pause
则暂停。
2.3.5?publish
?和?play
public function publish(name:String = null,type:String = null):void
public function play(... arguments):void
发布者调用publish
,用以向订阅者发送音视频数据,且发布时要指定名称。订阅者调用play
,用以播放收到的音视频数据,且订阅时要指定名称。
-
publish
参数
-
name:String (default = null)
?— 标识该流的字符串。 如果传递 false,则发布操作将停止。 订阅此流的客户端必须在调用 NetStream.play() 时仍然传递此名称。 不必在流名称中包含文件扩展名。 流名称后面不要跟“/”。 例如,不要使用流名称“bolero/”。
-
type:String (default = null)
?— 指定如何发布该流的字符串。 有效值为“record”、“append”和“live”。 默认值为“live”。
-
play
参数
… arguments?— 要播放的视频文件的位置(作为 URLRequest 对象或字符串)。 您可以播放与 SWF 文件存储于同一目录中或存储于其子目录中的本地视频文件;但不能导航到更高级别的目录。
2.3.5.1?publish
:发布者专用
- 当 Flash Media Server 应用程序客户端调用 publish() 时,应用程序将收到 onPublish 事件。
- 应用程序必须在服务器端脚本中处理该事件。 当客户端停止发布时,应用程序将收到 onUnpublish 事件。
- 停止发布:标识该流的字符串。 如果传递 false,则发布操作将停止。
2.3.5.2?play
:订阅者专用
- 无法播放:如果无法找到视频文件,则会调度 netStatus 事件。
- 停止播放:若要停止当前播放的流,请使用 close() 方法。
2.3.7?receiveAudio
和receiveVideo
2.3.7.1?receiveAudio
:订阅者专用
receiveAudio
指定传入的音频是否在流上播放。 此方法仅可用于订阅了指定流的客户端,不可用于流的发布者。
receiveAudio
的 prototype:
public function receiveAudio(flag:Boolean):void
arguments:
- flag:Boolean — 指定传入音频是在流上播放 (true) 还是不播放 (false)。 默认值为 true。
您可以在调用 NetStream.play() 方法并真正开始接收流之前或之后,调用此方法。 例如,您可以将这些方法附加到某个按钮上,用户可以通过单击该按钮将传入的音频流静音或取消静音。
如果指定的流仅包含音频数据,则将 false 值传递给该方法可以阻止 NetStream.time 进一步递增。
2.3.7.2?receiveVideo
:订阅者专用
指定传入的音频是否将在流上播放。 此方法仅可用于订阅了指定流的客户端,不可用于流的发布者。
receiveVideo
的 prototype:
public function receiveVideo(flagOrFPS:*):void
arguments:
- flagOrFPS:* — 指定传入视频是在此流上播放 (true) 还是不播放 (false)。 默认值是 true。 也可以使用一个整数来指定传入视频的每秒帧速率。 如果未指定帧速率,则帧速率默认为录制的视频或所播放的实时视频的帧速率。
您可以在调用 NetStream.play() 方法并真正开始接收流之前或之后,调用此方法。 例如,您可以将这些方法附加到某个按钮上,用户可以通过按该按钮来显示或隐藏传入的视频流。
如果指定的流仅包含视频数据,则将 false 值传递给该方法可以阻止 NetStream.time 进一步递增。
2.3.7?send
:发布者专用
- 在发布的流上向所有订阅客户端发送一条消息。 此方法仅供指定的流的发布者使用,并与 Flash Media Server 一起使用。
- 若要处理并响应该消息,请在 NetStream 对象上创建一个处理函数,例如,ns.HandlerName。
- Flash Player 不对方法或方法的数据、对象原型变量或不可枚举的变量进行序列化处理。 对于显示对象,Flash Player 仅对路径而不对数据进行序列化处理。
2.3.7.1 为什么用send
?
您可以调用 send() 方法,将数据关键帧添加到发送给 Flash Media Server 的实时流中。 数据关键帧是发布者添加到实时流中的消息。 通常,在从摄像头和麦克风为实时流捕获数据之前,使用数据关键帧将元数据添加到该流中。 在发布实时流期间,发布者可以随时添加数据关键帧。 只要发布者连接到服务器上,就会将数据关键帧保存在服务器的内存中。
2.3.7.2 订阅者什么时候收到关键帧?
如果客户端是在添加数据关键帧之前订阅实时流的,则会在添加后立即收到该关键帧。 如果客户端是在添加数据关键帧之后订阅实时流的,则会在订阅时收到该关键帧。
2.3.7.3 怎么用?
prototype:
public function send(handlerName:String,... arguments):void
若要将元数据关键帧添加到发送给 Flash Media Server 的实时流中,请使用 @setDataFrame 作为处理函数名称,后跟两个其它参数,例如:
var ns:NetStream = new NetStream(nc);
ns.send("@setDataFrame","onMetaData",metaData);
- 第一个参数:服务器端的处理函数。
- 第二个参数:客户端被回调的函数。
- 第三个参数开始:任意数据。
2.3.8?close
停止播放流上的所有数据,将 time 属性设置为 0,并使该流可用于其它用途。 此方法还会删除通过 HTTP 下载的视频文件的本地副本。 虽然 Flash Player 删除了它所创建的文件的本地副本,但可能会在浏览器的缓存目录中永久保留一个副本。 如果必须完全禁止缓存视频文件或在本地进行存储,请使用 Flash Media Server。
- 如果从发布流中调用 close(),该流将停止发布,发布者现在可以将该流用于其它用途。 订阅者不再接收在该流中发布的任何内容,因为该流已停止发布。
- 如果从订阅流中调用 close(),该流将停止为订阅者播放,订阅者现在可以将该流用于其它用途。 其它订阅者不受影响。
- 您可以让订阅流停止播放,而无需使用 flash.net.NetStream.play(false) 关闭该流或更改流类型。
2.4 相关事件
在异步引发异常(即来自本机异步代码)时调度。 当服务器调用客户端上未定义的方法时调度此事件。
flash.events.AsyncErrorEvent
在出现输入或输出错误并导致网络操作失败时调度。
flash.events.IOErrorEvent
在 NetStream 对象报告其状态或错误条件时调度。 netStatus 事件包含一个 info 属性,该属性是一个包含有关事件特定信息(例如连接尝试成功还是失败)的信息对象。
flash.events.NetStatusEvent
在播放视频文件期间到达嵌入的提示点时调用。
onCuePoint
在 Flash Player 接收所播放的视频文件中嵌入的描述性信息时调度。
onMetaData
在 NetStream 对象完全播放完流后调度。 此处理函数将返回信息对象,这些信息对象提供 netStatus 事件返回的信息之外的其它信息。
onPlayStatus
3 Reference
- http://livedocs.adobe.com/flash/9.0_cn/ActionScriptLangRefV3/flash/net/NetConnection.html
- http://livedocs.adobe.com/flash/9.0_cn/ActionScriptLangRefV3/flash/net/NetStream.html
-
转载请注明来自柳大的CSDN博客:Blog.CSDN.net/Poechant
-