【问题标题】:Download files via FTP on Android在 Android 上通过 FTP 下载文件
【发布时间】:2017-04-14 12:27:44
【问题描述】:

我需要使用本地 FTP 协议在计算机(服务器)和我的 Android 设备(客户端)之间建立连接。这应该会下载要在 Android Unity 应用场景中使用的文件(图像、OBJ...)。我使用 WWW 类来创建这个连接,它在作为客户端在另一台计算机上运行的 Unity 播放器中运行良好。一旦我导出了与 Android apk 相同的场景,它就不起作用了(我确信 FTP 连接是稳定的并且它可以工作,因为我能够从浏览器访问文件)。有人知道我的代码中是否有其他方法或有问题在 Android Unity 应用程序上使用 FTP 协议? (客户端不需要任何授权,身份验证是匿名的)这是我用来在场景中下载一张图像并将其渲染为精灵的代码。

 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 using System.Net;
 using System.IO;

 public class ClientFTP : MonoBehaviour
 {
   public UnityEngine.UI.Image label;

   IEnumerator Start ()
   {
       // Create the connection and whait until it is established
       string url = ("ftp://192.168.10.11/prova.png");
       WWW ftpconnection = new WWW (url);
       yield return ftpconnection;
       // Download the image and render it as a texture
       Texture2D tex = new Texture2D (250, 192);
       ftpconnection.LoadImageIntoTexture (tex);
       // Assign the texture to a new sprite
       Sprite s = Sprite.Create (tex, new Rect (0, 0, 250f, 192f), new Vector2 (0.5f, 0.5f), 300);
       label.preserveAspect = true;
       label.sprite = s;

    }
 }

【问题讨论】:

  • 好的,谢谢!现在可以了

标签: android unity3d web ftp client-server


【解决方案1】:

如果您不需要凭据来访问文件,为什么要使用 FTP?您可以将文件放在您的服务器中,然后使用WWWUnityWebRequest API 访问它们。

为了回答您的 FTP 问题,WWW 不适合与 FTP 协议一起使用。这就是FtpWebRequest API 的用途。

以下是FtpWebRequest 的示例。

private byte[] downloadWithFTP(string ftpUrl, string savePath = "", string userName = "", string password = "")
{
    FtpWebRequest request = (FtpWebRequest)WebRequest.Create(new Uri(ftpUrl));
    //request.Proxy = null;

    request.UsePassive = true;
    request.UseBinary = true;
    request.KeepAlive = true;

    //If username or password is NOT null then use Credential
    if (!string.IsNullOrEmpty(userName) && !string.IsNullOrEmpty(password))
    {
        request.Credentials = new NetworkCredential(userName, password);
    }

    request.Method = WebRequestMethods.Ftp.DownloadFile;

    //If savePath is NOT null, we want to save the file to path
    //If path is null, we just want to return the file as array
    if (!string.IsNullOrEmpty(savePath))
    {
        downloadAndSave(request.GetResponse(), savePath);
        return null;
    }
    else
    {
        return downloadAsbyteArray(request.GetResponse());
    }
}

byte[] downloadAsbyteArray(WebResponse request)
{
    using (Stream input = request.GetResponseStream())
    {
        byte[] buffer = new byte[16 * 1024];
        using (MemoryStream ms = new MemoryStream())
        {
            int read;
            while (input.CanRead && (read = input.Read(buffer, 0, buffer.Length)) > 0)
            {
                ms.Write(buffer, 0, read);
            }
            return ms.ToArray();
        }
    }
}

void downloadAndSave(WebResponse request, string savePath)
{
    Stream reader = request.GetResponseStream();

    //Create Directory if it does not exist
    if (!Directory.Exists(Path.GetDirectoryName(savePath)))
    {
        Directory.CreateDirectory(Path.GetDirectoryName(savePath));
    }

    FileStream fileStream = new FileStream(savePath, FileMode.Create);


    int bytesRead = 0;
    byte[] buffer = new byte[2048];

    while (true)
    {
        bytesRead = reader.Read(buffer, 0, buffer.Length);

        if (bytesRead == 0)
            break;

        fileStream.Write(buffer, 0, bytesRead);
    }
    fileStream.Close();
}

用法

下载并保存(无凭据)

string path = Path.Combine(Application.persistentDataPath, "FTP Files");
path = Path.Combine(path, "data.png");
downloadWithFTP("ftp://yourUrl.com/yourFile", path);

下载并保存(使用凭证)

string path = Path.Combine(Application.persistentDataPath, "FTP Files");
path = Path.Combine(path, "data.png");
downloadWithFTP("ftp://yourUrl.com/yourFile", path, "UserName", "Password");

仅下载(无凭据)

string path = Path.Combine(Application.persistentDataPath, "FTP Files");
path = Path.Combine(path, "data.png");
byte[] yourImage = downloadWithFTP("ftp://yourUrl.com/yourFile", "");

//Convert to Sprite
Texture2D tex = new Texture2D(250, 192);
tex.LoadImage(yourImage);
Sprite s = Sprite.Create(tex, new Rect(0, 0, texture2D.width, texture2D.height), new Vector2(0.5f, 0.5f));

仅下载(使用凭据)

string path = Path.Combine(Application.persistentDataPath, "FTP Files");
path = Path.Combine(path, "data.png");
byte[] yourImage = downloadWithFTP("ftp://yourUrl.com/yourFile", "", "UserName", "Password");

//Convert to Sprite
Texture2D tex = new Texture2D(250, 192);
tex.LoadImage(yourImage);
Sprite s = Sprite.Create(tex, new Rect(0, 0, texture2D.width, texture2D.height), new Vector2(0.5f, 0.5f));

【讨论】:

  • 我想制作加载栏,这段代码在主线程中运行并阻止 UI 更新。如何重构它使其不在主线程中运行?
  • @GuardFromUA 在我的other 帖子中使用UnityThread.executeInUpdate
【解决方案2】:
public boolean ftpDownloadVideo() {

String desFilePath = (Environment.getExternalStoragePublicDirectory(DIRECTORY_DOWNLOADS)).toString();    ///xet trong moi truong SD card////
        String srcFilePath = "/detect_disease/rice_detect_disease_2019_09_24__10_07_08.avi";
  boolean status = false;
        Log.d(TAG, "2");

        try {

                Log.e("downloadFTP login : ", "Success");
                OutputStream desFileStream = new BufferedOutputStream( new FileOutputStream(desFilePath));
                Log.d(TAG,"FileOutputStream");
                status = mFTPClient.retrieveFile(srcFilePath, desFileStream);
                Log.d(TAG, "4");
                desFileStream.close();

                Log.e("downloadFTP status : ", "" + status);
                Log.d(TAG, "5");
                return status;
        } catch (Exception e) {
            Log.d(TAG, "download failed");
        }
        return status;
    }

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-08-18
  • 2020-05-25
  • 2018-05-28
  • 1970-01-01
  • 2012-05-04
  • 2012-08-07
  • 1970-01-01
相关资源
最近更新 更多