@@ -23,6 +23,68 @@ public const string PANEL_EDITOR = "panel-editor";
2323public const string PANEL_PROJECTS_LIST = " panel-projects-list" ;
2424public const string PANEL_NEW_PROJECT = " panel-new-project" ;
2525
26+ public bool parse_port_from_string (out uint16 port , string str )
27+ {
28+ port = 0 ;
29+
30+ string trimmed = str. strip();
31+ if (trimmed == " " )
32+ return false ;
33+
34+ for (int i = 0 ; i < trimmed. length; ++ i) {
35+ if (trimmed[i] < ' 0' || trimmed[i] > ' 9' )
36+ return false ;
37+ }
38+
39+ int parsed = int . parse(trimmed);
40+ if (parsed < 1 || parsed > 65535 )
41+ return false ;
42+
43+ port = (uint16 )parsed;
44+ return true ;
45+ }
46+
47+ public bool wait_port_file (out uint16 port , string file_path , int num_tries , int interval )
48+ {
49+ port = 0 ;
50+ for (int tries = 0 ; tries < num_tries; ++ tries) {
51+ try {
52+ string contents = null ;
53+ GLib . FileUtils . get_contents(file_path, out contents);
54+ if (parse_port_from_string(out port, contents))
55+ return true ;
56+ } catch (FileError e) {
57+ }
58+
59+ GLib . Thread . usleep(interval* 1000 );
60+ }
61+
62+ return false ;
63+ }
64+
65+ public bool create_port_file_path (out string file_path , string prefix )
66+ {
67+ file_path = " " ;
68+
69+ try {
70+ string dir_path = GLib . DirUtils . make_tmp(" crown_%s_port_XXXXXX " . printf(prefix));
71+ file_path = GLib . Path . build_filename(dir_path, " console_port" );
72+ return true ;
73+ } catch (FileError e) {
74+ loge(" Could not create temporary directory for `%s `: %s " . printf(prefix, e. message));
75+ return false ;
76+ }
77+ }
78+
79+ public void cleanup_port_file_path (string file_path )
80+ {
81+ try {
82+ GLib . File . new_for_path(file_path). delete();
83+ } catch (Error e) {
84+ // Ignore.
85+ }
86+ }
87+
2688public bool widget_activate_action_variant (Gtk .Widget widget , string name , GLib .Variant ? args = null )
2789{
2890#if CROWN_GTK3
@@ -760,7 +822,7 @@ public class LevelEditorApplication : Gtk.Application
760822 public LevelEditorApplication ()
761823 {
762824 Object (application_id: " org.crownengine.Crown"
763- , flags: GLib . ApplicationFlags . FLAGS_NONE
825+ , flags: GLib . ApplicationFlags . NON_UNIQUE
764826 );
765827
766828 GLib . Environment . set_prgname(this . application_id); // FIXME: Drop after GTK4 port.
@@ -1571,6 +1633,10 @@ public class LevelEditorApplication : Gtk.Application
15711633 {
15721634 yield stop_backend();
15731635
1636+ string port_file;
1637+ if (! create_port_file_path(out port_file, " data_compiler" ))
1638+ return false ;
1639+
15741640 // Spawn the data compiler.
15751641 string args[] =
15761642 {
@@ -1582,6 +1648,8 @@ public class LevelEditorApplication : Gtk.Application
15821648 " --map-source-dir" ,
15831649 " core" ,
15841650 _project. toolchain_dir(),
1651+ " --port-file" ,
1652+ port_file,
15851653 " --server" ,
15861654 " --wait-console"
15871655 };
@@ -1596,8 +1664,20 @@ public class LevelEditorApplication : Gtk.Application
15961664 _editor_stack. set_visible_child_name(COMPILER_CONNECTING );
15971665 _inspector_stack. set_visible_child_name(COMPILER_CONNECTING );
15981666
1667+ uint16 data_compiler_port = 0 ;
1668+ bool has_port = wait_port_file(out data_compiler_port
1669+ , port_file
1670+ , DATA_COMPILER_CONNECTION_TRIES
1671+ , DATA_COMPILER_CONNECTION_INTERVAL
1672+ );
1673+ cleanup_port_file_path(port_file);
1674+ if (! has_port) {
1675+ loge(" Cannot read data_compiler port" );
1676+ return false ;
1677+ }
1678+
15991679 int tries = yield _compiler. connect_async(DATA_COMPILER_ADDRESS
1600- , DATA_COMPILER_TCP_PORT
1680+ , data_compiler_port
16011681 , DATA_COMPILER_CONNECTION_TRIES
16021682 , DATA_COMPILER_CONNECTION_INTERVAL
16031683 );
@@ -1689,14 +1769,18 @@ public class LevelEditorApplication : Gtk.Application
16891769 return ;
16901770 }
16911771
1772+ string port_file;
1773+ if (! create_port_file_path(out port_file, " game" ))
1774+ return ;
1775+
16921776 // Spawn the game.
16931777 string args[] =
16941778 {
16951779 ENGINE_EXE ,
16961780 " --data-dir" ,
16971781 _project. data_dir(),
1698- " --console- port" ,
1699- GAME_TCP_PORT . to_string() ,
1782+ " --port-file " ,
1783+ port_file ,
17001784 " --wait-console" ,
17011785 " --lua-string" ,
17021786 sg == StartGame . TEST ? " TEST=true" : " "
@@ -1708,9 +1792,21 @@ public class LevelEditorApplication : Gtk.Application
17081792 loge(e. message);
17091793 }
17101794
1795+ uint16 game_port = 0 ;
1796+ bool has_port = wait_port_file(out game_port
1797+ , port_file
1798+ , GAME_CONNECTION_TRIES
1799+ , GAME_CONNECTION_INTERVAL
1800+ );
1801+ cleanup_port_file_path(port_file);
1802+ if (! has_port) {
1803+ loge(" Cannot read game port" );
1804+ return ;
1805+ }
1806+
17111807 // Try to connect to the game.
17121808 int tries = yield _game. connect_async(GAME_ADDRESS
1713- , GAME_TCP_PORT
1809+ , game_port
17141810 , GAME_CONNECTION_TRIES
17151811 , GAME_CONNECTION_INTERVAL
17161812 );
@@ -1722,15 +1818,19 @@ public class LevelEditorApplication : Gtk.Application
17221818
17231819 public async void start_thumbnail ()
17241820 {
1821+ string port_file;
1822+ if (! create_port_file_path(out port_file, " thumbnail" ))
1823+ return ;
1824+
17251825 string args[] =
17261826 {
17271827 ENGINE_EXE ,
17281828 " --data-dir" ,
17291829 _project. data_dir(),
17301830 " --boot-dir" ,
17311831 THUMBNAIL_BOOT_DIR ,
1732- " --console- port" ,
1733- THUMBNAIL_TCP_PORT . to_string() ,
1832+ " --port-file " ,
1833+ port_file ,
17341834 " --wait-console" ,
17351835 " --pumped" ,
17361836 " --hidden"
@@ -1742,9 +1842,21 @@ public class LevelEditorApplication : Gtk.Application
17421842 loge(e. message);
17431843 }
17441844
1845+ uint16 thumbnail_port = 0 ;
1846+ bool has_port = wait_port_file(out thumbnail_port
1847+ , port_file
1848+ , THUMBNAIL_CONNECTION_TRIES
1849+ , THUMBNAIL_CONNECTION_INTERVAL
1850+ );
1851+ cleanup_port_file_path(port_file);
1852+ if (! has_port) {
1853+ loge(" Cannot read thumbnail port" );
1854+ return ;
1855+ }
1856+
17451857 // Try to connect to the game.
17461858 int tries = yield _thumbnail. connect_async(THUMBNAIL_ADDRESS
1747- , THUMBNAIL_TCP_PORT
1859+ , thumbnail_port
17481860 , THUMBNAIL_CONNECTION_TRIES
17491861 , THUMBNAIL_CONNECTION_INTERVAL
17501862 );
0 commit comments