initialize standalone OpenFL application structure with essential files and configurations

This commit is contained in:
2025-04-09 02:37:12 +02:00
parent d533ffd7a8
commit 8c36316409
12 changed files with 471 additions and 0 deletions

View File

@@ -0,0 +1,136 @@
package;
import openfl.Lib;
import lime.utils.AssetType;
import lime.tools.Asset;
import lime.ui.WindowAttributes;
import openfl.system.System;
import openfl.display.Application;
import openfl.display.Stage;
import openfl.events.Event;
import openfl.events.FullScreenEvent;
@:access(lime.app.Application)
@:access(lime.system.System)
@:access(openfl.display.Stage)
@:access(openfl.events.UncaughtErrorEvents)
class ApplicationMain {
public static function main() {
lime.system.System.__registerEntryPoint("src/DocumentClass.hx", create);
create(null);
}
public static function create(config):Void {
try {
trace("Creating minimal application");
var app = new Application();
// Initialize assets via macro-generated code
Assets.initializeAssets();
trace("Assets initialized");
// Minimal metadata
app.meta["name"] = "Debug Application";
// Simple window
var attributes:WindowAttributes = {
height: 600,
width: 800,
title: "Debug Window"
};
app.createWindow(attributes);
// Skip preloader, just call start directly
start(app.window.stage);
var result = app.exec();
lime.system.System.exit(result);
} catch (e:Dynamic) {
trace("Error: " + e);
}
}
// public static function create(config):Void
// {
// var app = new Application();
// app.meta["build"] = "1.0.0"; // Replace with actual build number
// app.meta["company"] = "Your Company"; // Replace with your company name
// app.meta["file"] = "src/Main.hx"; // Path to your main application file
// app.meta["name"] = "Your Application"; // Replace with your application title
// app.meta["packageName"] = "com.yourcompany.yourapp"; // Replace with your package name
// app.meta["version"] = "1.0.0"; // Replace with your application version
// // var asset = new Asset();
// // asset.sourcePath = "src/assets"; // Path to your assets
// // asset.targetPath = "assets"; // Target path for assets
// // asset.type = AssetType.IMAGE; // Type of asset
// if (config.hxtelemetry != null)
// {
// app.meta["hxtelemetry-allocations"] = config.hxtelemetry.allocations;
// app.meta["hxtelemetry-host"] = config.hxtelemetry.host;
// }
// var attributes:WindowAttributes = {
// allowHighDPI: true, // Set to true or false as needed
// alwaysOnTop: false, // Set to true or false as needed
// borderless: false, // Set to true or false as needed
// frameRate: 60, // Set your desired frame rate
// height: 600, // Set your desired window height
// hidden: false, // Set to true or false as needed
// maximized: false, // Set to true or false as needed
// minimized: false, // Set to true or false as needed
// resizable: true, // Set to true or false as needed
// title: "Your Application", // Replace with your application title
// width: 800, // Set your desired window width
// x: 100, // Set your desired x position
// y: 100 // Set your desired y position
// };
// app.createWindow(attributes);
// var preloader = getPreloader();
// app.preloader.onProgress.add(function(loaded, total)
// {
// @:privateAccess preloader.update(loaded, total);
// });
// app.preloader.onComplete.add(function()
// {
// @:privateAccess preloader.start();
// });
// preloader.onComplete.add(start.bind(app.window.stage));
// app.preloader.load();
// var result = app.exec();
// lime.system.System.exit(result);
// }
public static function start(stage:Stage):Void {
if (stage.__uncaughtErrorEvents.__enabled) {
try {
// Instantiate and add DocumentClass
var documentClass = new DocumentClass();
Lib.current.addChild(documentClass);
// Then dispatch events
stage.dispatchEvent(new Event(Event.RESIZE, false, false));
if (stage.window.fullscreen) {
stage.dispatchEvent(new FullScreenEvent(FullScreenEvent.FULL_SCREEN, false, false, true, true));
}
} catch (e:Dynamic) {
stage.__handleError(e);
}
} else {
// Instantiate and add DocumentClass
var documentClass = new DocumentClass();
Lib.current.addChild(documentClass);
// Then dispatch events
stage.dispatchEvent(new Event(Event.RESIZE, false, false));
if (stage.window.fullscreen) {
stage.dispatchEvent(new FullScreenEvent(FullScreenEvent.FULL_SCREEN, false, false, true, true));
}
}
}
public static function getPreloader() {
return new openfl.display.Preloader();
}
}

View File

@@ -0,0 +1,32 @@
package;
import openfl.display.BitmapData;
import openfl.media.Sound;
import openfl.text.Font;
import openfl.utils.ByteArray;
@:build(macros.AssetMacro.buildAssets())
class Assets {
// The @:build macro will inject the initializeAssets method
// Helper methods for convenience
public static function getBitmapData(id:String):BitmapData {
return openfl.Assets.getBitmapData(id);
}
public static function getSound(id:String):Sound {
return openfl.Assets.getSound(id);
}
public static function getFont(id:String):Font {
return openfl.Assets.getFont(id);
}
public static function getText(id:String):String {
return openfl.Assets.getText(id);
}
public static function getBytes(id:String):ByteArray {
return openfl.Assets.getBytes(id);
}
}

View File

@@ -0,0 +1,19 @@
package;
import openfl.events.EventDispatcher;
import openfl.display.Sprite;
import openfl.events.Event;
import openfl.display.DisplayObjectContainer;
import openfl.events.MouseEvent;
class DocumentClass extends Sprite
{
public function new()
{
super();
dispatchEvent(new openfl.events.Event(openfl.events.Event.ADDED_TO_STAGE, false, false));
graphics.beginFill(0xFFF00F, 1);
graphics.drawRect(0, 0, 800, 600);
graphics.endFill();
}
}

View File

@@ -0,0 +1,19 @@
package;
import openfl.events.EventDispatcher;
import openfl.display.Sprite;
import openfl.events.Event;
import openfl.display.DisplayObjectContainer;
import openfl.events.MouseEvent;
class Main extends Sprite
{
public function new()
{
super();
dispatchEvent(new openfl.events.Event(openfl.events.Event.ADDED_TO_STAGE, false, false));
graphics.beginFill(0xFFF00F, 1);
graphics.drawRect(0, 0, 800, 600);
graphics.endFill();
}
}

View File

@@ -0,0 +1,15 @@
// filepath: /standalone-openfl-app/standalone-openfl-app/src/ManifestResources.hx
package;
class ManifestResources
{
public static var preloadLibraries:Array<String> = [];
public static var preloadLibraryNames:Array<String> = [];
public static function init(config:Dynamic):Void
{
// Load assets and resources here
// Example: preloadLibraries.push("path/to/library");
// Example: preloadLibraryNames.push("LibraryName");
}
}

View File

@@ -0,0 +1,112 @@
package macros;
import haxe.macro.Context;
import haxe.macro.Expr;
import sys.FileSystem;
import sys.io.File;
import haxe.Json;
class AssetMacro {
public static macro function buildAssets():Array<Field> {
var fields = Context.getBuildFields();
// Define assets directory
var assetsDir = "assets";
// Check if directory exists
if (!FileSystem.exists(assetsDir) || !FileSystem.isDirectory(assetsDir)) {
Context.warning('Assets directory "$assetsDir" not found', Context.currentPos());
return fields;
}
// Generate manifest in the format OpenFL expects
var manifest = {
name: "default",
rootPath: "",
assets: []
};
// Scan assets
scanDirectory(assetsDir, manifest.assets);
// Create manifest file (for runtime use)
var manifestPath = "bin/manifest.json";
try {
// Make sure directory exists
var dir = manifestPath.split("/")[0];
if (!FileSystem.exists(dir)) {
FileSystem.createDirectory(dir);
}
File.saveContent(manifestPath, Json.stringify(manifest, null, " "));
} catch (e) {
Context.warning('Could not save manifest file: $e', Context.currentPos());
}
// Generate expression to register the assets
var registerExpr = macro {
// Create an AssetManifest from our generated file
var manifestPath = "bin/manifest.json";
if (sys.FileSystem.exists(manifestPath)) {
var manifest = lime.utils.AssetManifest.fromFile(manifestPath);
if (manifest != null) {
// Register the library with OpenFL
var library = openfl.utils.AssetLibrary.fromManifest(manifest);
if (library != null) {
openfl.Assets.registerLibrary("default", library);
trace("Asset library registered successfully");
} else {
trace("Failed to create library from manifest");
}
} else {
trace("Failed to parse manifest file");
}
} else {
trace("Manifest file not found at: " + manifestPath);
}
};
// Add initialization method
fields.push({
name: "initializeAssets",
access: [Access.APublic, Access.AStatic],
kind: FieldType.FFun({
args: [],
ret: macro:Void,
expr: registerExpr
}),
pos: Context.currentPos()
});
return fields;
}
private static function scanDirectory(dir:String, assets:Array<Dynamic>, ?prefix:String = ""):Void {
for (file in FileSystem.readDirectory(dir)) {
var path = dir + "/" + file;
var id = prefix + file;
if (FileSystem.isDirectory(path)) {
scanDirectory(path, assets, id + "/");
} else {
var type = getAssetType(file);
assets.push({
id: id,
path: path,
type: type
});
}
}
}
private static function getAssetType(file:String):String {
var ext = file.substr(file.lastIndexOf(".") + 1).toLowerCase();
return switch (ext) {
case "jpg", "jpeg", "png", "gif", "bmp": "image";
case "mp3", "ogg", "wav": "sound";
case "ttf", "otf": "font";
case "txt", "json", "xml", "csv": "text";
default: "binary";
}
}
}