[{"data":1,"prerenderedAt":1925},["ShallowReactive",2],{"navigation_docs_en":3,"-en-developers-build-android":272,"-en-developers-build-android-surround":1920},[4,38,110,190,232],{"title":5,"icon":6,"path":7,"stem":8,"children":9,"page":-1},"Getting started","i-lucide-rocket","\u002Fen\u002Fgetting-started","en\u002F1.getting-started\u002Findex",[10,13,18,23,28,33],{"title":11,"path":7,"stem":8,"icon":12},"Overview","i-lucide-layout-grid",{"title":14,"path":15,"stem":16,"icon":17},"Installation","\u002Fen\u002Fgetting-started\u002Finstallation","en\u002F1.getting-started\u002F01.installation","i-lucide-download",{"title":19,"path":20,"stem":21,"icon":22},"Sign in","\u002Fen\u002Fgetting-started\u002Fsign-in","en\u002F1.getting-started\u002F02.sign-in","i-lucide-log-in",{"title":24,"path":25,"stem":26,"icon":27},"Your first instance","\u002Fen\u002Fgetting-started\u002Ffirst-instance","en\u002F1.getting-started\u002F03.first-instance","i-lucide-play",{"title":29,"path":30,"stem":31,"icon":32},"Android: install the APK","\u002Fen\u002Fgetting-started\u002Fandroid","en\u002F1.getting-started\u002F04.android","i-lucide-smartphone",{"title":34,"path":35,"stem":36,"icon":37},"iPhone\u002FiPad: install with AltStore\u002FSideStore","\u002Fen\u002Fgetting-started\u002Fiphone-ipad","en\u002F1.getting-started\u002F05.iphone-ipad","i-lucide-tablet-smartphone",{"title":39,"icon":40,"path":41,"stem":42,"children":43,"page":-1},"Launcher","i-lucide-app-window","\u002Fen\u002Flauncher","en\u002F2.launcher\u002Findex",[44,45,50,55,60,65,70,75,80,85,90,95,100,105],{"title":11,"path":41,"stem":42,"icon":12},{"title":46,"path":47,"stem":48,"icon":49},"Instances","\u002Fen\u002Flauncher\u002Finstances","en\u002F2.launcher\u002F01.instances","i-lucide-boxes",{"title":51,"path":52,"stem":53,"icon":54},"Mod loaders","\u002Fen\u002Flauncher\u002Fmod-loaders","en\u002F2.launcher\u002F02.mod-loaders","i-lucide-layers",{"title":56,"path":57,"stem":58,"icon":59},"Mods","\u002Fen\u002Flauncher\u002Fmods","en\u002F2.launcher\u002F03.mods","i-lucide-puzzle",{"title":61,"path":62,"stem":63,"icon":64},"Modpacks","\u002Fen\u002Flauncher\u002Fmodpacks","en\u002F2.launcher\u002F04.modpacks","i-lucide-package",{"title":66,"path":67,"stem":68,"icon":69},"Share modpacks","\u002Fen\u002Flauncher\u002Fshare-modpacks","en\u002F2.launcher\u002F05.share-modpacks","i-lucide-share-2",{"title":71,"path":72,"stem":73,"icon":74},"Import from other launchers","\u002Fen\u002Flauncher\u002Fimport","en\u002F2.launcher\u002F06.import","i-lucide-folder-input",{"title":76,"path":77,"stem":78,"icon":79},"Clips & screenshots","\u002Fen\u002Flauncher\u002Fclips","en\u002F2.launcher\u002F07.clips","i-lucide-clapperboard",{"title":81,"path":82,"stem":83,"icon":84},"Friends & chat","\u002Fen\u002Flauncher\u002Fsocial","en\u002F2.launcher\u002F08.social","i-lucide-messages-square",{"title":86,"path":87,"stem":88,"icon":89},"Achievements","\u002Fen\u002Flauncher\u002Fachievements","en\u002F2.launcher\u002F09.achievements","i-lucide-trophy",{"title":91,"path":92,"stem":93,"icon":94},"Skins & capes","\u002Fen\u002Flauncher\u002Fwardrobe","en\u002F2.launcher\u002F10.wardrobe","i-lucide-shirt",{"title":96,"path":97,"stem":98,"icon":99},"Settings","\u002Fen\u002Flauncher\u002Fsettings","en\u002F2.launcher\u002F11.settings","i-lucide-settings",{"title":101,"path":102,"stem":103,"icon":104},"Updates","\u002Fen\u002Flauncher\u002Fupdates","en\u002F2.launcher\u002F12.updates","i-lucide-refresh-cw",{"title":106,"path":107,"stem":108,"icon":109},"Servers","\u002Fen\u002Flauncher\u002Fservers","en\u002F2.launcher\u002F13.servers","i-lucide-server",{"title":111,"icon":112,"path":113,"stem":114,"children":115,"page":-1},"TRS Client","i-lucide-blocks","\u002Fen\u002Fclient","en\u002F3.client\u002Findex",[116,117,121,126,131,136,141,146,151,156,160,165,170,175,180,185],{"title":11,"path":113,"stem":114,"icon":12},{"title":118,"path":119,"stem":120,"icon":112},"What is the TRS Client?","\u002Fen\u002Fclient\u002Foverview","en\u002F3.client\u002F01.overview",{"title":122,"path":123,"stem":124,"icon":125},"TRS menu and HUD editor","\u002Fen\u002Fclient\u002Fmenu-and-hud-editor","en\u002F3.client\u002F02.menu-and-hud-editor","i-lucide-layout-dashboard",{"title":127,"path":128,"stem":129,"icon":130},"Performance and FPS","\u002Fen\u002Fclient\u002Fperformance","en\u002F3.client\u002F03.performance","i-lucide-gauge",{"title":132,"path":133,"stem":134,"icon":135},"PvP modules","\u002Fen\u002Fclient\u002Fpvp","en\u002F3.client\u002F04.pvp","i-lucide-swords",{"title":137,"path":138,"stem":139,"icon":140},"Zoom, freelook and toggle sprint","\u002Fen\u002Fclient\u002Fzoom-and-freelook","en\u002F3.client\u002F05.zoom-and-freelook","i-lucide-zoom-in",{"title":142,"path":143,"stem":144,"icon":145},"Minimap, waypoints and world map","\u002Fen\u002Fclient\u002Fminimap-and-world-map","en\u002F3.client\u002F06.minimap-and-world-map","i-lucide-map",{"title":147,"path":148,"stem":149,"icon":150},"Redstone tools","\u002Fen\u002Fclient\u002Fredstone-tools","en\u002F3.client\u002F07.redstone-tools","i-lucide-zap",{"title":152,"path":153,"stem":154,"icon":155},"Circuit library","\u002Fen\u002Fclient\u002Fcircuit-library","en\u002F3.client\u002F08.circuit-library","i-lucide-cpu",{"title":157,"path":158,"stem":159,"icon":94},"Emotes, capes, wardrobe and accounts","\u002Fen\u002Fclient\u002Femotes-and-capes","en\u002F3.client\u002F09.emotes-and-capes",{"title":161,"path":162,"stem":163,"icon":164},"Screenshots, clips and panoramas","\u002Fen\u002Fclient\u002Fscreenshots-and-clips","en\u002F3.client\u002F10.screenshots-and-clips","i-lucide-camera",{"title":166,"path":167,"stem":168,"icon":169},"World notes","\u002Fen\u002Fclient\u002Fnotes","en\u002F3.client\u002F11.notes","i-lucide-notebook-pen",{"title":171,"path":172,"stem":173,"icon":174},"Chat and comfort","\u002Fen\u002Fclient\u002Fchat-and-comfort","en\u002F3.client\u002F12.chat-and-comfort","i-lucide-message-square",{"title":176,"path":177,"stem":178,"icon":179},"Social in game","\u002Fen\u002Fclient\u002Fsocial-in-game","en\u002F3.client\u002F13.social-in-game","i-lucide-users",{"title":181,"path":182,"stem":183,"icon":184},"Default keys","\u002Fen\u002Fclient\u002Fkeybinds","en\u002F3.client\u002F14.keybinds","i-lucide-keyboard",{"title":186,"path":187,"stem":188,"icon":189},"Host a world for friends","\u002Fen\u002Fclient\u002Fworld-hosting","en\u002F3.client\u002F15.world-hosting","i-lucide-globe",{"title":191,"icon":192,"path":193,"stem":194,"children":195,"page":-1},"Help","i-lucide-life-buoy","\u002Fen\u002Fhelp","en\u002F4.help\u002Findex",[196,197,202,207,212,217,222,227],{"title":11,"path":193,"stem":194,"icon":12},{"title":198,"path":199,"stem":200,"icon":201},"Crash helper","\u002Fen\u002Fhelp\u002Fcrash-helper","en\u002F4.help\u002F01.crash-helper","i-lucide-heart-pulse",{"title":203,"path":204,"stem":205,"icon":206},"Common problems","\u002Fen\u002Fhelp\u002Fcommon-problems","en\u002F4.help\u002F02.common-problems","i-lucide-circle-help",{"title":208,"path":209,"stem":210,"icon":211},"Java & memory","\u002Fen\u002Fhelp\u002Fjava","en\u002F4.help\u002F03.java","i-lucide-coffee",{"title":213,"path":214,"stem":215,"icon":216},"Linux","\u002Fen\u002Fhelp\u002Flinux","en\u002F4.help\u002F04.linux","i-lucide-terminal",{"title":218,"path":219,"stem":220,"icon":221},"Logs","\u002Fen\u002Fhelp\u002Flogs","en\u002F4.help\u002F05.logs","i-lucide-scroll-text",{"title":223,"path":224,"stem":225,"icon":226},"Report a bug","\u002Fen\u002Fhelp\u002Freport-a-bug","en\u002F4.help\u002F06.report-a-bug","i-lucide-bug",{"title":228,"path":229,"stem":230,"icon":231},"Privacy","\u002Fen\u002Fhelp\u002Fprivacy","en\u002F4.help\u002F07.privacy","i-lucide-shield-check",{"title":233,"icon":234,"path":235,"stem":236,"children":237,"page":-1},"Developers","i-lucide-code-xml","\u002Fen\u002Fdevelopers","en\u002F5.developers\u002Findex",[238,239,244,249,254,259,263,267],{"title":11,"path":235,"stem":236,"icon":12},{"title":240,"path":241,"stem":242,"icon":243},"Build from source","\u002Fen\u002Fdevelopers\u002Fbuild-from-source","en\u002F5.developers\u002F01.build-from-source","i-lucide-hammer",{"title":245,"path":246,"stem":247,"icon":248},"Contributing","\u002Fen\u002Fdevelopers\u002Fcontributing","en\u002F5.developers\u002F02.contributing","i-lucide-git-pull-request",{"title":250,"path":251,"stem":252,"icon":253},"Translating","\u002Fen\u002Fdevelopers\u002Ftranslating","en\u002F5.developers\u002F03.translating","i-lucide-languages",{"title":255,"path":256,"stem":257,"icon":258},"Public API","\u002Fen\u002Fdevelopers\u002Fpublic-api","en\u002F5.developers\u002F04.public-api","i-lucide-braces",{"title":260,"path":261,"stem":262,"icon":32},"Build the Android app yourself","\u002Fen\u002Fdevelopers\u002Fbuild-android","en\u002F5.developers\u002F05.build-android",{"title":264,"path":265,"stem":266,"icon":37},"Build the iOS app yourself with Xcode","\u002Fen\u002Fdevelopers\u002Fbuild-ios","en\u002F5.developers\u002F06.build-ios",{"title":268,"path":269,"stem":270,"icon":271},"TRS Server Rules","\u002Fen\u002Fdevelopers\u002Fserver-rules","en\u002F5.developers\u002F07.server-rules","i-lucide-server-cog",{"id":273,"title":260,"body":274,"description":1913,"extension":1914,"links":1915,"meta":1916,"navigation":1917,"path":261,"seo":1918,"stem":262,"__hash__":1919},"docs_en\u002Fen\u002F5.developers\u002F05.build-android.md",{"type":275,"value":276,"toc":1880},"minimark",[277,285,293,321,326,400,404,520,540,559,563,998,1009,1013,1037,1048,1052,1073,1088,1313,1339,1343,1350,1438,1481,1484,1516,1522,1526,1532,1600,1607,1683,1686,1690,1717,1721,1749,1753,1769,1773,1779,1783,1789,1793,1799,1803,1812,1816,1826,1830,1833,1837,1858,1861,1865,1876],[278,279,280,281,284],"p",{},"The Android app is the same Tauri 2 project as the desktop launcher, built for Android. This page is for contributors\nand for players who want to build and sideload their own APK. If you only want to play, take the signed APK from our\nwebsite – see ",[282,283,29],"a",{"href":30},".",[278,286,287,288,292],{},"What you get: the full app – sign-in, instances, modpacks, social, wardrobe and ",[289,290,291],"strong",{},"Minecraft: Java Edition"," through the\nbuilt-in game engine with the touch overlay. What you don't get: automatic updates. The app checks our official\nupdate channel, but Android only installs an update that has the same package name and the same signing key – your own\nbuild has a different key, so you update it by building again.",[294,295,296,297,301,302,305,306,309,310,313,314,316,317,320],"note",{},"The commands on this page are the ones the CI uses (",[298,299,300],"code",{},".github\u002Fworkflows\u002Fci.yml"," and ",[298,303,304],{},"release.yml",", jobs\n",[289,307,308],{},"Android",") plus the local notes from ",[298,311,312],{},"docs\u002Fmobile.md"," in the repository. The CI builds on ",[289,315,213],{},"; local builds are\ndescribed for ",[289,318,319],{},"Windows",". Building the Android app on macOS is not tested.",[322,323,325],"h2",{"id":324},"what-is-where","What is where",[327,328,329,342],"table",{},[330,331,332],"thead",{},[333,334,335,339],"tr",{},[336,337,338],"th",{},"Path",[336,340,341],{},"What it is",[343,344,345,356,366,376,390],"tbody",{},[333,346,347,353],{},[348,349,350],"td",{},[298,351,352],{},"src-tauri\u002Fgen\u002Fandroid\u002F",[348,354,355],{},"The Gradle project of the app (checked in, minSdk 26 = Android 8.0)",[333,357,358,363],{},[348,359,360],{},[298,361,362],{},"src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fbuild.gradle.kts",[348,364,365],{},"App ID, SDK levels, release signing",[333,367,368,373],{},[348,369,370],{},[298,371,372],{},"src-tauri\u002Ftauri.android.conf.json",[348,374,375],{},"Android overrides of the Tauri config (no desktop updater, no bundled TRS Client jars)",[333,377,378,383],{},[348,379,380],{},[298,381,382],{},"src-tauri\u002Fplugins\u002Ftauri-plugin-trs-game\u002Fandroid\u002F",[348,384,385,386,389],{},"The game engine (parts of Amethyst\u002FPojavLauncher, ",[298,387,388],{},"ndk-build",") and the touch overlay",[333,391,392,397],{},[348,393,394],{},[298,395,396],{},"src-tauri\u002Fplugins\u002Ftauri-plugin-trs-game\u002Fandroid\u002Fprebuilt.lock",[348,398,399],{},"Prebuilt engine parts that Gradle downloads and checks with SHA-256",[322,401,403],{"id":402},"requirements","Requirements",[327,405,406,416],{},[330,407,408],{},[333,409,410,413],{},[336,411,412],{},"Tool",[336,414,415],{},"Version (as in the CI)",[343,417,418,437,460,471,485,508],{},[333,419,420,423],{},[348,421,422],{},"Node.js and pnpm",[348,424,425,428,429,432,433,436],{},[289,426,427],{},"Node 22",", pnpm as pinned in ",[298,430,431],{},"package.json"," (",[298,434,435],{},"corepack enable",")",[333,438,439,442],{},[348,440,441],{},"Rust",[348,443,444,445,451,452,455,456,459],{},"stable via ",[282,446,450],{"href":447,"rel":448},"https:\u002F\u002Frustup.rs",[449],"nofollow","rustup",", targets ",[298,453,454],{},"aarch64-linux-android"," (phones) and ",[298,457,458],{},"x86_64-linux-android"," (emulator)",[333,461,462,465],{},[348,463,464],{},"JDK",[348,466,467,470],{},[289,468,469],{},"21"," (CI: Temurin; the JBR that comes with Android Studio works too)",[333,472,473,476],{},[348,474,475],{},"Android SDK",[348,477,478,479,301,482],{},"with ",[298,480,481],{},"cmdline-tools",[298,483,484],{},"platform-tools",[333,486,487,490],{},[348,488,489],{},"Android NDK",[348,491,492,495,496,499,500,503,504,507],{},[289,493,494],{},"28.2.13676358"," for the app (",[298,497,498],{},"NDK_HOME",") ",[289,501,502],{},"and"," ",[289,505,506],{},"27.3.13750724"," (r27d) for the game engine",[333,509,510,513],{},[348,511,512],{},"Gradle",[348,514,515,516,519],{},"nothing to install – the wrapper in ",[298,517,518],{},"src-tauri\u002Fgen\u002Fandroid"," uses Gradle 8.14.3",[278,521,522,523,432,526,529,530,533,534,536,537,284],{},"The app compiles against Android SDK ",[289,524,525],{},"36",[298,527,528],{},"compileSdk","\u002F",[298,531,532],{},"targetSdk","). In the CI only ",[298,535,484],{}," and the two NDKs\nare installed by hand; the rest comes through the Android Gradle plugin. Accept the SDK licenses once with\n",[298,538,539],{},"sdkmanager --licenses",[541,542,543,544,547,548,551,552,555,556,558],"warning",{},"You need ",[289,545,546],{},"both NDKs",". The game engine plugin pins ",[298,549,550],{},"ndkVersion = \"27.3.13750724\""," in its own ",[298,553,554],{},"build.gradle.kts","; the\nRust part is linked with the NDK from ",[298,557,498],{}," (28.2).",[322,560,562],{"id":561},"build-a-debug-apk","Build a debug APK",[564,565,567,572,616,620,673,684,688,691,805,816,820,850,865,869,876,962,966,973,992],"steps",{"level":566},"3",[568,569,571],"h3",{"id":570},"get-the-code","Get the code",[573,574,579],"pre",{"className":575,"code":576,"language":577,"meta":578,"style":578},"language-bash shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","git clone https:\u002F\u002Fgithub.com\u002Ftheredstonee\u002FTRS-Launcher.git\ncd TRS-Launcher\npnpm install\n","bash","",[298,580,581,597,607],{"__ignoreMap":578},[582,583,586,590,594],"span",{"class":584,"line":585},"line",1,[582,587,589],{"class":588},"sBMFI","git",[582,591,593],{"class":592},"sfazB"," clone",[582,595,596],{"class":592}," https:\u002F\u002Fgithub.com\u002Ftheredstonee\u002FTRS-Launcher.git\n",[582,598,600,604],{"class":584,"line":599},2,[582,601,603],{"class":602},"s2Zo4","cd",[582,605,606],{"class":592}," TRS-Launcher\n",[582,608,610,613],{"class":584,"line":609},3,[582,611,612],{"class":588},"pnpm",[582,614,615],{"class":592}," install\n",[568,617,619],{"id":618},"install-the-sdk-parts-and-rust-targets","Install the SDK parts and Rust targets",[573,621,623],{"className":575,"code":622,"language":577,"meta":578,"style":578},"sdkmanager --install \"platform-tools\" \"ndk;28.2.13676358\" \"ndk;27.3.13750724\"\nrustup target add aarch64-linux-android x86_64-linux-android\n",[298,624,625,657],{"__ignoreMap":578},[582,626,627,630,633,637,639,642,644,647,649,651,654],{"class":584,"line":585},[582,628,629],{"class":588},"sdkmanager",[582,631,632],{"class":592}," --install",[582,634,636],{"class":635},"sMK4o"," \"",[582,638,484],{"class":592},[582,640,641],{"class":635},"\"",[582,643,636],{"class":635},[582,645,646],{"class":592},"ndk;28.2.13676358",[582,648,641],{"class":635},[582,650,636],{"class":635},[582,652,653],{"class":592},"ndk;27.3.13750724",[582,655,656],{"class":635},"\"\n",[582,658,659,661,664,667,670],{"class":584,"line":599},[582,660,450],{"class":588},[582,662,663],{"class":592}," target",[582,665,666],{"class":592}," add",[582,668,669],{"class":592}," aarch64-linux-android",[582,671,672],{"class":592}," x86_64-linux-android\n",[278,674,675,676,679,680,683],{},"You can also install the two NDK versions in Android Studio (",[289,677,678],{},"SDK Manager → SDK Tools → NDK (Side by side)",", tick\n",[289,681,682],{},"Show Package Details",").",[568,685,687],{"id":686},"set-the-environment","Set the environment",[278,689,690],{},"On Windows (PowerShell) or Linux:",[692,693,694,743],"code-group",{},[573,695,699],{"className":696,"code":697,"filename":319,"language":698,"meta":578,"style":578},"language-shell shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","$env:ANDROID_HOME = \"$env:LOCALAPPDATA\\Android\\Sdk\"\n$env:NDK_HOME     = \"$env:ANDROID_HOME\\ndk\\28.2.13676358\"\n$env:JAVA_HOME    = \"C:\\Program Files\\Android\\Android Studio\\jbr\"\n","shell",[298,700,701,717,731],{"__ignoreMap":578},[582,702,703,707,709,712,715],{"class":584,"line":585},[582,704,706],{"class":705},"sTEyZ","$env:ANDROID_HOME = ",[582,708,641],{"class":635},[582,710,711],{"class":705},"$env",[582,713,714],{"class":592},":LOCALAPPDATA\\Android\\Sdk",[582,716,656],{"class":635},[582,718,719,722,724,726,729],{"class":584,"line":599},[582,720,721],{"class":705},"$env:NDK_HOME     = ",[582,723,641],{"class":635},[582,725,711],{"class":705},[582,727,728],{"class":592},":ANDROID_HOME\\ndk\\28.2.13676358",[582,730,656],{"class":635},[582,732,733,736,738,741],{"class":584,"line":609},[582,734,735],{"class":705},"$env:JAVA_HOME    = ",[582,737,641],{"class":635},[582,739,740],{"class":592},"C:\\Program Files\\Android\\Android Studio\\jbr",[582,742,656],{"class":635},[573,744,746],{"className":575,"code":745,"filename":213,"language":577,"meta":578,"style":578},"export ANDROID_HOME=\"$HOME\u002FAndroid\u002FSdk\"          # where your SDK is\nexport NDK_HOME=\"$ANDROID_HOME\u002Fndk\u002F28.2.13676358\"\nexport JAVA_HOME=\u002Fpath\u002Fto\u002Fjdk-21\n",[298,747,748,774,793],{"__ignoreMap":578},[582,749,750,754,757,760,762,765,768,770],{"class":584,"line":585},[582,751,753],{"class":752},"spNyl","export",[582,755,756],{"class":705}," ANDROID_HOME",[582,758,759],{"class":635},"=",[582,761,641],{"class":635},[582,763,764],{"class":705},"$HOME",[582,766,767],{"class":592},"\u002FAndroid\u002FSdk",[582,769,641],{"class":635},[582,771,773],{"class":772},"sHwdD","          # where your SDK is\n",[582,775,776,778,781,783,785,788,791],{"class":584,"line":599},[582,777,753],{"class":752},[582,779,780],{"class":705}," NDK_HOME",[582,782,759],{"class":635},[582,784,641],{"class":635},[582,786,787],{"class":705},"$ANDROID_HOME",[582,789,790],{"class":592},"\u002Fndk\u002F28.2.13676358",[582,792,656],{"class":635},[582,794,795,797,800,802],{"class":584,"line":609},[582,796,753],{"class":752},[582,798,799],{"class":705}," JAVA_HOME",[582,801,759],{"class":635},[582,803,804],{"class":705},"\u002Fpath\u002Fto\u002Fjdk-21\n",[278,806,807,808,811,812,284],{},"On Windows, turn on ",[289,809,810],{},"Developer Mode"," first – see ",[282,813,815],{"href":814},"#a-required-privilege-is-not-held-by-the-client","Troubleshooting",[568,817,819],{"id":818},"build","Build",[573,821,823],{"className":575,"code":822,"language":577,"meta":578,"style":578},"pnpm tauri android build --apk --debug --target aarch64\n",[298,824,825],{"__ignoreMap":578},[582,826,827,829,832,835,838,841,844,847],{"class":584,"line":585},[582,828,612],{"class":588},[582,830,831],{"class":592}," tauri",[582,833,834],{"class":592}," android",[582,836,837],{"class":592}," build",[582,839,840],{"class":592}," --apk",[582,842,843],{"class":592}," --debug",[582,845,846],{"class":592}," --target",[582,848,849],{"class":592}," aarch64\n",[278,851,852,853,856,857,860,861,864],{},"This builds the frontend (",[298,854,855],{},"pnpm generate","), the Rust library for arm64 and then the APK with Gradle. The first Gradle\nrun downloads the prebuilt engine parts from ",[298,858,859],{},"prebuilt.lock"," (checked with SHA-256, cached in\n",[298,862,863],{},"~\u002F.gradle\u002Fcaches\u002Ftrs-engine-prebuilt","), so it needs internet and takes a while.",[568,866,868],{"id":867},"find-the-apk","Find the APK",[278,870,871,872,875],{},"The APKs end up under ",[298,873,874],{},"src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fbuild\u002Foutputs\u002Fapk\u002F",", in a folder per ABI and build type. The CI\ndoesn't rely on the exact folder name, and you don't have to either:",[692,877,878,903],{},[573,879,881],{"className":575,"code":880,"filename":213,"language":577,"meta":578,"style":578},"find src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fbuild\u002Foutputs\u002Fapk -name '*.apk'\n",[298,882,883],{"__ignoreMap":578},[582,884,885,888,891,894,897,900],{"class":584,"line":585},[582,886,887],{"class":588},"find",[582,889,890],{"class":592}," src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fbuild\u002Foutputs\u002Fapk",[582,892,893],{"class":592}," -name",[582,895,896],{"class":635}," '",[582,898,899],{"class":592},"*.apk",[582,901,902],{"class":635},"'\n",[573,904,906],{"className":696,"code":905,"filename":319,"language":698,"meta":578,"style":578},"Get-ChildItem -Recurse -Filter *.apk src-tauri\\gen\\android\\app\\build\\outputs\\apk\n",[298,907,908],{"__ignoreMap":578},[582,909,910,913,916,919,922,925,928,931,934,937,940,942,945,948,951,954,957,959],{"class":584,"line":585},[582,911,912],{"class":588},"Get-ChildItem",[582,914,915],{"class":592}," -Recurse",[582,917,918],{"class":592}," -Filter",[582,920,921],{"class":705}," *",[582,923,924],{"class":592},".apk",[582,926,927],{"class":592}," src-tauri",[582,929,930],{"class":705},"\\g",[582,932,933],{"class":592},"en",[582,935,936],{"class":705},"\\a",[582,938,939],{"class":592},"ndroid",[582,941,936],{"class":705},[582,943,944],{"class":592},"pp",[582,946,947],{"class":705},"\\b",[582,949,950],{"class":592},"uild",[582,952,953],{"class":705},"\\o",[582,955,956],{"class":592},"utputs",[582,958,936],{"class":705},[582,960,961],{"class":592},"pk\n",[568,963,965],{"id":964},"install-it-on-your-phone","Install it on your phone",[278,967,968,969,972],{},"Turn on ",[289,970,971],{},"USB debugging"," in the developer options of your phone, connect it and run:",[573,974,976],{"className":575,"code":975,"language":577,"meta":578,"style":578},"adb install -r path\u002Fto\u002Fthe.apk\n",[298,977,978],{"__ignoreMap":578},[582,979,980,983,986,989],{"class":584,"line":585},[582,981,982],{"class":588},"adb",[582,984,985],{"class":592}," install",[582,987,988],{"class":592}," -r",[582,990,991],{"class":592}," path\u002Fto\u002Fthe.apk\n",[278,993,994,995,997],{},"Or copy the APK to the phone and open it there, as described in ",[282,996,29],{"href":30},".\nA debug APK is signed with the debug key of your Android SDK, so it installs right away.",[541,999,1000,1001,1004,1005,683],{},"A debug build and our official app have the ",[289,1002,1003],{},"same package name but different keys",". Android refuses to install one\nover the other (\"App not installed\" \u002F \"conflicts with an existing package\"). Uninstall the other one first – that also\ndeletes its instances and worlds – or give your build its own app ID (see ",[282,1006,1008],{"href":1007},"#make-it-your-own-app","below",[568,1010,1012],{"id":1011},"for-the-emulator","For the emulator",[573,1014,1016],{"className":575,"code":1015,"language":577,"meta":578,"style":578},"pnpm tauri android build --apk --debug --target x86_64\n",[298,1017,1018],{"__ignoreMap":578},[582,1019,1020,1022,1024,1026,1028,1030,1032,1034],{"class":584,"line":585},[582,1021,612],{"class":588},[582,1023,831],{"class":592},[582,1025,834],{"class":592},[582,1027,837],{"class":592},[582,1029,840],{"class":592},[582,1031,843],{"class":592},[582,1033,846],{"class":592},[582,1035,1036],{"class":592}," x86_64\n",[278,1038,1039,1040,1043,1044,1047],{},"Start the emulator with ",[298,1041,1042],{},"-gpu host"," – with SwiftShader the renderer crashes in its Vulkan check. Minecraft ",[289,1045,1046],{},"26.x"," can't\nbe played in the emulator (its Vulkan lacks the needed extensions and OpenGL hangs there); test those versions on a\nreal phone.",[322,1049,1051],{"id":1050},"build-a-release-apk","Build a release APK",[573,1053,1055],{"className":575,"code":1054,"language":577,"meta":578,"style":578},"pnpm tauri android build --apk --target aarch64\n",[298,1056,1057],{"__ignoreMap":578},[582,1058,1059,1061,1063,1065,1067,1069,1071],{"class":584,"line":585},[582,1060,612],{"class":588},[582,1062,831],{"class":592},[582,1064,834],{"class":592},[582,1066,837],{"class":592},[582,1068,840],{"class":592},[582,1070,846],{"class":592},[582,1072,849],{"class":592},[278,1074,1075,1076,1079,1080,1083,1084,1087],{},"That is the release command of the CI without ",[298,1077,1078],{},"--ci",". Release builds are minified with R8. Without a signing key the\nresult is an ",[289,1081,1082],{},"unsigned"," APK (",[298,1085,1086],{},"…-unsigned.apk",") – Android can't install that. Sign it with your own key:",[564,1089,1090,1094,1146,1151,1155,1169,1234,1241,1245,1298],{"level":566},[568,1091,1093],{"id":1092},"create-a-keystore-once","Create a keystore once",[573,1095,1097],{"className":575,"code":1096,"language":577,"meta":578,"style":578},"keytool -genkeypair -v -keystore my-release.jks -alias my-key \\\n  -keyalg RSA -keysize 4096 -validity 10000\n",[298,1098,1099,1125],{"__ignoreMap":578},[582,1100,1101,1104,1107,1110,1113,1116,1119,1122],{"class":584,"line":585},[582,1102,1103],{"class":588},"keytool",[582,1105,1106],{"class":592}," -genkeypair",[582,1108,1109],{"class":592}," -v",[582,1111,1112],{"class":592}," -keystore",[582,1114,1115],{"class":592}," my-release.jks",[582,1117,1118],{"class":592}," -alias",[582,1120,1121],{"class":592}," my-key",[582,1123,1124],{"class":705}," \\\n",[582,1126,1127,1130,1133,1136,1140,1143],{"class":584,"line":599},[582,1128,1129],{"class":592},"  -keyalg",[582,1131,1132],{"class":592}," RSA",[582,1134,1135],{"class":592}," -keysize",[582,1137,1139],{"class":1138},"sbssI"," 4096",[582,1141,1142],{"class":592}," -validity",[582,1144,1145],{"class":1138}," 10000\n",[278,1147,1148,1150],{},[298,1149,1103],{}," comes with the JDK. Keep the file and the passwords safe: Android only installs updates of an app that are\nsigned with the same key.",[568,1152,1154],{"id":1153},"set-the-four-variables","Set the four variables",[278,1156,1157,1158,1161,1162,1164,1165,1168],{},"Gradle signs the release APK itself (",[298,1159,1160],{},"signingConfigs"," in ",[298,1163,362],{},") when\n",[298,1166,1167],{},"ANDROID_KEYSTORE_PATH"," points to an existing file:",[573,1170,1172],{"className":575,"code":1171,"language":577,"meta":578,"style":578},"export ANDROID_KEYSTORE_PATH=\u002Fpath\u002Fto\u002Fmy-release.jks\nexport ANDROID_KEYSTORE_PASSWORD='…'\nexport ANDROID_KEY_ALIAS=my-key\nexport ANDROID_KEY_PASSWORD='…'      # same as the keystore password unless you chose another one\n",[298,1173,1174,1186,1203,1215],{"__ignoreMap":578},[582,1175,1176,1178,1181,1183],{"class":584,"line":585},[582,1177,753],{"class":752},[582,1179,1180],{"class":705}," ANDROID_KEYSTORE_PATH",[582,1182,759],{"class":635},[582,1184,1185],{"class":705},"\u002Fpath\u002Fto\u002Fmy-release.jks\n",[582,1187,1188,1190,1193,1195,1198,1201],{"class":584,"line":599},[582,1189,753],{"class":752},[582,1191,1192],{"class":705}," ANDROID_KEYSTORE_PASSWORD",[582,1194,759],{"class":635},[582,1196,1197],{"class":635},"'",[582,1199,1200],{"class":592},"…",[582,1202,902],{"class":635},[582,1204,1205,1207,1210,1212],{"class":584,"line":609},[582,1206,753],{"class":752},[582,1208,1209],{"class":705}," ANDROID_KEY_ALIAS",[582,1211,759],{"class":635},[582,1213,1214],{"class":705},"my-key\n",[582,1216,1218,1220,1223,1225,1227,1229,1231],{"class":584,"line":1217},4,[582,1219,753],{"class":752},[582,1221,1222],{"class":705}," ANDROID_KEY_PASSWORD",[582,1224,759],{"class":635},[582,1226,1197],{"class":635},[582,1228,1200],{"class":592},[582,1230,1197],{"class":635},[582,1232,1233],{"class":772},"      # same as the keystore password unless you chose another one\n",[278,1235,1236,1237,1240],{},"On Windows set them with ",[298,1238,1239],{},"$env:NAME = \"…\""," like above.",[568,1242,1244],{"id":1243},"build-and-check","Build and check",[573,1246,1248],{"className":575,"code":1247,"language":577,"meta":578,"style":578},"pnpm tauri android build --apk --target aarch64\n\"$ANDROID_HOME\"\u002Fbuild-tools\u002F\u003Cversion>\u002Fapksigner verify --print-certs \u003Cthe.apk>\n",[298,1249,1250,1266],{"__ignoreMap":578},[582,1251,1252,1254,1256,1258,1260,1262,1264],{"class":584,"line":585},[582,1253,612],{"class":588},[582,1255,831],{"class":592},[582,1257,834],{"class":592},[582,1259,837],{"class":592},[582,1261,840],{"class":592},[582,1263,846],{"class":592},[582,1265,849],{"class":592},[582,1267,1268,1270,1272,1274,1277,1280,1283,1286,1289,1292,1295],{"class":584,"line":599},[582,1269,641],{"class":588},[582,1271,787],{"class":705},[582,1273,641],{"class":588},[582,1275,1276],{"class":588},"\u002Fbuild-tools\u002F",[582,1278,1279],{"class":705},"\u003Cversion>\u002Fapksigner ",[582,1281,1282],{"class":592},"verify",[582,1284,1285],{"class":592}," --print-certs",[582,1287,1288],{"class":635}," \u003C",[582,1290,1291],{"class":592},"the.ap",[582,1293,1294],{"class":705},"k",[582,1296,1297],{"class":635},">\n",[278,1299,1300,1303,1304,1307,1308,1312],{},[298,1301,1302],{},"apksigner"," shows the SHA-256 of ",[289,1305,1306],{},"your"," certificate – not the one listed on the\n",[282,1309,1311],{"href":1310},"\u002Fen\u002Fgetting-started\u002Fandroid#install","install page",", which belongs to our official key.",[294,1314,1315,1316,1319,1320,1323,1324,1327,1328,1331,1332,432,1335,1338],{},"You don't need any of the project's secrets. The desktop updater key (",[298,1317,1318],{},"TAURI_SIGNING_PRIVATE_KEY",") only signs the update\nchannel files in the release workflow, and Android builds don't create updater files anyway\n(",[298,1321,1322],{},"tauri.android.conf.json","). The ",[289,1325,1326],{},"CurseForge"," key is optional, exactly as on the desktop: the environment variable\n",[298,1329,1330],{},"CURSEFORGE_API_KEY"," or the file ",[298,1333,1334],{},"~\u002F.tauri\u002Fcurseforge-api-key",[298,1336,1337],{},"%USERPROFILE%\\.tauri\\curseforge-api-key"," on\nWindows). Without it the build works and simply hides CurseForge.",[322,1340,1342],{"id":1341},"make-it-your-own-app","Make it your own app",[278,1344,1345,1346,1349],{},"If you want to install your build ",[289,1347,1348],{},"next to"," the official app or share it with friends, give it its own app ID and\nname:",[327,1351,1352,1365],{},[330,1353,1354],{},[333,1355,1356,1359,1362],{},[336,1357,1358],{},"What",[336,1360,1361],{},"Where",[336,1363,1364],{},"Change",[343,1366,1367,1385,1403,1423],{},[333,1368,1369,1372,1376],{},[348,1370,1371],{},"App ID (package name)",[348,1373,1374],{},[298,1375,362],{},[348,1377,1378,1381,1382],{},[298,1379,1380],{},"applicationId = \"dev.theredstonee.trslauncher\""," → for example ",[298,1383,1384],{},"\"io.github.yourname.trslauncher\"",[333,1386,1387,1390,1395],{},[348,1388,1389],{},"Name on the home screen",[348,1391,1392],{},[298,1393,1394],{},"src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fsrc\u002Fmain\u002Fres\u002Fvalues\u002Fstrings.xml",[348,1396,1397,301,1400],{},[298,1398,1399],{},"app_name",[298,1401,1402],{},"main_activity_title",[333,1404,1405,1408,1413],{},[348,1406,1407],{},"Icon",[348,1409,1410],{},[298,1411,1412],{},"src-tauri\u002Fgen\u002Fandroid\u002Fapp\u002Fsrc\u002Fmain\u002Fres\u002Fmipmap-*\u002F",[348,1414,1415,1418,1419,1422],{},[298,1416,1417],{},"ic_launcher*.png"," (the ",[298,1420,1421],{},"ic_launcher_halloween*"," files are the event icon)",[333,1424,1425,1428,1431],{},[348,1426,1427],{},"Signing key",[348,1429,1430],{},"your own keystore",[348,1432,1433,1434],{},"see ",[282,1435,1437],{"href":1436},"#build-a-release-apk","above",[541,1439,1440,1441,1447,1448,1451,1452,1161,1455,1458,1459,1462,1463,1466,1467,1470,1471,1466,1474,1477,1478,1480],{},"Change ",[289,1442,1443,1444],{},"only ",[298,1445,1446],{},"applicationId"," – not ",[298,1449,1450],{},"namespace"," in the same file and not ",[298,1453,1454],{},"identifier",[298,1456,1457],{},"src-tauri\u002Ftauri.conf.json",".\nThe Kotlin package ",[298,1460,1461],{},"dev.theredstonee.trslauncher"," is wired into the Rust code (",[298,1464,1465],{},"register_android_plugin"," in\n",[298,1468,1469],{},"src-tauri\u002Fsrc\u002Fmobile.rs",", the JNI function ",[298,1472,1473],{},"Java_dev_theredstonee_trslauncher_PushPollWorker_nativePoll",[298,1475,1476],{},"src-tauri\u002Fsrc\u002Fpush.rs","), and the Tauri CLI stops the build with \"you have modified your \"identifier\" in the Tauri\nconfiguration\" when the identifier no longer matches the Kotlin folder. The engine and push plugins read the package\nname at runtime, so a new ",[298,1479,1446],{}," is fine for them.",[278,1482,1483],{},"What still works in your own build, according to the code:",[1485,1486,1487,1494,1500,1510],"ul",{},[1488,1489,1490,1493],"li",{},[289,1491,1492],{},"Microsoft sign-in:"," the app uses Microsoft's device-code sign-in (you type a code on Microsoft's page). It doesn't\ndepend on the package name or a redirect into the app.",[1488,1495,1496,1499],{},[289,1497,1498],{},"TRS services"," (friends, chat, capes, TRS API): the app talks to the same API; there is no check of the package\nname or signature.",[1488,1501,1502,1505,1506,1509],{},[289,1503,1504],{},"Links"," like ",[298,1507,1508],{},"trs-launcher:\u002F\u002Fpack\u002F\u003Ccode>"," use the same scheme in every build. With the official app and your build\ninstalled side by side, Android asks which app should open them.",[1488,1511,1512,1515],{},[289,1513,1514],{},"Updates:"," see the top of the page. The in-app installer only accepts an APK for its own package name, so it can't\nreplace your build with the official one, and Android rejects our APK over a build with your key.",[278,1517,1518,1519,284],{},"We haven't tested a renamed build ourselves – if something breaks, please ",[282,1520,1521],{"href":224},"report it",[322,1523,1525],{"id":1524},"run-the-checks","Run the checks",[278,1527,1528,1529,1531],{},"The same checks as the CI job ",[289,1530,308],{},":",[573,1533,1535],{"className":575,"code":1534,"language":577,"meta":578,"style":578},"pnpm generate                       # generate_context! needs the built frontend\ncd src-tauri\ncargo clippy --workspace --target aarch64-linux-android -- -D warnings\ncd gen\u002Fandroid\n.\u002Fgradlew --no-daemon :tauri-plugin-trs-game:testDebugUnitTest   # touch overlay and engine logic, no device\n",[298,1536,1537,1547,1554,1578,1585],{"__ignoreMap":578},[582,1538,1539,1541,1544],{"class":584,"line":585},[582,1540,612],{"class":588},[582,1542,1543],{"class":592}," generate",[582,1545,1546],{"class":772},"                       # generate_context! needs the built frontend\n",[582,1548,1549,1551],{"class":584,"line":599},[582,1550,603],{"class":602},[582,1552,1553],{"class":592}," src-tauri\n",[582,1555,1556,1559,1562,1565,1567,1569,1572,1575],{"class":584,"line":609},[582,1557,1558],{"class":588},"cargo",[582,1560,1561],{"class":592}," clippy",[582,1563,1564],{"class":592}," --workspace",[582,1566,846],{"class":592},[582,1568,669],{"class":592},[582,1570,1571],{"class":592}," --",[582,1573,1574],{"class":592}," -D",[582,1576,1577],{"class":592}," warnings\n",[582,1579,1580,1582],{"class":584,"line":1217},[582,1581,603],{"class":602},[582,1583,1584],{"class":592}," gen\u002Fandroid\n",[582,1586,1588,1591,1594,1597],{"class":584,"line":1587},5,[582,1589,1590],{"class":588},".\u002Fgradlew",[582,1592,1593],{"class":592}," --no-daemon",[582,1595,1596],{"class":592}," :tauri-plugin-trs-game:testDebugUnitTest",[582,1598,1599],{"class":772},"   # touch overlay and engine logic, no device\n",[278,1601,1602,1603,1606],{},"Clippy runs outside ",[298,1604,1605],{},"tauri android build"," and needs the NDK compiler for the C parts (SQLite, ring). The CI sets these\non Linux:",[573,1608,1610],{"className":575,"code":1609,"language":577,"meta":578,"style":578},"bin=\"$NDK_HOME\u002Ftoolchains\u002Fllvm\u002Fprebuilt\u002Flinux-x86_64\u002Fbin\"\nexport CC_aarch64_linux_android=\"$bin\u002Faarch64-linux-android26-clang\"\nexport AR_aarch64_linux_android=\"$bin\u002Fllvm-ar\"\nexport CARGO_TARGET_AARCH64_LINUX_ANDROID_LINKER=\"$bin\u002Faarch64-linux-android26-clang\"\n",[298,1611,1612,1629,1648,1666],{"__ignoreMap":578},[582,1613,1614,1617,1619,1621,1624,1627],{"class":584,"line":585},[582,1615,1616],{"class":705},"bin",[582,1618,759],{"class":635},[582,1620,641],{"class":635},[582,1622,1623],{"class":705},"$NDK_HOME",[582,1625,1626],{"class":592},"\u002Ftoolchains\u002Fllvm\u002Fprebuilt\u002Flinux-x86_64\u002Fbin",[582,1628,656],{"class":635},[582,1630,1631,1633,1636,1638,1640,1643,1646],{"class":584,"line":599},[582,1632,753],{"class":752},[582,1634,1635],{"class":705}," CC_aarch64_linux_android",[582,1637,759],{"class":635},[582,1639,641],{"class":635},[582,1641,1642],{"class":705},"$bin",[582,1644,1645],{"class":592},"\u002Faarch64-linux-android26-clang",[582,1647,656],{"class":635},[582,1649,1650,1652,1655,1657,1659,1661,1664],{"class":584,"line":609},[582,1651,753],{"class":752},[582,1653,1654],{"class":705}," AR_aarch64_linux_android",[582,1656,759],{"class":635},[582,1658,641],{"class":635},[582,1660,1642],{"class":705},[582,1662,1663],{"class":592},"\u002Fllvm-ar",[582,1665,656],{"class":635},[582,1667,1668,1670,1673,1675,1677,1679,1681],{"class":584,"line":1217},[582,1669,753],{"class":752},[582,1671,1672],{"class":705}," CARGO_TARGET_AARCH64_LINUX_ANDROID_LINKER",[582,1674,759],{"class":635},[582,1676,641],{"class":635},[582,1678,1642],{"class":705},[582,1680,1645],{"class":592},[582,1682,656],{"class":635},[322,1684,815],{"id":1685},"troubleshooting",[568,1687,1689],{"id":1688},"a-required-privilege-is-not-held-by-the-client","\"A required privilege is not held by the client\"",[278,1691,1692,1693,1695,1696,1699,1700,1702,1703,1706,1707,1710,1711,1713,1714,284],{},"On Windows, ",[298,1694,1605],{}," links the Rust library into ",[298,1697,1698],{},"gen\u002Fandroid\u002Fapp\u002Fsrc\u002Fmain\u002FjniLibs"," with a symbolic link.\nWithout ",[289,1701,810],{}," (or admin rights) that fails. Turn on Developer Mode in the Windows settings, or copy the\nlibrary yourself (",[298,1704,1705],{},"src-tauri\u002Ftarget\u002F\u003Ctriple>\u002Fdebug\u002Flibtrs_launcher_lib.so"," → ",[298,1708,1709],{},"jniLibs\u002F\u003Cabi>\u002F",") and run the Gradle task\nin ",[298,1712,518],{},", for the emulator ",[298,1715,1716],{},"gradlew assembleX86_64Debug",[568,1718,1720],{"id":1719},"ndk-not-found-or-wrong-ndk-version","NDK not found or wrong NDK version",[278,1722,1723,1725,1726,1728,1729,1731,1732,1735,1736,1161,1739,1742,1743,1746,1747,683],{},[298,1724,498],{}," must point to ",[289,1727,494],{},", and ",[289,1730,506],{}," must be installed in the SDK's ",[298,1733,1734],{},"ndk\u002F"," folder as well.\nIf your r27d lives somewhere else, set ",[298,1737,1738],{},"android.ndkPath",[298,1740,1741],{},"src-tauri\u002Fgen\u002Fandroid\u002Flocal.properties"," or the variable\n",[298,1744,1745],{},"ANDROID_NDK_HOME"," (see the comment in the plugin's ",[298,1748,554],{},[568,1750,1752],{"id":1751},"the-sdk-setup-asks-for-the-package-tools","The SDK setup asks for the package \"tools\"",[278,1754,1755,1756,1759,1760,1762,1763,1765,1766,1768],{},"The old SDK package ",[298,1757,1758],{},"tools"," doesn't exist any more with current ",[298,1761,481],{},". Install only ",[298,1764,481],{},",\n",[298,1767,484],{}," and the two NDKs – the CI does the same.",[568,1770,1772],{"id":1771},"the-release-apk-doesnt-install","The release APK doesn't install",[278,1774,1775,1776,1778],{},"It is unsigned (",[298,1777,1086],{},"). Set the four signing variables and build again, or use a debug build.",[568,1780,1782],{"id":1781},"app-not-installed-or-conflicts-with-an-existing-package","\"App not installed\" or \"conflicts with an existing package\"",[278,1784,1785,1786,284],{},"Another build of the app with a different key is installed – often our official app. Uninstall it first (this removes\nits instances) or give your build its own ",[282,1787,1788],{"href":1007},"app ID",[568,1790,1792],{"id":1791},"sha-256-stimmt-nicht-while-gradle-downloads-the-engine-parts","\"SHA-256 stimmt nicht\" while Gradle downloads the engine parts",[278,1794,1795,1796,1798],{},"A download from ",[298,1797,859],{}," didn't match its checksum (for example a broken connection or a proxy). The file is\nthrown away; run the build again.",[568,1800,1802],{"id":1801},"the-game-crashes-in-the-emulator-or-26x-doesnt-start-there","The game crashes in the emulator or 26.x doesn't start there",[278,1804,1805,1806,1808,1809,683],{},"Use ",[298,1807,1042],{},", and test Minecraft 26.x on a real phone (see ",[282,1810,1012],{"href":1811},"#for-the-emulator",[568,1813,1815],{"id":1814},"the-app-cant-be-installed-on-an-older-or-32-bit-phone","The app can't be installed on an older or 32-bit phone",[278,1817,1818,1819,301,1822,1825],{},"The app needs Android 8.0 and a 64-bit processor: only ",[298,1820,1821],{},"arm64-v8a",[298,1823,1824],{},"x86_64"," are packaged because the game engine\nexists only for 64 bit.",[568,1827,1829],{"id":1828},"curseforge-is-missing","CurseForge is missing",[278,1831,1832],{},"The build had no CurseForge API key. That's expected for own builds – see the note on the key above.",[322,1834,1836],{"id":1835},"license-and-name","License and name",[278,1838,1839,1840,432,1843,1846,1847,1850,1851,1854,1855,1857],{},"TRS Launcher is free software under the ",[289,1841,1842],{},"GNU General Public License v3.0",[298,1844,1845],{},"LICENSE",", copyright notices in ",[298,1848,1849],{},"NOTICE",").\nYou may build, change and share the app. If you share an APK, the GPL requires that you share it under the same license\nand make the ",[289,1852,1853],{},"complete source code"," of exactly that build available, including your changes. The game engine\ncontains third-party parts with their own licenses (Amethyst\u002FPojavLauncher under LGPL-3.0 and more) – they are listed\nin ",[298,1856,1849],{}," and must stay in.",[278,1859,1860],{},"The repository has no separate trademark rules. Still: if you hand out your own build, give it its own name and app ID\nso nobody mistakes it for the official TRS Launcher, and point people to your source code – not to our support.",[322,1862,1864],{"id":1863},"next-steps","Next steps",[1866,1867,1868,1873],"card-group",{},[1869,1870,1872],"card",{"icon":37,"title":1871,"to":265},"Build the iOS app yourself","The same for iPhone and iPad – needs a Mac with Xcode.",[1869,1874,1875],{"icon":243,"title":240,"to":241},"The desktop launcher, the checks and the TRS Client mod.",[1877,1878,1879],"style",{},"html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .spNyl, html code.shiki .spNyl{--shiki-light:#9C3EDA;--shiki-default:#C792EA;--shiki-dark:#C792EA}html pre.shiki code .sHwdD, html code.shiki .sHwdD{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#546E7A;--shiki-default-font-style:italic;--shiki-dark:#676E95;--shiki-dark-font-style:italic}html pre.shiki code .sbssI, html code.shiki .sbssI{--shiki-light:#F76D47;--shiki-default:#F78C6C;--shiki-dark:#F78C6C}",{"title":578,"searchDepth":599,"depth":599,"links":1881},[1882,1883,1884,1893,1898,1899,1900,1911,1912],{"id":324,"depth":599,"text":325},{"id":402,"depth":599,"text":403},{"id":561,"depth":599,"text":562,"children":1885},[1886,1887,1888,1889,1890,1891,1892],{"id":570,"depth":609,"text":571},{"id":618,"depth":609,"text":619},{"id":686,"depth":609,"text":687},{"id":818,"depth":609,"text":819},{"id":867,"depth":609,"text":868},{"id":964,"depth":609,"text":965},{"id":1011,"depth":609,"text":1012},{"id":1050,"depth":599,"text":1051,"children":1894},[1895,1896,1897],{"id":1092,"depth":609,"text":1093},{"id":1153,"depth":609,"text":1154},{"id":1243,"depth":609,"text":1244},{"id":1341,"depth":599,"text":1342},{"id":1524,"depth":599,"text":1525},{"id":1685,"depth":599,"text":815,"children":1901},[1902,1903,1904,1905,1906,1907,1908,1909,1910],{"id":1688,"depth":609,"text":1689},{"id":1719,"depth":609,"text":1720},{"id":1751,"depth":609,"text":1752},{"id":1771,"depth":609,"text":1772},{"id":1781,"depth":609,"text":1782},{"id":1791,"depth":609,"text":1792},{"id":1801,"depth":609,"text":1802},{"id":1814,"depth":609,"text":1815},{"id":1828,"depth":609,"text":1829},{"id":1835,"depth":599,"text":1836},{"id":1863,"depth":599,"text":1864},"Build the TRS Launcher APK from source: Android SDK and NDK, Rust targets, debug and release builds, your own signing key and your own app ID.","md",null,{},{"icon":32},{"title":260,"description":1913},"0B_934SigdtV1m1dtTNoCi8Ke77g4zkwCmGuuSvHWfE",[1921,1923],{"title":255,"path":256,"stem":257,"description":1922,"icon":258,"children":-1},"Read-only TRS API endpoints you can use without an account – status, releases, capes, circuits, modpack codes, blog, issues, team and achievements.",{"title":264,"path":265,"stem":266,"description":1924,"icon":37,"children":-1},"Build the TRS Launcher IPA for iPhone and iPad on a Mac: Xcode project, Rust library, game engine, sideloading and running it with your own Apple ID.",1792830333699]