Test store. Prices are the planned list prices stored as test data, license terms are drafts, and payments go to a Stripe test-mode account. No real money moves.

GameMaker Studio HTML5 Export: Setup, Common Fixes and Limits

GameMaker exports to the browser in two ways: the HTML5 target, which turns your GML into JavaScript, and the GX.games target, which runs a WebAssembly build. Both are free for non-commercial games, and the one-time Professional licence covers selling them. Most HTML5 bugs come from browser rules: serve the game over HTTP, start audio after a tap, and test with WebGL on.

GameMaker (sold for years as Game Maker Studio and GameMaker Studio 2) can export the same project you run on Windows as a browser game. You pick the HTML5 target, run it once to test in a local web server, then use Create Executable to get a ZIP of index.html, JavaScript and texture pages that any static host can serve. The export itself takes minutes. The time goes into the browser-specific problems: a black screen when you double-click the file, music that won't start, blurry text, arrow keys that scroll the page.

This guide covers setup, publishing to itch.io and your own site, and the fixes for the problems people search for most. We checked every fact against GameMaker's manual and help centre on 25 October 2026. We build our own games in TypeScript with Phaser 4 and Three.js, not GameMaker, so where it helps we also say when a JavaScript engine is the better fit. For the wider picture, see our comparison of HTML5 game engines.

Game Maker Studio HTML5 vs GX.games: the two web exports

GameMaker has two targets that run in a browser, and they work differently:

HTML5 targetGX.games target
What it outputsYour GML compiled to JavaScript, plus texture pages and audioA WebAssembly runner plus your game data
Where it runsAny modern browser and any static hostGX.games, or any site that accepts WASM games
RenderingWebGL, or a 2D canvas fallback if WebGL is offWebGL
Built-in online multiplayerNo (you write networking yourself)Yes, rollback multiplayer through GX servers
DebuggingBrowser developer tools on readable JavaScript in debug runsBrowser tools on a WASM build

The HTML5 runtime is open source: YoYo Games published it on GitHub in November 2022, so you can read exactly what your game calls when something behaves differently in a browser. Since release 2024.11, the GX.games Create Executable window also has a ZIP option, which GameMaker says you can upload to any other platform that supports WASM games. If your HTML5 build has a bug you can't work around, a GX.games ZIP is worth trying before you rewrite anything.

Is GameMaker's HTML5 export free?

Yes, for non-commercial games. As of October 2026, GameMaker's pricing page lists three tiers:

  • Free (non-commercial): desktop, mobile, web (HTML5) and GX.games exports, with no watermark or splash screen. You can share the game as long as it earns nothing.
  • Professional: a one-time purchase that adds the commercial licence, needed as soon as the game makes money (ads, sales, sponsorships).
  • Enterprise: a subscription that adds console exports and engine source access.

If you remember paying for an "HTML5 module", that was the old model. GameMaker Studio 1.4 sold export targets as add-on modules, and GameMaker Studio 2 had a permanent Desktop/Web/Mobile licence. Holders of that permanent licence can still release games commercially with the runtime it covers; everyone else uses the tiers above. Old 1.4 projects need converting before they build in current GameMaker, and you should expect to replace obsolete functions.

How to export a GameMaker game to HTML5

These steps work in current GameMaker (the 2026 LTS and monthly releases), and they are the short version of any GameMaker HTML5 tutorial:

  1. Pick the target. In the Target Manager at the top right of the IDE, set the platform to HTML5.
  2. Check the HTML5 Game Options (table below). The defaults are sensible, but scaling, interpolation and WebGL decide how your game looks.
  3. Run it. Press Run as usual. GameMaker starts a small built-in web server (port 51264 by default) and opens your default browser. Your firewall may ask for permission the first time. Add other browsers in the device manager and test in at least Chrome, Firefox and Safari.
  4. Test on a phone. Point your phone's browser at your computer's address and the same port while the game runs, if your network allows it. Restrict the allowed IP range in the target settings when you do.
  5. Build it. Use Build > Create Executable. GameMaker writes a ZIP package.
  6. Publish it. Unzip it and upload the files to your host, or upload the ZIP as-is to sites that accept one, such as itch.io.

GameMaker's own HTML5 setup article has screenshots of each dialog.

HTML5 Game Options worth changing

SettingWhat it doesWhen to change it
Interpolate colours between pixelsSmooths scaled graphicsTurn off for pixel art, or text and sprites will blur
ScalingKeep aspect ratio, or stretch to the canvasKeep aspect ratio unless your UI is built to stretch
WebGLOff, auto-detect or requiredSet to required if you use shaders, surfaces heavily or 3D
Texture page size256 to 8192 pixels, default 2048Leave at 2048 unless you know your players' devices
Allow switching to fullscreenLets the game enter fullscreenKeep on if you offer a fullscreen button
Center the game in the browserCentres the canvasTurn on for your own site; hosts often centre for you
Use Built-In Font / ParticlesShips Arial and default particle spritesTurn off if you don't use them, to save download size
Output Debug To ConsoleSends show_debug_message to the browser consoleTurn on while testing

The full list is in the manual's HTML5 Game Options page.

Making a custom loading screen

You have three options, from simplest to most flexible. A splash screen image replaces the loading bar with a PNG the size of your canvas. A loading bar extension replaces the default bar with your own drawing code. And Included file as index.html lets you ship your own HTML page around the game, which is where you add a branded preloader, a cookie notice or a portal's SDK script.

Publishing your GameMaker HTML5 game

How to get a GameMaker HTML5 game to work on itch.io

itch.io accepts the ZIP from Create Executable. In the upload settings, mark the file as This file will be played in the browser, then set the viewport to your room size (or a multiple of it). itch's HTML5 rules cause most failed uploads:

  • index.html must be in the ZIP, with relative paths only.
  • File names are case-sensitive on their server even if they aren't on your PC, so Music.ogg and music.ogg are different files.
  • A ZIP can hold up to 1,000 files and 500 MB extracted.
  • Tick Mobile Friendly only after testing on a phone, and turn on itch's fullscreen button if your game doesn't draw its own.

Hosting it on your own site, in an iframe or on GX.games

Any static host works, because a GameMaker HTML5 build is just files; there is nothing to run on the server. Upload the unzipped folder and link to index.html, or show it inside a page with an <iframe>. Our guides to hosting HTML5 games and embedding a game in a website cover hosts, caching and iframe settings.

A common question is how to "get the iframe" from inside the game, for example to detect that you're embedded or to read the page's URL. GML can't reach the page directly. Write a small JavaScript extension (a .js file with a function such as return window.self !== window.top;) and call it from GML. If JavaScript needs to call back into a GML function, give that function the gmcallback_ prefix so the HTML5 export doesn't obfuscate its name.

For GX.games, choose the GX.games target and either publish from the IDE or upload the ZIP yourself.

Common GameMaker HTML5 problems and how to fix them

Black screen, or the game not rendering the full room

Open the browser console first (F12). The usual causes, in order:

  1. You opened index.html from your disk. Browsers block much of what a game loads from file:// addresses. Serve the folder with any local web server instead (npx serve or python -m http.server both work). That's why GameMaker shows a "running outside server" warning.
  2. A script error. The console names the function. Debug builds keep readable names, so reproduce it with the debug run.
  3. WebGL problems. Some browsers or old GPUs fail with WebGL on. Test with WebGL set to auto-detect and to off, as GameMaker's own setup guide suggests.
  4. Room, camera and canvas sizes disagree. If only part of the game shows, check that your first room, viewport and window size match, and that the scaling option is what you expect. Our guide to HTML5 game scaling explains letterboxing and full-screen layouts.
  5. show_message calls. They become browser alert() dialogs, which many embedded frames block. Replace them with in-game UI.

Sound doesn't play, loops restart or won't stop

Browsers don't let a page start audio until the player taps, clicks or presses a key. GameMaker's manual says the HTML5 audio context can change state at any time, so check audio_system_is_available() and listen for the Async System event, which reports "audio_system_status" as "available" or "unavailable" (audio overview). Start or resume your music there:

obj_audio: Async - System event
if (async_load[? "event_type"] == "audio_system_status") {
    if (async_load[? "status"] == "available" && !audio_is_playing(snd_music)) {
        audio_play_sound(snd_music, 10, true); // true = loop
    }
}

Looping questions usually have one of three causes:

  • The loop restarts in every room. Sounds keep playing across room changes; a persistent controller that calls audio_play_sound in its Room Start event starts a second copy each time. Guard it with audio_is_playing, as above.
  • Old code uses sound_loop(). That function belongs to very old versions of GameMaker. Current GameMaker loops with the third argument of audio_play_sound.
  • A sound won't stop. audio_stop_sound(snd_music) stops every instance of that asset; if you stored the ID returned by audio_play_sound, stop that ID instead.

If audio_master_gain() seems to do nothing in the browser, apply the volume again once the audio system reports "available", and test whether gain on audio groups or individual sounds behaves the same. Settings applied before the browser's audio context is running don't always stick.

Text looks blurry or scales badly

GameMaker draws text from font textures, so text blurs when the canvas is scaled up with interpolation on. Turn off Interpolate colours between pixels, draw your HUD on the GUI layer at its real size, and avoid scaling the whole canvas by fractions (1.5x looks worse than 1x or 2x). For crisp UI text at many screen sizes, create the font at the largest size you need and scale down, never up.

Fullscreen doesn't work

Keep Allow switching to fullscreen on, and only request fullscreen when the player clicks a button. Browsers grant fullscreen only in response to a user action (MDN), so a call at game start is ignored. On itch.io, the site's own fullscreen button is the most reliable option. Safari on iPhone has long limited fullscreen to video, so design your layout to fit the visible area without it.

Arrow keys scroll the page or don't reach the game

When your game is embedded in a page, the browser can use arrow keys and the space bar to scroll. Call browser_input_capture(true) so the game captures input (manual), and give the player a "click to play" start screen so the game's frame has keyboard focus. If keys work on your PC but not on itch.io, focus is almost always the reason.

Controlling the mouse outside the canvas

The browser only sends mouse positions while the pointer is over the canvas, so mouse_x and mouse_y freeze when the pointer leaves it. Pause or clamp aiming when that happens. If you need drags that continue outside the game, write a JavaScript extension that uses the browser's pointer capture; GML alone can't do it.

"Blocked by client" errors on sprites or scripts

ERR_BLOCKED_BY_CLIENT in the console means a browser extension, almost always an ad blocker, refused to load a file. Filter lists match words such as "ad", "ads", "banner" and "track" in URLs, so a sprite or folder name containing them can disappear for some players. Rename the asset or folder and rebuild, and test once with your ad blocker on.

Depth and draw-order differences

If objects overlap in a different order in the browser than on Windows, you're probably relying on the order of instances at the same depth, which isn't guaranteed across targets. Put things that must overlap on separate layers or give them different depths.

The game runs slowly in HTML5

Measure first with the browser's performance panel. The usual culprits: WebGL turned off, so everything falls back to the slower canvas renderer; many texture swaps because sprites drawn together sit on different texture pages; surfaces created every frame; and large numbers of precise collision checks. Group sprites that draw together onto the same texture page, reuse surfaces, and test the release build, because debug runs are slower. Our HTML5 game performance guide covers frame budgets in more depth.

file_bin_open and other file functions

The binary file functions, including file_bin_open, don't work on the HTML5 target (manual). Saving and loading go to the browser's local storage, and loading a file from a server must use buffer_load_async. Use buffers or INI and JSON strings for saves, and test that saves survive a page reload in every browser you support.

Does the GameMaker debugger work for HTML5?

Use the browser's developer tools, which GameMaker's help centre recommends for debugging HTML5 games in the browser. Run with the debug (orange) button so the generated JavaScript isn't obfuscated; your GML appears as comments above each function, and variables keep a gml prefix. Set breakpoints in the Sources panel and read errors in the Console. Our guide to testing and debugging HTML5 games covers browser tools in general.

Can you make a 3D game in GameMaker for HTML5?

Yes, within limits. GameMaker draws 3D with vertex buffers, matrices and depth testing, and the HTML5 target supports that only with WebGL on, so set WebGL to required. There's no built-in 3D editor, model importer or lighting system, so you write the camera, model loading and shaders yourself. That suits low-poly or retro 3D. For full 3D in the browser, a dedicated library such as Three.js is a better tool; we build our Three.js games with it, and our guide to 3D HTML5 games compares the options.

GameMaker HTML5 multiplayer and networking

A browser game can't open raw TCP or UDP sockets, and it can't act as a server. On the HTML5 target, your GameMaker game is a WebSocket client talking to a server you host somewhere else:

obj_net: Create event
socket = network_create_socket(network_socket_wss); // secure WebSocket
network_connect_raw_async(socket, "game.example.com", 443);
// Messages arrive in the Async - Networking event

The network_create_socket page lists the WebSocket types. "Raw" means GameMaker doesn't add its own packet header, so the game can talk to an ordinary WebSocket server written in Node.js, Go or anything else.

Socket.IO is a common stumbling block. It runs its own protocol on top of WebSockets, and its documentation says a plain WebSocket client can't connect to a Socket.IO server. Either run a plain WebSocket server, or load the Socket.IO client library through a JavaScript extension and call it from GML.

The other route is rollback multiplayer, which is built into GameMaker but only for the GX.games target. It uses GX servers, so you host nothing. It relies on the WebTransport API, and the manual's rollback constraints page lists Safari and Firefox on desktop, and all major mobile browsers, as unsupported. An .io-style game with dozens of players per room needs your own server either way. Our guide to multiplayer HTML5 games covers server choices.

Do GameMaker HTML5 games work on mobile devices?

Yes. They run in mobile Chrome and Safari, and the first touch maps to the left mouse button, so simple tap games work unchanged. For real touch controls, read each finger with the device_mouse_* functions (device 0 is the first finger, 1 the second, and so on) or add on-screen buttons with virtual_key_add. Here is a swipe detector:

obj_input: Step event
if (device_mouse_check_button_pressed(0, mb_left)) {
    start_x = device_mouse_x_to_gui(0);
    start_y = device_mouse_y_to_gui(0);
}
if (device_mouse_check_button_released(0, mb_left)) {
    var dx = device_mouse_x_to_gui(0) - start_x;
    var dy = device_mouse_y_to_gui(0) - start_y;
    if (max(abs(dx), abs(dy)) > 40) { // pixels before it counts as a swipe
        swipe = (abs(dx) > abs(dy)) ? (dx > 0 ? "right" : "left") : (dy > 0 ? "down" : "up");
    }
}

Test on real phones before you tick "Mobile Friendly" anywhere. Mid-range Android phones expose texture page sizes, overdraw and audio-unlock problems that a desktop never shows.

Dialogue systems, extensions and other libraries

Pure GML works the same on every target, so a dialogue system written in GML (typewriter text, choices, portraits) needs no changes for HTML5. Extensions are different: one that wraps a Windows DLL or a native mobile SDK has no HTML5 version, and calling it in a browser build fails. Check each extension's supported platforms before you rely on it, and remove ad or store extensions you don't use from web builds.

GameMaker vs a JavaScript HTML5 engine

Choosing between "Game Maker Studio vs HTML5" really means choosing between GameMaker and a code-first JavaScript engine such as Phaser:

GameMakerJavaScript engine (for example Phaser 4)
LanguageGML, or GML Visual blocksJavaScript or TypeScript
EditorFull IDE with room, sprite and sequence editorsYour code editor plus separate tools
Web outputGML compiled to JavaScript, or a WASM buildYour own code, unchanged
Browser APIsThrough JavaScript extensionsCalled directly
Other platformsDesktop, mobile and consoles from one projectWeb first; apps through wrappers
CostFree non-commercial; one-time licence to sellPhaser is open source under the MIT licence
MultiplayerWebSockets yourself, or rollback on GX.games onlyAny WebSocket or WebRTC library

Pick GameMaker if you want one project for desktop, mobile and the web, or you prefer its editor. Pick a JavaScript engine if the browser is your main platform, you need web features such as portal SDKs, ads and analytics, or you want to debug the code you wrote rather than generated code. Our Phaser tutorial shows that workflow, and our roundup of HTML5 game makers compares GameMaker with Construct and GDevelop.

If your goal is a finished web game rather than learning an engine, starting from working source can save months. Our Phaser 4 games are TypeScript projects with tests, touch, mouse, keyboard and gamepad input, and an initial download of 300 to 750 KB. You can browse all 50 games and play each one in the browser first.

Frequently asked questions

Can I sell a game made with GameMaker's free version?

No. The free tier is for non-commercial use. As of October 2026, selling the game or earning from ads needs the one-time Professional licence, and consoles need the Enterprise subscription. Check GameMaker's pricing page for the current terms.

Why does my GameMaker HTML5 test work but the uploaded game shows a black screen?

The most common causes are file names that differ only in capital letters (servers are case-sensitive), files missing from the ZIP, or a host that sends the wrong content types. Open the browser console on the live page; a 403 or 404 error names the file.

Where can I find GameMaker HTML5 examples and games?

GX.games hosts many GameMaker games you can play in the browser, and itch.io lets you filter browser games by engine. GameMaker's own tutorials and templates make good test projects: export one to HTML5 and inspect what the build contains.

Is GameMaker HTML5 slower than a desktop build?

Usually, yes. The HTML5 target runs your game as JavaScript in a browser, without the compiled YYC option desktop builds can use. Most 2D games still run at full frame rate with WebGL on, but heavy logic or many particles show the gap first on phones.

We make and sell HTML5 game source code; links to our games are marked as ours.