mirror of https://github.com/ArduPilot/ardupilot
211 lines
5.9 KiB
C#
211 lines
5.9 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Text;
|
|
using System.Net;
|
|
using System.IO;
|
|
using System.Drawing;
|
|
using System.Threading;
|
|
using log4net;
|
|
|
|
namespace ArdupilotMega.Utilities
|
|
{
|
|
public class CaptureMJPEG
|
|
{
|
|
private static readonly ILog log =
|
|
LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
|
|
|
|
static Thread asyncthread;
|
|
static bool running = false;
|
|
public static string URL = @"http://127.0.0.1:56781/map.jpg";
|
|
|
|
public static event EventHandler OnNewImage;
|
|
|
|
static DateTime lastimage = DateTime.Now;
|
|
static int fps = 0;
|
|
|
|
public static void runAsync()
|
|
{
|
|
while (asyncthread != null && asyncthread.IsAlive)
|
|
{
|
|
running = false;
|
|
}
|
|
|
|
asyncthread = new Thread(new ThreadStart(getUrl))
|
|
{
|
|
IsBackground = true,
|
|
Priority = ThreadPriority.BelowNormal,
|
|
Name = "mjpg stream reader"
|
|
};
|
|
|
|
asyncthread.Start();
|
|
}
|
|
|
|
public static void Stop()
|
|
{
|
|
running = false;
|
|
}
|
|
|
|
public static string ReadLine(BinaryReader br)
|
|
{
|
|
StringBuilder sb = new StringBuilder();
|
|
|
|
while (true) {
|
|
byte by = br.ReadByte();
|
|
sb.Append((char)by);
|
|
if (by == '\n')
|
|
break;
|
|
}
|
|
|
|
sb = sb.Replace("\r\n", "");
|
|
|
|
return sb.ToString();
|
|
}
|
|
|
|
static void getUrl()
|
|
{
|
|
|
|
running = true;
|
|
|
|
Bitmap frame = new Bitmap(640, 480);
|
|
|
|
// Create a request using a URL that can receive a post.
|
|
WebRequest request = HttpWebRequest.Create(URL);
|
|
// Set the Method property of the request to POST.
|
|
request.Method = "GET";
|
|
|
|
((HttpWebRequest)request).AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate;
|
|
|
|
request.Headers.Add("Accept-Encoding", "gzip,deflate");
|
|
|
|
// Get the response.
|
|
WebResponse response = request.GetResponse();
|
|
// Display the status.
|
|
log.Debug(((HttpWebResponse)response).StatusDescription);
|
|
// Get the stream containing content returned by the server.
|
|
Stream dataStream = response.GetResponseStream();
|
|
|
|
BinaryReader br = new BinaryReader(dataStream);
|
|
|
|
// get boundary header
|
|
|
|
string mpheader = response.Headers["Content-Type"];
|
|
if (mpheader.IndexOf("boundary=") == -1) {
|
|
ReadLine(br); // this is a blank line
|
|
string line = "proxyline";
|
|
while (line.Length > 2)
|
|
{
|
|
line = ReadLine(br);
|
|
if (line.StartsWith("--")) {
|
|
mpheader = line;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
int startboundary = mpheader.IndexOf("boundary=") + 9;
|
|
int endboundary = mpheader.Length;
|
|
|
|
mpheader = mpheader.Substring(startboundary, endboundary - startboundary);
|
|
}
|
|
|
|
dataStream.ReadTimeout = 30000; // 30 seconds
|
|
br.BaseStream.ReadTimeout = 30000;
|
|
|
|
while (running)
|
|
{
|
|
try
|
|
{
|
|
// get the multipart start header
|
|
int length = int.Parse(getHeader(br)["Content-Length"]);
|
|
|
|
// read boundary header
|
|
if (length > 0)
|
|
{
|
|
byte[] buf1 = new byte[length];
|
|
|
|
dataStream.ReadTimeout = 3000;
|
|
|
|
int offset = 0;
|
|
int len = 0;
|
|
|
|
while ((len = br.Read(buf1, offset, length)) > 0)
|
|
{
|
|
offset += len;
|
|
length -= len;
|
|
|
|
}
|
|
/*
|
|
BinaryWriter sw = new BinaryWriter(File.OpenWrite("test.jpg"));
|
|
|
|
sw.Write(buf1,0,buf1.Length);
|
|
|
|
sw.Close();
|
|
*/
|
|
try
|
|
{
|
|
|
|
frame = new Bitmap(new MemoryStream(buf1));
|
|
|
|
}
|
|
catch { }
|
|
|
|
fps++;
|
|
|
|
if (lastimage.Second != DateTime.Now.Second)
|
|
{
|
|
Console.WriteLine("MJPEG " + fps);
|
|
fps = 0;
|
|
lastimage = DateTime.Now;
|
|
}
|
|
|
|
if (OnNewImage != null)
|
|
OnNewImage(frame, new EventArgs());
|
|
}
|
|
|
|
// blank line at end of data
|
|
ReadLine(br);
|
|
}
|
|
catch (Exception ex) { log.Info(ex); break; }
|
|
}
|
|
|
|
// clear last image
|
|
if (OnNewImage != null)
|
|
OnNewImage(null, new EventArgs());
|
|
|
|
dataStream.Close();
|
|
response.Close();
|
|
|
|
running = false;
|
|
}
|
|
|
|
static void getUrlRTSP()
|
|
{
|
|
|
|
|
|
}
|
|
|
|
static Dictionary<string, string> getHeader(BinaryReader stream)
|
|
{
|
|
Dictionary<string, string> answer = new Dictionary<string, string>();
|
|
|
|
string line;
|
|
|
|
do
|
|
{
|
|
line = ReadLine(stream);
|
|
|
|
string[] items = line.Split(new char[] { ':' }, StringSplitOptions.RemoveEmptyEntries);
|
|
|
|
|
|
if (items.Length == 2)
|
|
answer.Add(items[0].Trim(), items[1].Trim());
|
|
|
|
} while (line != "");
|
|
|
|
return answer;
|
|
}
|
|
|
|
}
|
|
} |