繁体   English   中英

LibGDX:无法在Android上打开服务器套接字

[英]LibGDX: can't open server socket on android

我正在使用libGDX开发多人游戏,但我的问题是该代码可在桌面上运行。 这会导致Android崩溃。 当我在android上启动服务器线程时,发生以下错误:

FATAL EXCEPTION: YellowServer
com.badlogic.gdx.utils.GdxRuntimeException: Cannot create a server socket at port 4444.
at com.badlogic.gdx.net.NetJavaServerSocketImpl.<init>(NetJavaServerSocketImpl.java:63)
at com.badlogic.gdx.backends.android.AndroidNet.newServerSocket(AndroidNet.java:60)
at hu.hundevelopers.yellow.net.NetServer.<init>(NetServer.java:41)
at hu.hundevelopers.yellow.YellowServer.create(YellowServer.java:32)
at hu.hundevelopers.yellow.YellowServer.run(YellowServer.java:61)
Caused by: java.net.SocketException: socket failed: EACCES (Permission denied)
at libcore.io.IoBridge.socket(IoBridge.java:583)
at java.net.PlainSocketImpl.create(PlainSocketImpl.java:201)
at java.net.PlainServerSocketImpl.create(PlainServerSocketImpl.java:38)
at java.net.ServerSocket.<init>(ServerSocket.java:59)
at com.badlogic.gdx.net.NetJavaServerSocketImpl.<init>(NetJavaServerSocketImpl.java:46)
... 4 more
Caused by: libcore.io.ErrnoException: socket failed: EACCES (Permission denied)
at libcore.io.Posix.socket(Native Method)
at libcore.io.BlockGuardOs.socket(BlockGuardOs.java:181)
at libcore.io.IoBridge.socket(IoBridge.java:568)
... 8 more

好像我从清单xml文件中忘记了权限,但是它们在那里:

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

NetServer.java:

package hu.hundevelopers.yellow.net;

import java.util.ArrayList;
import java.util.List;

import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Net;
import com.badlogic.gdx.net.ServerSocket;

import hu.hundevelopers.yellow.YellowServer;
import hu.hundevelopers.yellow.net.packet.Packet;

public class NetServer {
    public class ListenThread extends Thread {
        public NetServer net;

        public ListenThread(NetServer net) {
            super("ListenThread");
            this.net = net;
        }

        @Override
        public void run() {
            try {
                while (this.net.server.game.isHosting) {
                    NetServerClient client = new NetServerClient(this.net, this.net.socket.accept(this.net.server.game.socketHints));
                    this.net.clients.add(client);
                }
            } catch (Exception e) {

            }
        }
    }

    public YellowServer server;
    public ServerSocket socket;
    public List<NetServerClient> clients;

    public NetServer(YellowServer server, int port) {
        this.server = server;
        this.socket = Gdx.net.newServerSocket(Net.Protocol.TCP, port, this.server.game.serverSocketHints);
        this.clients = new ArrayList<NetServerClient>();
        new ListenThread(this).start();
    }

    public void sendToAll(Packet pkt) {
        for (NetServerClient client : this.clients)
            client.send(pkt);
    }

    public void sendToAllAndDispose(Packet pkt) {
        this.sendToAll(pkt);
        pkt.dispose();
    }

    public void update() {
        for (int i = 0; i < this.clients.size(); i++) {
            this.clients.get(i).update();
            if (!this.clients.get(i).connection) {
                this.clients.get(i).dispose();
                this.clients.remove(i--);
            }
        }
    }

    public void dispose() {
        for(NetServerClient client : this.clients)
            client.dispose();
        this.socket.dispose();
    }
}

编辑:

AndroidManifest.xml中:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="hu.hundevelopers.yellow.android"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk android:minSdkVersion="8" android:targetSdkVersion="19" />

    <uses-permission android:name="android.permission.INTERNET" />
    <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/GdxTheme" >
        <activity
            android:name="hu.hundevelopers.yellow.android.AndroidLauncher"
            android:label="@string/app_name" 
            android:screenOrientation="landscape"
            android:configChanges="keyboard|keyboardHidden|orientation|screenSize">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

AndroidLauncher.java:

package hu.hundevelopers.yellow.android;

import android.content.pm.PackageManager;
import android.os.Bundle;

import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.backends.android.AndroidApplication;
import com.badlogic.gdx.backends.android.AndroidApplicationConfiguration;

import hu.hundevelopers.yellow.Yellow;

public class AndroidLauncher extends AndroidApplication {
    @Override
    protected void onCreate (Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        AndroidApplicationConfiguration config = new AndroidApplicationConfiguration();
        initialize(new Yellow(new String[]{}), config);
        if(getContext().checkCallingOrSelfPermission("android.permission.INTERNET") == PackageManager.PERMISSION_GRANTED) {
            Gdx.app.log("INFO", "PERMISSION GRANTED");
        } else {
            Gdx.app.log("ERROR", "PERMISSION DENIED");
        }
    }
}

我解决了问题。 我将所需的最低Android版本从8更改为10,现在一切正常。

异常指示其权限问题。 因此,在打包或部署步骤中可能会出现一些问题(或者清单未达到您的预期目的)。

您可以添加一些调试代码以验证您是否没有权限。 请参阅如何在运行时检查权限而不抛出SecurityException? 那应该有助于缩小问题的范围。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM