Skip to content
  • Our Product
    • Namazu Elements
      • What is Elements?
      • Why open source?
      • Docs
        • Namazu Elements in Five Minutes or Less
        • RESTful APIs Library
        • Security Model
        • Accessing the Web UI (CMS)

    Our Product

    A logomark with three layered rhombuses adorning the lettermark that says Elements in bold all-caps sans-serif letters.
    • What is Namazu Elements? Discover our easy-to-use backend network solution built for online games. Rapidly enables full-scale multiplayer games or online solo adventures.
    • Why open source? Is there a truly open source server backend for connected games? There is now. Download and run a local copy of Namazu Elements and try it for yourself.
    Download Namazu Elements

    Get started

    • Quick start Read our Elements 5-minute quick start guide
    • Documentation Read our developer docs for learning more about Elements
    • RESTful APIs A full list of core API specs for working with the Elements framework
    • Security An overview of the server-authoritative security model of Elements
    • Accessing the CMS Manage your game with ease via the Namazu Elements CMS.

    Co-development Reimagined

    • Best real-time game backends in 2026 If you're researching an alternative to your current backend solution, we've prepared a report of all of the backend solutions on the market in 2026 and how Namazu Elements compares.
      Co-dev

    Recent Posts

    • The watercolor-styled Namazu Studios logo over a giant namazu lurking in the depth
      Namazu Studios Featured in San Diego Business Journal
      22 Sep 2025 Press
    • Namazu Elements 3.1 Released – Service Layer Fixes, Secure APIs, and Steam Bug Fix
      22 Apr 2025 Release Notes
  • Case Studies
  • About Us
  • News
  • Services
  • Book a call
namazu-studios-logo
Book a call
Popular Search Roblox

Getting Started

  • Namazu Elements in Five Minutes or Less
  • Overview
  • Accessing the Web UI (CMS)
  • CMS Feature Overview

Fundamentals

  • Why You Need a Server (and What “Authoritative” Means)
  • Elements as a Game Runtime
  • Where Your Authoritative Code Runs
  • Lifecycles and Flows

General Concepts

  • Custom Elements
  • Data Models
  • Security Model
  • N-Tier Architecture

Namazu Elements Core Features

  • Email Service
  • Applications
  • Sessions
  • Users and Profiles
  • Digital Goods
  • Progress and Missions
  • Progress and Missions (3.4+)
  • Leaderboards
  • Matchmaking – Comprehensive Guide
  • Friends
  • Followers
  • Product Bundles and SKUs
  • Item Ledger
  • Receipts
  • Reward Issuances
  • Save Data
  • Metadata
  • Metadata (3.4+)
  • Queries
  • User Authentication / Sign In
    • What is a User?
    • Email Verification
    • User Authentication in Elements
    • Account Linking
    • Setting Up Twitch OIDC Login (Backend)
    • OIDC Login for Thick Clients (Browser Redirect Flow)
    • Auth Schemes
      • Auth Schemes
      • OAuth2
      • OIDC
  • Features
    • Web3
      • Wallets
      • Vaults
      • Omni Chain Support
      • Smart Contracts
        • Smart Contracts
  • Queries
    • Advanced Operators
    • Object Graph Navigation
    • Boolean Queries
    • Base Query Syntax
  • Advanced Operators
    • .name
    • .ref

Your Game Code - Adding Custom Elements

  • Custom Code Overview
  • Windows Setup
  • Mac OS Setup
  • Ubuntu Linux Setup
  • Element Anatomy: A Technical Deep Dive
  • Introduction to Guice and Jakarta in Elements
  • Structuring your Element
  • Events
  • Packaging an Element with Maven
  • Deploying an Element
  • Preparing for code generation
  • Properties
  • Websockets
  • RESTful APIs
  • Direct MongoDB Access (3.5+)
  • Building the Example Element: A Complete Walkthrough
  • Building the Kotlin Example Element: A Complete Walkthrough

Configuration

  • Configuring External URLs for Deployment
  • Matchmaking – Comprehensive Guide
  • Direct Database Access and Batch Configuration
  • Connecting Namazu Elements to a TLS-Enabled MongoDB Replica Set
  • Batch Samples
    • Mission Upload Bash Script Sample
    • Item Upload Bash Script Sample

RESTful APIs

  • Importing into Postman
  • RESTful APIs Library
  • Swagger and Swagger UI

Add-Ons

  • Crossplay
    • Crossfire Client Libraries (JVM & Browser)
    • Crossfire Protocol Reference
    • Crossfire: Custom Matchmaking Algorithms
    • Namazu Crossfire (Multiplayer)
    • Deploying Namazu Crossfire in your game
  • Roblox
    • Roblox Overview
    • Secure Player Authentication & Registration
    • Global Matchmaking
    • Roblox Security Best Practices
  • Container on Demand
    • Namazu Conductor
    • Namazu Conductor Admin API
    • Configuring Namazu Conductor Providers
  • Commerce
    • Stripe
      • Stripe
      • Configuring the Stripe Element
      • Stripe REST API Reference
      • Stripe REST API Reference

Game Engine & Client Support

  • Unity
    • Elements Unity Plugin
    • Unity Crossfire Plugin
  • Gamemaker
    • Incorporating GMEXT-Elements into a GameMaker Project

Troubleshooting

  • Common Issues with Docker
  • Local SDK
    • Unable to deploy application : dev.getelements.elements.sdk.exception.SdkElementNotFoundException
    • Could not load class : java.lang.NoClassDefFoundError
  • Namazu Elements Community Edition
    • Common Issues with Docker
    • Unable to deploy application : dev.getelements.elements.sdk.exception.SdkElementNotFoundException
    • Running in the IDE
      • Exception in monitor thread while connecting to server localhost:27017
      • Could not deployAvailableApplications Jetty server Failed to bind to /0.0.0.0:8080 Address already in use

Releases

  • 3.8 Release Notes
  • 3.7 Release Notes
  • 3.6 Release Notes
  • 3.5 Release Notes
  • 3.4 Release Notes
  • 3.3 Release Notes
  • 3.2 Release Notes
  • 3.1 Release Notes
View Categories
  • Home
  • Docs
  • Game Engine & Client Support
  • Gamemaker
  • Incorporating GMEXT-Elements into a GameMaker Project

Incorporating GMEXT-Elements into a GameMaker Project

Est. read time: 9 min read

AI Doc Summarizer Doc Summary
AI Doc Summarizer Thinking Thinking

A walkthrough for adding YoYoGames’ GMEXT-Elements extension to any GameMaker Studio project by vendoring the source directly from GitHub.

A Marketplace listing for GMEXT-Elements isn’t available yet — vendoring from GitHub is the only option today. This doc should get a Marketplace-install alternative once that listing exists.

Why vendor the source #

Reasons to pull the source in directly rather than depending on a prebuilt drop-in:

  • You need a fix or feature that’s landed on main but hasn’t been tagged in a stable point yet.
  • You want to read/patch the actual source (a compiled-in version isn’t easily diffable).
  • You’re scripting project setup and want reproducible, version-pinned source rather than a manual install step.

Trade-off: you’re now responsible for tracking upstream changes yourself.


1. Understand what you’re actually importing #

Don’t just copy the whole GMEXT-Elements repo wholesale — most of it is the demo project GameMaker uses to showcase the extension, not the extension itself. Clone it first and look:

git clone --depth 1 https://github.com/YoYoGames/GMEXT-Elements.git

The relevant subtree is source/Elements_gml/, which is itself a full .yyp demo project. Inside it:

PathWhat it isDo you need it?
extensions/Elements/Elements.yyThe extension resource — just holds config options (server URLs, ports, debug flag). No code lives here.Yes
objects/obj_elements_core/Singleton that owns the HTTP async event, auth token storage, request bookkeeping.Yes
objects/obj_elements_crossfire/Singleton that owns the WebSocket async event and dispatches Crossfire messages.Yes, if you want realtime/matchmaking
scripts/elements_rest_api/, elements_rest_helpers/, elements_rest_schemas/The generated REST client — every elements_* HTTP wrapper function and request/response schema constructor.Yes
scripts/elements_crossfire_api/, elements_crossfire_client/, elements_crossfire_helpers/The Crossfire WebSocket client — connect/matchmake/send/receive.Yes, if you want realtime/matchmaking
extensions/Elements/docs/A static HTML help viewer (fonts, CSS, JS) for GameMaker’s in-IDE “view docs” button.No — skip it, it’s ~4 MB of dead weight for a game build. The real docs are the GitHub wiki.
objects/obj_game, objects/obj_gm_button, objects/obj_gm_text, objects/obj_gm_textbox, objects/obj_elements_crossfire_* (the Mouse_7-only ones), objects/obj_elements_rest_*, rooms/rm_main, fonts/fnt_gm_*Demo-project UI: buttons and labels used to click through the sample.No — these only exist to make the demo clickable.

The key realization: the “extension” resource itself (Elements.yy) is nearly empty — it’s just a place for server_rest_url, server_crossfire_url, server_crossfire_port, and debug_logging to live as extension options. All the actual functionality is in plain GML scripts and two small controller objects, which you import as ordinary project resources.


2. Copy the resources into your project #

GameMaker’s .yy/.yyp files are JSON-with-trailing-commas. You can hand-edit them; the IDE re-normalizes on next save. Copy in this shape:

your_project/
  extensions/Elements/Elements.yy
  objects/obj_elements_core/{obj_elements_core.yy, Create_0.gml, CleanUp_0.gml, Other_62.gml}
  objects/obj_elements_crossfire/{obj_elements_crossfire.yy, Create_0.gml, Other_68.gml}
  scripts/elements_rest_api/{elements_rest_api.yy, elements_rest_api.gml}
  scripts/elements_rest_helpers/{elements_rest_helpers.yy, elements_rest_helpers.gml}
  scripts/elements_rest_schemas/{elements_rest_schemas.yy, elements_rest_schemas.gml}
  scripts/elements_crossfire_api/{elements_crossfire_api.yy, elements_crossfire_api.gml}
  scripts/elements_crossfire_client/{elements_crossfire_client.yy, elements_crossfire_client.gml}
  scripts/elements_crossfire_helpers/{elements_crossfire_helpers.yy, elements_crossfire_helpers.gml}

Every .yy resource file has a "parent" field pointing at a folder, e.g.:

"parent": { "name": "REST", "path": "folders/Elements/REST.yy" }

Folders in the .yyp format are virtual — folders/Elements/REST.yy is not a real file on disk anywhere, it’s just an identifier string. You don’t need to create anything at that path; you only need a matching entry in the project’s .yyp Folders array (see next step). Leave the copied .yy files’ parent fields untouched — they already point at the right virtual paths.


3. Register everything in the .yyp #

Two arrays in your project’s .yyp need new entries: Folders (so the IDE shows a folder in the asset tree) and resources (so the resources actually load).

Folders — add the folder chain the copied resources expect:

{"$GMFolder":"","%name":"Elements","folderPath":"folders/Elements.yy","name":"Elements","resourceType":"GMFolder","resourceVersion":"2.0",},
{"$GMFolder":"","%name":"Crossfire","folderPath":"folders/Elements/Crossfire.yy","name":"Crossfire","resourceType":"GMFolder","resourceVersion":"2.0",},
{"$GMFolder":"","%name":"REST","folderPath":"folders/Elements/REST.yy","name":"REST","resourceType":"GMFolder","resourceVersion":"2.0",},

resources — one entry per resource, name matching the resource’s internal name and path matching where you put its .yy file:

{"id":{"name":"Elements","path":"extensions/Elements/Elements.yy",},},
{"id":{"name":"obj_elements_core","path":"objects/obj_elements_core/obj_elements_core.yy",},},
{"id":{"name":"obj_elements_crossfire","path":"objects/obj_elements_crossfire/obj_elements_crossfire.yy",},},
{"id":{"name":"elements_rest_api","path":"scripts/elements_rest_api/elements_rest_api.yy",},},
{"id":{"name":"elements_rest_helpers","path":"scripts/elements_rest_helpers/elements_rest_helpers.yy",},},
{"id":{"name":"elements_rest_schemas","path":"scripts/elements_rest_schemas/elements_rest_schemas.yy",},},
{"id":{"name":"elements_crossfire_api","path":"scripts/elements_crossfire_api/elements_crossfire_api.yy",},},
{"id":{"name":"elements_crossfire_client","path":"scripts/elements_crossfire_client/elements_crossfire_client.yy",},},
{"id":{"name":"elements_crossfire_helpers","path":"scripts/elements_crossfire_helpers/elements_crossfire_helpers.yy",},},

Placement inside the resources array doesn’t matter functionally — GameMaker doesn’t care about ordering — but grouping by type (near other extensions, near other objects, near other scripts) keeps diffs readable.

Validate before opening the IDE. The .yyp is JSON except for trailing commas, so you can sanity-check your edit without launching GameMaker:

import re, json
text = open("YourProject.yyp").read()
cleaned = re.sub(r',s*([}]])', r'1', text)
data = json.loads(cleaned)  # raises if malformed
names = [r["id"]["name"] for r in data["resources"]]
assert len(names) == len(set(names)), "duplicate resource name"

A malformed .yyp or a duplicate resource name will cause GameMaker to fail to open the project or silently drop a resource — catching it before opening the IDE saves a round trip.


4. One likely fix: make the core singleton persistent #

Both obj_elements_core and obj_elements_crossfire are lazily instantiated singletons — you never place them in a room. The pattern (from elements_rest_helpers.gml):

function _elements_get_singleton(_where) {
    static instance = instance_create_depth(0, 0, 0, obj_elements_core);
    with (instance) return self;
}

The static keyword means this instance is created exactly once, the first time any elements_* function runs. obj_elements_crossfire ships persistent: true in the stock extension, but obj_elements_core ships persistent: false. If your project has more than one room and the room changes after the singleton is created, the non-persistent instance is destroyed — but the static variable still holds a reference to it, so every subsequent call silently operates on a dead instance (auth tokens, in-flight request bookkeeping, all gone).

If your project is single-room, this doesn’t matter. If it’s multi-room (a login screen, a menu, gameplay rooms, etc.), set it persistent:

// objects/obj_elements_core/obj_elements_core.yy
"persistent": true,

5. Configure the extension options #

Open the project in GameMaker, find the Elements extension under Extensions in the asset tree, and fill in:

  • server_rest_url — your Elements REST API base URL
  • server_crossfire_url — your Elements Crossfire WebSocket host
  • server_crossfire_port — usually 443 for WSS
  • debug_logging — True while integrating, so failed requests and Crossfire phase transitions print to the debug console

These are read via extension_get_option_value("Elements", "...") inside the vendored scripts — don’t hardcode URLs elsewhere in your game code.


6. Verify it works #

  1. Open the project in GameMaker. It should load with no missing-resource errors and no red squiggles in the copied scripts.
  2. Drop a test call somewhere reachable at startup, e.g. in a controller object’s Create event:
  3. Run the game. debug_logging = True should print the outgoing request and response in the console. A _code of 200 (or a clear connection error if your server isn’t running yet) confirms the plumbing — extension options, singleton creation, async event handling — is wired correctly.
elements_get_application("your-app-id", function(_code, _data, _request) {
    show_debug_message($"Elements reachable: {_code}");
});

7. Using it: REST and Crossfire basics #

REST — every endpoint is a thin async wrapper, callback-based:

elements_create_username_password_session(_session_request, function(_code, _data, _request) {
    if (_code == 200) {
        _elements_request_auth_set_token("auth_bearer", _data.sessionSecret);
        // now every endpoint that declares "auth_bearer" as a security scheme is authenticated
    }
});

Crossfire — connect, then either find/create/join a match:

elements_crossfire_set_identity(profile_id, session_secret);
elements_crossfire_events_on_connected_callback(function() {
    elements_crossfire_create_match("my_config");   // host path — server responds with a join code
});
elements_crossfire_events_on_created_callback(function(_msg) {
    show_debug_message("Room code: " + _msg.joinCode);
});
elements_crossfire_connect();

Guests call elements_crossfire_join_match_by_code(_join_code) instead of elements_crossfire_create_match, and listen for elements_crossfire_events_on_matched_callback instead of _on_created_callback.

Once connected, elements_crossfire_send_string_broadcast(_text) pushes a message to every participant in the match — this is the “push an event to all connected clients” mechanism for anything server-driven (e.g., “your generated content is ready”).


Gotchas learned the hard way #

  • Don’t hand-patch a feature before checking upstream. GMEXT-Elements is under active development. A capability that looks missing from the version you last read the source of — whether that was an older commit you vendored from, or a plan doc written a few weeks ago — may already exist on main — always re-diff against the current GitHub source before writing a patch, or you’ll duplicate work upstream already did.
  • The extension resource itself has an empty files list. If you’re used to native extensions with per-platform binaries, this one is disorienting — there’s nothing to compile, it’s pure GML. Don’t go looking for a .dll/.so/.dylib to place; there isn’t one.
  • Don’t import the demo project’s UI objects. It’s tempting to copy everything under source/Elements_gml/objects/ for completeness, but half of them (obj_gm_button, obj_elements_rest_create_profile, etc.) exist only to make the sample clickable and add dead weight and demo-specific coupling to your project.
  • Folder paths in .yy files don’t need real files. If you see "path": "folders/Elements/REST.yy" in a copied resource, that’s a virtual identifier consumed only by the .yyp‘s Folders array — don’t go looking for (or creating) an actual file there.
What are your Feelings
Still stuck? How can we help?

How can we help?

Updated on August 14, 2026
Incorporating GMEXT-Elements into a GameMaker ProjectIncorporating GMEXT-Elements into a GameMaker Project
Table of Contents
  • Why vendor the source
  • 1. Understand what you're actually importing
  • 2. Copy the resources into your project
  • 3. Register everything in the .yyp
  • 4. One likely fix: make the core singleton persistent
  • 5. Configure the extension options
  • 6. Verify it works
  • 7. Using it: REST and Crossfire basics
  • Gotchas learned the hard way
  • Documentation
  • Terms of Service
  • Privacy Policy
  • Contact us
  • Linkedin
  • Join our Discord

Namazu Studios LLC is powered by Namazu Elements, an open source modular backend framework for connected games.

Namazu Elements
  • Download
  • About Elements
  • Open source
  • Documentation
  • Support
Namazu Studios
  • Case Studies
  • About Us
  • News
Best realtime game backends 2026
Get in Touch
  • info@namazustudios.com
  • Book a call
  • (619) 862-2890
  • Linkedin
  • Discord

©2008-2026 Namazu Studios. All Rights Reserved.