Skip to content

dev

FreeBodyEngine.core.files.dev #

DevFileStream(path, writes_allowed) #

Bases: FileStream

A FileStream backed by a real file on disk, opened in binary mode for the lifetime of the resource (r+b when writes are allowed, else read- only rb) rather than reopened per read/write.

Opens path, creating an empty file there first if it doesn't exist and writes_allowed is True (errors instead if writes aren't allowed and the file is missing).

path = path instance-attribute #

writes_allowed = writes_allowed instance-attribute #

clear() #

Truncates the file to empty. A no-op if writes aren't allowed.

close() #

Closes the underlying file handle.

read(size=-1, offset=0) #

Reads size bytes starting at offset (the whole file when size is -1, the default). Leaves the stream position reset to 0 afterwards.

remove(start=0, end=-1) #

Deletes the byte range [start, end) from the file (the rest of the file when end is -1, the default), shifting every following byte down to close the gap and truncating the file to its new, shorter length. Copies in 1MB chunks rather than loading the whole tail into memory at once, since asset files this shifts can be large. A no-op if writes aren't allowed, or if the range is empty.

write(data, offset=-1) #

Writes data at offset (appending at the current end of file when offset is -1, the default). A no-op if writes aren't allowed. Leaves the stream position reset to 0 afterwards.

DevFileSystem(asset_directory) #

Bases: FileSystem

The dev-mode FileSystem: reads/writes loose files straight off disk under asset_directory (rather than a bundled release .pak, see AssetPackFileSystem) and drives a FileWatcher so edits to those files trigger hot reload.

Starts a FileWatcher polling asset_directory immediately - actually wiring its update() into the update loop happens later, in on_initialize().

asset_directory = self.ensure_trailing_slash(self.sanitise_path(asset_directory)) instance-attribute #

file_watcher = FileWatcher(os.path.expanduser(self.asset_directory)) instance-attribute #

hot_reloading = True instance-attribute #

user_files_path = self.sanitise_path(get_user_file_path()) instance-attribute #

ensure_path(path) #

Returns whether path (a real, already-resolved host filesystem path) exists on disk.

get_file(path) #

Resolves path to a real file on disk and returns a FileResource wrapping it - user:// paths resolve under the per-platform user data directory (always writable), engine:// paths resolve into the installed FreeBodyEngine.engine_assets package (never writable), and anything else resolves under asset_directory (writable only when ASSET_WRITES_PERMITTED is set, true by default in dev mode). For that last case, if the resolved path already exists on disk but writes aren't permitted, this warns and returns None instead of a resource; otherwise DevFileStream itself creates the underlying file on disk if it's missing and writes are permitted.

get_system_path(path) #

Intended to resolve a virtual path to a real host filesystem path, mirroring get_file()'s path-prefix handling. Not currently called anywhere in the engine; note the engine/-prefixed branch falls through without a return (implicitly returning None) rather than resolving anything.

on_destroy() #

Undoes on_initialize()'s registrations.

on_initialize() #

Wires the FileWatcher's polling into the update loop and starts listening for the FILE_CHANGE events it emits, for as long as this FileSystem is alive (i.e. the whole dev-mode run).

get_user_file_path() #

Returns the per-platform base directory for user:// files (saves, logs, and other runtime-writable data) - unset for any platform other than linux/win32/darwin.

open_file(path, mode) #

Thin wrapper around the builtin open() - exists so DevFileStream can be tested/mocked by patching this one call site instead of the builtin itself.