Не удается загрузить HTML с локального хоста в Awesomium.Net + XNA
Я пишу игру в XNA, в которой в качестве пользовательского интерфейса используются веб-представления Awesomium. Веб-изображения отображаются в Texture2D с использованием этого класса.
Он прекрасно работает с использованием локальных html-файлов, но мне также нужно использовать некоторый XML, и Awesomium, похоже, не позволяет этого (установка для FileAccessFromFileURL и WebSecurity значения false ничего не делает). Моим решением было разместить мой HTML/XML UI на локальном веб-сервере, используя этот класс для сервера.
Веб-сервер работает нормально и доступен через мой браузер, но я получаю пустые окна, когда я устанавливаю свои источники веб-просмотра на http://localhost:8023/myindex.html. Я не получаю эти выходные данные при доступе к localhost с помощью элемента управления Awesomium WPF, а также при удаленном размещении html. Это заставляет меня думать, что проблема вызвана тем, как мой класс обрабатывает URI.
public struct AwesomiumMenu
{
public WebView webView;
public Microsoft.Xna.Framework.Rectangle Rectangle;
public AwesomiumMenu(string Source, Microsoft.Xna.Framework.Rectangle rectangle)
{
// WebPreferences to disable same-origin policy so we can load local XML + remove scrollbars
const string SCROLLBAR_CSS = "::-webkit-scrollbar { visibility: hidden; }";
WebSession session = WebCore.CreateWebSession(new WebPreferences()
{
CustomCSS = SCROLLBAR_CSS,
UniversalAccessFromFileURL = true,
FileAccessFromFileURL = true,
WebSecurity = false
});
//// CSS styling
//const string SCROLLBAR_CSS = "::-webkit-scrollbar { visibility: hidden; }";
//WebCore.Initialize(new WebConfig()
//{
// CustomCSS = SCROLLBAR_CSS
//});
webView = WebCore.CreateWebView(rectangle.Width, rectangle.Height, session);
webView.Source = Source.ToUri();
Console.WriteLine(webView.Source);
webView.IsTransparent = true;
while (webView.IsLoading)
WebCore.Update();
2 ответа
Я использую mongoose в качестве локального сервера - очень прост в использовании. Я сделал простейшее тестовое приложение, которое я мог, и оно работает для меня. Вот весь код:
public partial class Form1 : Form
{
private Awesomium.Windows.Forms.WebControl webControl1;
public Form1()
{
if (!WebCore.IsInitialized)
{
WebCore.Initialize(new WebConfig(), true);
}
InitializeComponent();
this.webControl1.Dock = System.Windows.Forms.DockStyle.Fill;
this.webControl1.Location = new System.Drawing.Point(0, 0);
this.webControl1.Size = new System.Drawing.Size(1134, 681);
this.webControl1.TabIndex = 0;
this.webControl1.WebSession = WebCore.CreateWebSession("%APPDATA%\\Test", new WebPreferences
{
CustomCSS = "body { overflow:hidden; }",
WebSecurity = false,
DefaultEncoding = "UTF-8",
});
this.webControl1.Source = new Uri("http://localhost:8080/Test/test.html");
}
}
Поскольку вы играете в XNA, почему бы не встроить свой интерфейс в виде ресурсов в файлы DLL? это то, что я сделал для своей игры, и она отлично работает
В моей игре у меня есть интерфейс, загруженный из DLL, и по дизайну я предотвращаю навигацию по URL вне моего контекста (без внешней навигации по URL).
Чтобы добиться этого, я реализовал класс DataSource, который при вызове OnRequest загружает ресурс из dll, вот он (немного оптимизирован и прямо извлечен из моего проекта, но вы должны это понимать)
class SampleDataSource : DataSource {
Assembly InterfaceAssembly;
string[] names;
public SampleDataSource() {
InterfaceAssembly = typeof(Interface.HTMLInterface).Assembly;
// Get the names of all the resources in the assembly
names = InterfaceAssembly.GetManifestResourceNames();
Array.Sort(names, CaseInsensitiveComparer.Default);
}
protected override void OnRequest(DataSourceRequest request) {
var response = new DataSourceResponse();
string[] parts = request.Path.Replace("\\", "/").Split('/');
for (int i = 0; i < parts.Length - 1; i++) {
parts[i] = parts[i].Replace(".", "_").Replace("-", "_");
}
string resourcePath = "Interface.html." + request.Path
//.Replace(".", "_")
.Replace("/", ".")
.Replace("\\", ".");
resourcePath = "Interface.html." + String.Join(".", parts);
// Find the image in the names array
int pos = Array.BinarySearch(names, resourcePath, CaseInsensitiveComparer.Default);
if (pos > -1) {
resourcePath = names[pos];
}
byte[] data = null;
using (Stream stream = InterfaceAssembly.GetManifestResourceStream(resourcePath)) {
data = new byte[stream.Length];
stream.Read(data, 0, data.Length);
}
IntPtr unmanagedPointer = IntPtr.Zero;
try {
unmanagedPointer = Marshal.AllocHGlobal(data.Length);
Marshal.Copy(data, 0, unmanagedPointer, data.Length);
response.Buffer = unmanagedPointer;
switch (System.IO.Path.GetExtension(request.Path).ToLower()) {
case ".html":
case ".htm":
response.MimeType = "text/html";
break;
case ".js":
response.MimeType = "application/javascript";
break;
case ".css":
response.MimeType = "text/css";
break;
case ".png":
response.MimeType = "image/png";
break;
case ".jpeg":
case ".jpg":
response.MimeType = "image/jpeg";
break;
default:
response.MimeType = "text/html";
break;
}
response.Size = (uint)data.Length;
SendResponse(request, response);
}
catch (Exception e) {
throw e;
}
finally {
Marshal.FreeHGlobal(unmanagedPointer);
}
}
}
Вы можете найти информацию о DataSource в официальной документации docs.awesomium.net
в любом случае, вот как я связываю источник данных с моим веб-представлением:
WebView.WebSession.AddDataSource("sample", new SampleDataSource());