前一段时间给IP摄像头和USB摄像头加入RTMP推流支持,支持将音视频推送到直播平台做直播。甚至YouTube也能推过去,前提是你要有个好梯子😀就能实现上图的效果,网络状况好的时候好不错,延迟10秒以上。如果是自己搭推流服务器(像nginx-rtmp或者srs)或者使用国内直播云延迟可以控制到1~2秒以内,使用Flash播放器甚至可以降低到1秒。

实现这个的目的是想直播FPV,即通过采集卡把图传接收的画面通过USB摄像头App显示在手机上的同时推送到直播平台😀苦于搬了房子附近没场子飞四轴,就没直播FPV改为家庭监控用了,自己架一个RTMP推流服务器,把旧手机放家里,运行IP摄像头App进行推流,即使家里没有公网IP也能查看家里情况。

IP摄像头和USB摄像头app共用RTMP推流的代码,视频使用H.264编码,音频使用AAC编码,支持根据网络状况自动调整码率,网络状况差时会自动丢帧,以保证延迟。当遇到网络切换或者连接暂时中断时,会自行重连,直到重新连接到推流服务器或者用户自行断开连接。该推流算法自行实现,经过二月份户外4G网络测试效果不错(消耗了近2G流量,刚好二月份移动送流量),即使在户外也能通过4G网络使用IP摄像头或者USB摄像头进行RTMP推流直播。

++++++++++++++++++++++++++++++



昨晚一个朋友把笔记本带过来了,说会自动关机。开机一看,发现散热器出风口没有风,然后机器就自动断电掉了,凭感觉,肯定散热器堵了。拆开散热器一看,如下图所示,正在吃饭的就别看了……

厚厚的灰尘堵住了散热鳍片

把那层像毛毯一样的灰去除之后,重新装上,散热孔出热风了,笔记本运行几个小时都没问题!

本代码用于远程重启水星无线路由一体机MD898N,硬件版本v2,固件版本0.8.0 1.0 v1003.0 Build 140216。

由于需要,需要用C#实现对这台机器的定时重启,根据chrome开发者工具的抓包结果,发现新版的固件不支持直接的base认证,但是原理一样,只是把用base64加密过的密码存在cookies中了(今年开始更新后的固件都是这种登录方式),发送http请求时候带上这个cookies即可通过认证!

具体代码如下:

	string passwd = "12345678";   // 路由器登录密码
	string routeIP = "192.168.1.1";  // 路由器IP
	byte[] bytes = Encoding.Default.GetBytes(passwd);
	string base64str = Convert.ToBase64String(bytes);
 
	string url = "http://" + ip + "/cgi?7";
	HttpWebRequest req = (HttpWebRequest)WebRequest.Create(url);
	req.Referer = "http://" + ip + "/";
	req.Method = "POST";
	req.CookieContainer = new CookieContainer();
	req.CookieContainer.Add(new Uri(url), new Cookie("Authorization", "Basic " + base64str));
	req.ContentType = "text/plain";
	string payload = "[ACT_REBOOT#0,0,0,0,0,0#0,0,0,0,0,0]0,0\r\n";  // 抓包后发现在请求中携带这个字符串即可让路由器重启
	byte[] pl = Encoding.UTF8.GetBytes(payload);
	req.ContentLength = pl.Length;
	Stream s = req.GetRequestStream();
	s.Write(pl, 0, pl.Length);
	s.Close();
	req.GetResponse();

在编写IP摄像头的Win8.1版和WP8版时遇到多线程调用StreamSocket发送数据时被意外Dispose,具体是StreamSocket是从StreamSocketListener接受连接后传过来的,然后用DataWriter发送一行数据后插入List供别的线程发送数据,问题就出现在别的线程发送数据时产生Dispose异常,可是奇怪的是我并没有将StreamSocket给Dispose,因为我还要用来传输数据呢!

问题解决:在插入List之前,将DataWriter先DetachStream,然后再给别的线程条用,这样就正常了!估计是DataWriter离开作用域后被销毁时顺便把StreamSocket给连带Dispose了,这个在使用StreamSocket时候得注意一下!当然如果用用DataReader的话也得DetachStream!

本想用Silverlight让IP摄像头支持IE,结果做出来后发现很卡顿,不流畅,按理说Silverlight性能应该比Flash好才对,找不出原因,果断用Flash插件代替,而且Flash在Win8的Modern版的IE也支持。编写后本地测试没问题,编译进IP摄像头后就不行了,一直报Error #2048安全沙箱冲突,所以就有了这篇文章以下的故事……

首先以下的内容是可以完完全全解决问题的,感谢这篇文章《完全解决AS3 中使用Socket的安全问题.》,我是网上搜了好久才找到这篇有用的,最后还看这篇《flash跨域策略文件crossdomain.xml配置详解》。依次看完这两篇就能解决这个问题。

IP摄像头里开辟了一个端口专门用于发送跨域策略文件,然后就解决这个问题了。不懂为什么在网站根目录下放策略文件不行(网络监控显示文件被Flash正常获取了),真觉得Adobe闲得蛋疼~~。所以如果你想要用IE通过外网访问IP摄像头,除了开辟IP摄像头的端口外,还要开辟IP摄像头的策略文件发送端口 8430(If you want to use IE to access IP Camera through external network, you must open up the  port 8430 to send policy file.) 。

完成以上步骤,就能用IE正常访问IP摄像头了!

View IP Camera from Modern IE