Skip to content

Commit

Permalink
Add validate and new icon
Browse files Browse the repository at this point in the history
  • Loading branch information
Chi-EEE committed Apr 17, 2024
1 parent 4e60a29 commit 5f484cf
Show file tree
Hide file tree
Showing 27 changed files with 509 additions and 87 deletions.
7 changes: 7 additions & 0 deletions app/admin_panel/.gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,10 @@ private

# Desktop Services Store on macOS
.DS_Store

# Allow following inside of resources directory
!resources/win32/x64/behaviour_tree_validator.exe
!resources/win32/x64/behaviour_tree.lib

!resources/win32/x86/behaviour_tree_validator.exe
!resources/win32/x86/behaviour_tree.lib
32 changes: 30 additions & 2 deletions app/admin_panel/js/behaviour_tree.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,18 @@
const { ipcMain } = require('electron');
const { app, ipcMain } = require('electron');
const { websocket_server } = require('./websocket');
const { getStore } = require('./store')
const util = require('util');
const exec = util.promisify(require('child_process').exec);
const Os = require('os');
const path = require("path");
const fs = require("fs");

function isDev() {
return !app.isPackaged;
}

const base_path = app.getAppPath();
const resources_dir = isDev() ? path.join(base_path, 'resources') : path.join(base_path, '..', '..', 'resources');

function sendBehaviourTree(_event, args) {
const behaviour_tree = args.data;
Expand Down Expand Up @@ -34,7 +46,7 @@ async function saveBehaviourTree(_event, args) {
const name = args.name;
const code = args.code;
let behaviour_tree_list = getBehaviourTreeList();
updateBehaviourTreeList(behaviour_tree_list.concat({uuid: uuid, name: name, code: code}));
updateBehaviourTreeList(behaviour_tree_list.concat({ uuid: uuid, name: name, code: code }));
}

async function removeBehaviourTree(_event, args) {
Expand All @@ -44,6 +56,19 @@ async function removeBehaviourTree(_event, args) {
updateBehaviourTreeList(behaviour_tree_list);
}

async function validateBehaviourTree(_event, args) {
/** @type {string} */
let code = args.data;
code = code.replace(new RegExp('"|\n'), "'");
const behaviour_tree_validator = path.join(resources_dir, Os.platform(), Os.arch(), 'behaviour_tree_validator.exe');
if (!fs.existsSync(behaviour_tree_validator)) {
return JSON.stringify({ success: false, error: `The current platform / architecture is not supported.` });
}
const command = `${behaviour_tree_validator} --behaviour_tree @"\n${code}\n"@`;
const { stdout, stderr } = await exec(command, { 'shell': 'powershell.exe' });
return stdout;
}

ipcMain.handle('sendBehaviourTree', sendBehaviourTree);
ipcMain.handle('startBehaviourTree', startBehaviourTree);
ipcMain.handle('stopBehaviourTree', stopBehaviourTree);
Expand All @@ -52,11 +77,14 @@ ipcMain.handle('getBehaviourTreeList', getBehaviourTreeList);
ipcMain.handle('saveBehaviourTree', saveBehaviourTree);
ipcMain.handle('removeBehaviourTree', removeBehaviourTree);

ipcMain.handle('validateBehaviourTree', validateBehaviourTree);

module.exports = {
sendBehaviourTree: sendBehaviourTree,
startBehaviourTree: startBehaviourTree,
stopBehaviourTree: stopBehaviourTree,
getBehaviourTreeList: getBehaviourTreeList,
saveBehaviourTree: saveBehaviourTree,
removeBehaviourTree: removeBehaviourTree,
validateBehaviourTree: validateBehaviourTree,
}
2 changes: 1 addition & 1 deletion app/admin_panel/js/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ const { websocket_server } = require('./websocket');
const { closeWebSocketServer } = require('./websocket_events');
const { selectRaspberryPi, unselectRaspberryPi, getRaspberryPiList, getSelectedRaspberryPi } = require('./raspberry_pi');
const { getLocalIPList } = require('./device');
const { sendBehaviourTree, startBehaviourTree, stopBehaviourTree, getBehaviourTreeList, saveBehaviourTree, removeBehaviourTree } = require('./behaviour_tree');
const { sendBehaviourTree, startBehaviourTree, stopBehaviourTree, getBehaviourTreeList, saveBehaviourTree, removeBehaviourTree, validateBehaviourTree } = require('./behaviour_tree');

function onClose() {
closeWebSocketServer();
Expand Down
4 changes: 3 additions & 1 deletion app/admin_panel/js/preload.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@ const WINDOW_API = {

getBehaviourTreeList: () => ipcRenderer.invoke("getBehaviourTreeList"),
saveBehaviourTree: (/** @type {any} */ args) => ipcRenderer.invoke("saveBehaviourTree", args),
removeBehaviourTree: (/** @type {any} */ args) => ipcRenderer.invoke("removeBehaviourTree", args)
removeBehaviourTree: (/** @type {any} */ args) => ipcRenderer.invoke("removeBehaviourTree", args),

validateBehaviourTree : (/** @type {any} */ args) => ipcRenderer.invoke("validateBehaviourTree", args)
}

contextBridge.exposeInMainWorld("api", WINDOW_API)
162 changes: 86 additions & 76 deletions app/admin_panel/package.json
Original file line number Diff line number Diff line change
@@ -1,77 +1,87 @@
{
"name": "admin_panel",
"version": "1.2.0",
"description": "The Admin Panel to directly control the Raspberry Pi and connect to the web server for sharing the Raspberry Pi.",
"private": false,
"license": "MIT",
"main": "js/main.js",
"author": "Chi Huu Huynh",
"build": {
"icon": "public/Sunfounder-PiCar.png",
"productName": "Admin Panel for Raspberry Pi",
"files": [
"public/**/*",
"js/**/*.js"
],
"win": {},
"linux": {},
"mac": {}
},
"scripts": {
"build": "rollup -c --bundleConfigAsCjs",
"dev": "rollup -c -w --bundleConfigAsCjs",
"start": "sirv public --no-clear",
"electron": "wait-on http://localhost:8080 && electron .",
"electron-dev": "concurrently \"pnpm run dev\" \"pnpm run electron\"",
"preelectron-pack": "pnpm run build",
"electron-pack": "electron-builder"
},
"devDependencies": {
"@rollup/plugin-commonjs": "^25.0.7",
"@rollup/plugin-node-resolve": "^15.2.3",
"@sveltejs/vite-plugin-svelte": "^3.0.2",
"autoprefixer": "^10.4.17",
"concurrently": "^8.2.2",
"electron": "^29.1.0",
"electron-builder": "^24.12.0",
"flowbite-svelte-icons": "1.4.0",
"postcss": "^8.4.35",
"postcss-load-config": "^5.0.3",
"rollup": "^4.12.0",
"rollup-plugin-css-only": "^4.5.2",
"rollup-plugin-livereload": "^2.0.5",
"rollup-plugin-node-polyfills": "^0.2.1",
"rollup-plugin-svelte": "^7.1.6",
"sirv-cli": "^2.0.2",
"svelte": "^4.2.12",
"svelte-copy": "^1.4.1",
"svelte-spa-router": "^4.0.1",
"tailwind-merge": "^2.2.1",
"tailwindcss": "^3.4.1",
"wait-on": "^7.2.0"
},
"dependencies": {
"@codemirror/lang-xml": "^6.0.2",
"@codemirror/theme-one-dark": "^6.1.2",
"@codemirror/view": "^6.23.0",
"electron-serve": "^1.3.0",
"electron-store": "^8.2.0",
"flowbite": "^2.3.0",
"flowbite-svelte": "^0.44.24",
"pixi.js": "^7.4.0",
"rollup-plugin-postcss": "^4.0.2",
"rollup-plugin-terser": "^7.0.2",
"svelte-codemirror-editor": "^1.3.0",
"svelte-pixi": "^0.1.3",
"svelte-splitpanes": "^0.8.0",
"tcp-port-used": "^1.0.2",
"ws": "^8.16.0",
"xml-formatter": "^3.6.2"
},
"dependencyGroupComments": {
"1": "flowbite: UI components",
"2": "codemirror: Code editor",
"3": "pixi.js: 2D rendering engine",
"4": "ws & tcp-port-used: For web socket connection"
}
}
"name": "Behaviour-Tree-PiCar-V-Admin-Panel",
"version": "1.2.0",
"description": "The Admin Panel to directly control the Sunfounder PiCar-V.",
"private": false,
"license": "MIT",
"main": "js/main.js",
"author": "Chi Huu Huynh",
"build": {
"appId": "com.chi_eee.behaviour-tree-picar-v-admin-panel",
"productName": "Behaviour Tree PiCar-V Admin Panel",
"icon": "public/Sunfounder-PiCar.png",
"files": [
"public/**/*",
"js/**/*.js"
],
"extraFiles": [
{
"from": "resources",
"to": "resources",
"filter": [
"**/*"
]
}
],
"win": {},
"linux": {},
"mac": {}
},
"scripts": {
"build": "rollup -c --bundleConfigAsCjs",
"dev": "rollup -c -w --bundleConfigAsCjs",
"start": "sirv public --no-clear",
"electron": "wait-on http://localhost:8080 && electron .",
"electron-dev": "concurrently \"pnpm run dev\" \"pnpm run electron\"",
"preelectron-pack": "pnpm run build",
"electron-pack": "electron-builder"
},
"devDependencies": {
"@rollup/plugin-commonjs": "^25.0.7",
"@rollup/plugin-node-resolve": "^15.2.3",
"@sveltejs/vite-plugin-svelte": "^3.0.2",
"autoprefixer": "^10.4.17",
"concurrently": "^8.2.2",
"electron": "^29.1.0",
"electron-builder": "^24.12.0",
"flowbite-svelte-icons": "1.4.0",
"postcss": "^8.4.35",
"postcss-load-config": "^5.0.3",
"rollup": "^4.12.0",
"rollup-plugin-css-only": "^4.5.2",
"rollup-plugin-livereload": "^2.0.5",
"rollup-plugin-node-polyfills": "^0.2.1",
"rollup-plugin-svelte": "^7.1.6",
"sirv-cli": "^2.0.2",
"svelte": "^4.2.12",
"svelte-copy": "^1.4.1",
"svelte-spa-router": "^4.0.1",
"tailwind-merge": "^2.2.1",
"tailwindcss": "^3.4.1",
"wait-on": "^7.2.0"
},
"dependencies": {
"@codemirror/lang-xml": "^6.0.2",
"@codemirror/theme-one-dark": "^6.1.2",
"@codemirror/view": "^6.23.0",
"electron-serve": "^1.3.0",
"electron-store": "^8.2.0",
"flowbite": "^2.3.0",
"flowbite-svelte": "^0.44.24",
"pixi.js": "^7.4.0",
"rollup-plugin-postcss": "^4.0.2",
"rollup-plugin-terser": "^7.0.2",
"svelte-codemirror-editor": "^1.3.0",
"svelte-pixi": "^0.1.3",
"svelte-splitpanes": "^0.8.0",
"tcp-port-used": "^1.0.2",
"ws": "^8.16.0",
"xml-formatter": "^3.6.2"
},
"dependencyGroupComments": {
"1": "flowbite: UI components",
"2": "codemirror: Code editor",
"3": "pixi.js: 2D rendering engine",
"4": "ws & tcp-port-used: For web socket connection"
}
}
Binary file modified app/admin_panel/public/Sunfounder-PiCar.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions app/admin_panel/public/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@
<meta charset='utf-8'>
<meta name='viewport' content='width=device-width,initial-scale=1'>

<title>Svelte app</title>
<title>Behaviour Tree PiCar-V</title>

<link rel='icon' type='image/png' href='/favicon.png'>
<link rel='icon' type='image/png' href='/Sunfounder-PiCar.png'>
<link rel='stylesheet' href='/global.css'>
<link rel='stylesheet' href='/build/bundle.css'>

Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
3 changes: 3 additions & 0 deletions app/admin_panel/src/lib/NavigationBar.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@
<NavLi>
<a href="#/websocket">Manage Websockets</a>
</NavLi>
<NavLi>
<a href="#/validate">Validate Behaviour Tree</a>
</NavLi>
</NavUl>
<NavHamburger class="lg:hidden" />
<DarkMode {btnClass} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@
import { xml } from "@codemirror/lang-xml";
import { oneDark } from "@codemirror/theme-one-dark";
import { node_hover, xml_schema } from "./CodeBox_Constants";
import { node_hover, xml_schema } from "../CodeBox_Constants";
import { behaviour_tree_xml_code } from "../store/behaviour_tree_store";
import { behaviour_tree_xml_code } from "../../store/behaviour_tree_store";
import CodeMessagingBar from "./CodeMessagingBar.svelte";
</script>

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<script>
import { selected_raspberry_pi_uuid } from "../store/raspberry_pi_store";
import { selected_raspberry_pi_uuid } from "../../store/raspberry_pi_store";
import xmlFormat from "xml-formatter";
import { behaviour_tree_xml_code } from "../store/behaviour_tree_store";
import { behaviour_tree_xml_code } from "../../store/behaviour_tree_store";
/** @type {string} */
let send_behaviour_tree_text = "Send Behaviour Tree";
Expand Down
35 changes: 35 additions & 0 deletions app/admin_panel/src/lib/validate/CodeBox.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
<script>
// If this does not work then try preview
import CodeMirror from "svelte-codemirror-editor";
import { xml } from "@codemirror/lang-xml";
import { oneDark } from "@codemirror/theme-one-dark";
import { node_hover, xml_schema } from "../CodeBox_Constants";
import { behaviour_tree_xml_code } from "../../store/behaviour_tree_store";
import CodeButton from "./CodeButton.svelte";
</script>

<div class="h-full m-1">
<CodeButton/>
<CodeMirror
class="text-left h-full flex-auto font-mono text-lg font-bold"
bind:value={$behaviour_tree_xml_code}
lang={xml(xml_schema)}
tabSize={4}
theme={oneDark}
extensions={[node_hover]}
/>
<style>
.cm-editor {
height: 90% !important;
}
.cm-editor * {
font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas,
"Liberation Mono", "Courier New" !important;
}
.cm-scroller {
height: 100% !important;
}
</style>
</div>
43 changes: 43 additions & 0 deletions app/admin_panel/src/lib/validate/CodeButton.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
<script>
import xmlFormat from "xml-formatter";
import { behaviour_tree_xml_code } from "../../store/behaviour_tree_store";
/** @type {string} */
let validate_behaviour_tree_text = "Validate Behaviour Tree";
/** @type {string} */
let validate_behaviour_tree_color = "#4C9CFF";
/** @type {boolean} */
let validate_behaviour_tree_debounce = false;
async function validateBehaviourTree() {
if (validate_behaviour_tree_debounce) {
return;
}
validate_behaviour_tree_debounce = true;
try {
const result = await api.validateBehaviourTree({
data: xmlFormat.minify($behaviour_tree_xml_code),
});
console.log(result);
validate_behaviour_tree_text = "Sent Behaviour Tree!";
validate_behaviour_tree_color = "#3457AA";
} catch (error) {
console.log(error)
validate_behaviour_tree_text = "Unable to send Behaviour Tree!";
validate_behaviour_tree_color = "#AA3434";
}
setTimeout(() => {
validate_behaviour_tree_text = "Validate Behaviour Tree";
validate_behaviour_tree_color = "#4C9CFF";
validate_behaviour_tree_debounce = false;
}, 1000);
}
</script>

<button
on:mousedown={validateBehaviourTree}
class="p-2 rounded-lg shadow-lg relative inset-0"
style="background-color: {validate_behaviour_tree_color}; color: white; width: 100%; border: none;">{validate_behaviour_tree_text}</button
>
2 changes: 2 additions & 0 deletions app/admin_panel/src/routes.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
import Home from './routes/Home.svelte';
import Websocket from './routes/Websocket.svelte';
import Validate from './routes/Validate.svelte';
import NotFound from './routes/NotFound.svelte';

export default {
'/': Home,
'/websocket': Websocket,
'/validate': Validate,
// The catch-all route must always be last
'*': NotFound
};
Loading

0 comments on commit 5f484cf

Please sign in to comment.