Да, я заменил все на ваш скрипт, и я использую Unity 5.5.0f3
аюсь передавать потоковое видео из одного приложения в другое. В настоящее время у меня есть 2 приложения. где приложение 1 является сервером / отправителем, а приложение 2 является клиентом / получателем. В приложении 1 я успешно отправляю байты видео клиенту. и на стороне клиента я также получаю все байты. Я использую сокеты и TCP. Проблема, с которой я сталкиваюсь, заключается в том, что, когда я получаю байты видео и присваиваю их текстуре необработанного изображения, изображение на текстуре выглядит слишком сильно увеличенным, и оно становится таким пикселированным.
Обновленное изображение
и это то, что я получаю на клиенте.
Это первая проблема, однако в настоящее время я тестирую с рабочего стола на другой, моя цель - передать IPAD на рабочий стол, и когда я это делаю, это происходит очень медленно и убивает приложение как на ipad, так и на рабочем столе.
Некоторые проблемы, которые я пробовал до сих пор.
1: я думаю, что это происходит, потому что у меня есть 2 разных разрешения, потому что я передаю с ipad на рабочий стол
2: Текстурное изображение слишком большое, я вывожу его, и оно возвращает 630. Я попытался изменить его размер с помощью Unity Texture2D.resize, но я получил серую текстуру, потому что функция устанавливает пиксели как неопознанные
3: я использовал другие библиотеки для изменения размера текстур, и я получаю то, что хочу, но после 12 кадров rawimage начинает мерцать между видео и "?" текстуру так много, что она зависает как в приложении (ipad, так и на рабочем столе)
4: я полагаю, что способ, которым я читаю текстуру, вызывает проблему, потому что я использую и функции Setpixels и Getpixels, и они тяжелы.
Мой код: Сервер / Сторона отправителя:
using UnityEngine;
using System.Collections;
using System.IO;
using UnityEngine.UI;
using System;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using System.Collections.Generic;
public class Connecting : MonoBehaviour
{
WebCamTexture webCam;
public RawImage myImage;
Texture2D currentTexture;
private TcpListener listner;
private const int port = 8010;
private bool stop = false;
private List<TcpClient> clients = new List<TcpClient>();
private void Start()
{
// Open the Camera on the desired device, in my case IPAD pro
webCam = new WebCamTexture();
// Get all devices , front and back camera
webCam.deviceName = WebCamTexture.devices[WebCamTexture.devices.Length - 1].name;
// request the lowest width and heigh possible
webCam.requestedHeight = 10;
webCam.requestedWidth = 10;
webCam.Play();
/
currentTexture = new Texture2D(webCam.width, webCam.height);
// Connect to the server
listner = new TcpListener(port);
listner.Start();
// Create Seperate thread for requesting from client
Loom.RunAsync(() => {
while (!stop)
{
// Wait for client approval
var client = listner.AcceptTcpClient();
// We are connected
clients.Add(client);
Loom.RunAsync(() =>
{
while (!stop)
{
var stremReader = client.GetStream();
if (stremReader.CanRead)
{
// we need storage for data
using (var messageData = new MemoryStream())
{
Byte[] buffer = new Byte[client.ReceiveBufferSize];
while (stremReader.DataAvailable)
{
int bytesRead = stremReader.Read(buffer, 0, buffer.Length);
if (bytesRead == 0)
break;
// Writes to the data storage
messageData.Write(buffer, 0, bytesRead);
}
if (messageData.Length > 0)
{
// send pngImage
SendPng(client);
}
}
}
}
});
}
});
}
private void Update()
{
myImage.texture = webCam;
}
// Read video pixels and send them to the client
private void SendPng (TcpClient client)
{
Loom.QueueOnMainThread(() =>
{
// Get the webcame texture pixels
currentTexture.SetPixels(webCam.GetPixels());
var pngBytes = currentTexture.EncodeToPNG();
// Want to Write
var stream = client.GetStream();
// Write the image bytes
stream.Write(pngBytes, 0, pngBytes.Length);
// send it
stream.Flush();
});
}
// stop everything
private void OnApplicationQuit()
{
webCam.Stop();
stop = true;
listner.Stop();
foreach (TcpClient c in clients)
c.Close();
}
}
Клиент / получатель
using UnityEngine;
using System.Collections;
using UnityEngine.UI;
using System.Net.Sockets;
using System.Net;
using System.IO;
public class reciver : MonoBehaviour
{
public RawImage image;
const int port = 8010;
public string IP = "";
TcpClient client;
Texture2D tex;
// Use this for initialization
void Start()
{
client = new TcpClient();
// connect to server
Loom.RunAsync(() => {
Debug.LogWarning("Connecting to server...");
// if on desktop
client.Connect(IPAddress.Loopback, port);
// if using the IPAD
//client.Connect(IPAddress.Parse(IP), port);
Debug.LogWarning("Connected!");
});
}
float lastTimeRequestedTex = 0;
// Update is called once per frame
void Update()
{
//if (Time.time - lastTimeRequestedTex < 0.1f)
// return;
lastTimeRequestedTex = Time.time;
if (!client.Connected)
return;
// Send 1 byte to server
var serverStream = client.GetStream();
// request the texture from the server
if (serverStream.CanWrite)
{
// Texture request
// send request
serverStream.WriteByte(byte.MaxValue);
serverStream.Flush();
Debug.Log("Succesfully send 1 byte");
}
if (serverStream.CanRead)
{
// Read the bytes
using (var writer = new MemoryStream())
{
var readBuffer = new byte[client.ReceiveBufferSize];
while (serverStream.DataAvailable)
{
int numberOfBytesRead = serverStream.Read(readBuffer, 0, readBuffer.Length);
if (numberOfBytesRead <= 0)
{
break;
}
writer.Write(readBuffer, 0, numberOfBytesRead);
}
if (writer.Length > 0)
{
// got whole data in writer
// Get the bytes and apply them to the texture
var tex = new Texture2D(0, 0);
tex.LoadImage(writer.ToArray());
Debug.Log(tex.width + tex.height);
image.texture = tex;
}
}
}
}
void OnApplicationQuit()
{
Debug.LogWarning("OnApplicationQuit");
client.Close();
}
}