1
Fork 0
mirror of https://github.com/redstrate/Kawari.git synced 2025-05-06 20:57:45 +00:00

Add Bootstrap styling for the launcher page, implement launcher login

Instead of the placeholder SID, it sets it to an actual one that can be
used with the lobby server.
This commit is contained in:
Joshua Goins 2025-05-03 18:16:36 -04:00
parent a9ec268a4f
commit def9b4ab48
3 changed files with 174 additions and 120 deletions

View file

@ -1,14 +1,21 @@
<!DOCTYPE html> {% extends "layout.html" %}
<html lang=en>
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge;">
<title>Kawari Launcher</title>
</head>
<body> {% block title %}Kawari Launcher{% endblock %}
{% block body %}
<p>Welcome to Kawari!</p> <p>Welcome to Kawari!</p>
<form id="login">
<label for="sqexid" class="form-label">Username</label><br>
<input type='text' id='sqexid' name='sqexid' class="form-control"/><br>
<label for="password" class="form-label">Password</label><br>
<input id='password' name='password' class="form-control" type="password"/><br>
<label for="otppw" class="form-label">One-Time Password</label><br>
<input type='text' id='otppw' name='otppw' class="form-control"/><br>
<input type="hidden" id="_STORED_" name="_STORED_" value="34657" />
<button type='submit' class="btn btn-primary">Login</button>
</form>
<input type="button" value="System Info" onclick="window.external.user('systemInfo');" /> <input type="button" value="System Info" onclick="window.external.user('systemInfo');" />
<input type="button" value="Play" onclick="window.external.user('startPlay');" /> <input type="button" value="Play" onclick="window.external.user('startPlay');" />
<input type="button" value="Login" onclick="window.external.user('login=auth,ok,sid,9001,terms,1,region,2,etmadd,0,playable,1,ps3pkg,0,maxex,5,product,1');" /> <input type="button" value="Login" onclick="window.external.user('login=auth,ok,sid,9001,terms,1,region,2,etmadd,0,playable,1,ps3pkg,0,maxex,5,product,1');" />
@ -28,6 +35,32 @@
<p id="replace-me">meh</p> <p id="replace-me">meh</p>
<script type="text/javascript"> <script type="text/javascript">
let req;
function readystatechange(event) {
if (req.readyState == 4) {
// This login endpoint sends a "window.external.user" which we need to evaludate.
eval(req.response);
}
}
function error(event) {
document.getElementById('replace-me').innerText += "login error: " + event;
}
function login() {
let sqexid = document.getElementById('sqexid').value;
let password = document.getElementById('password').value;
let otppw = document.getElementById('otppw').value;
let stored = document.getElementById('_STORED_').value;
req = new XMLHttpRequest();
req.addEventListener("readystatechange", readystatechange);
req.addEventListener("error", error);
req.open("POST", "http://ffxiv-login.square.localhost/oauth/ffxivarr/login/login.send");
req.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
req.send("sqexid=" + sqexid + "&password=" + password + "&otppw=" + otppw + "&_STORED_=" + stored);
}
function checkHandlerType(e) { function checkHandlerType(e) {
if ('function' != typeof e) throw new Error('Protocol Callback is not function.'); if ('function' != typeof e) throw new Error('Protocol Callback is not function.');
return e return e
@ -141,6 +174,17 @@
window.external.user('requestConfig'); window.external.user('requestConfig');
window.external.user('requestDisplaySettings'); window.external.user('requestDisplaySettings');
window.external.user('requestResumeInfo'); window.external.user('requestResumeInfo');
// setup form submission
const form = document.getElementById("login");
form.addEventListener("submit", function (event) {
// ie11 is amazing
if (event.preventDefault) {
event.preventDefault();
} else {
event.returnValue = false;
}
login();
});
</script> </script>
</body> {% endblock %}
</html>

View file

@ -3,6 +3,7 @@
<head> <head>
<meta charset="utf-8"> <meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1"> <meta name="viewport" content="width=device-width, initial-scale=1">
<meta http-equiv="X-UA-Compatible" content="IE=edge;">
<title>{% block title %}some website{% endblock %}</title> <title>{% block title %}some website{% endblock %}</title>
<link href="/static/bootstrap.min.css" rel="stylesheet"> <link href="/static/bootstrap.min.css" rel="stylesheet">
</head> </head>

View file

@ -5,9 +5,16 @@ use kawari::config::get_config;
use minijinja::Environment; use minijinja::Environment;
use minijinja::context; use minijinja::context;
use serde::Deserialize; use serde::Deserialize;
use tower_http::services::ServeDir;
fn setup_default_environment() -> Environment<'static> { fn setup_default_environment() -> Environment<'static> {
let mut env = Environment::new(); let mut env = Environment::new();
env.add_template_owned(
"layout.html",
std::fs::read_to_string("resources/templates/layout.html")
.expect("Failed to find template!"),
)
.unwrap();
env.add_template_owned( env.add_template_owned(
"launcher.html", "launcher.html",
std::fs::read_to_string("resources/templates/launcher.html") std::fs::read_to_string("resources/templates/launcher.html")
@ -41,7 +48,9 @@ async fn root(Query(_): Query<Params>) -> Html<String> {
async fn main() { async fn main() {
tracing_subscriber::fmt::init(); tracing_subscriber::fmt::init();
let app = Router::new().route("/v700/index.html", get(root)); let app = Router::new()
.route("/v700/index.html", get(root))
.nest_service("/static", ServeDir::new("resources/static"));
let config = get_config(); let config = get_config();