Initial commit 2
This commit is contained in:
39
src/app.tsx
Normal file
39
src/app.tsx
Normal file
@@ -0,0 +1,39 @@
|
||||
import * as React from 'react';
|
||||
import {createRoot} from 'react-dom/client';
|
||||
|
||||
import '../src/assets/style.css';
|
||||
import { findExistingAxe } from '.';
|
||||
|
||||
const App: React.FC = () => {
|
||||
const addAxe = async () => {
|
||||
var axe = await findExistingAxe()
|
||||
if (!axe) {
|
||||
axe = await miro.board.createImage({
|
||||
url: 'https://www.svgrepo.com/show/395800/axe.svg',
|
||||
width: 200,
|
||||
title: 'todo-tree-axe'
|
||||
});
|
||||
}
|
||||
|
||||
await miro.board.viewport.zoomTo(axe);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="grid wrapper">
|
||||
<div className="cs1 ce12">
|
||||
<h1>TODO Tree Chopper 🪓</h1>
|
||||
</div>
|
||||
<div className="cs1 ce12">
|
||||
<button className="button button-primary" onClick={addAxe}>
|
||||
Create Axe
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const container = document.getElementById('root');
|
||||
if (container) {
|
||||
const root = createRoot(container);
|
||||
root.render(<App />);
|
||||
}
|
||||
22
src/assets/style.css
Normal file
22
src/assets/style.css
Normal file
@@ -0,0 +1,22 @@
|
||||
@import 'mirotone/dist/styles.css';
|
||||
|
||||
*,
|
||||
*:before,
|
||||
*:after {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
#root {
|
||||
width: 100%;
|
||||
overflow: auto;
|
||||
padding: var(--space-medium);
|
||||
}
|
||||
|
||||
img {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
}
|
||||
87
src/index.ts
Normal file
87
src/index.ts
Normal file
@@ -0,0 +1,87 @@
|
||||
import { StickyNote, Image } from "@mirohq/websdk-types";
|
||||
|
||||
export async function init() {
|
||||
miro.board.ui.on('icon:click', async () => {
|
||||
await miro.board.ui.openPanel({ url: 'app.html' });
|
||||
});
|
||||
|
||||
await miro.board.ui.on('custom:chop-todo-tree', handleChoppingAction);
|
||||
await miro.board.experimental.action.register(
|
||||
{
|
||||
"event": "chop-todo-tree",
|
||||
"ui": {
|
||||
"label": {
|
||||
"en": "Chop TODO tree",
|
||||
},
|
||||
"icon": "scissors",
|
||||
"description": "Chop down TODO tree staring here",
|
||||
},
|
||||
"scope": "local",
|
||||
"predicate": {
|
||||
"type": "sticky_note"
|
||||
},
|
||||
"contexts": {
|
||||
"item": {}
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
interface AxeAnimationArgs {
|
||||
axe: Image,
|
||||
stickyNote: StickyNote,
|
||||
onChopped: () => void
|
||||
}
|
||||
|
||||
const playAxeAnimation = async ({axe, stickyNote, onChopped}: AxeAnimationArgs) => {
|
||||
await miro.board.bringToFront(axe);
|
||||
axe.x = stickyNote.x;
|
||||
axe.y = stickyNote.y;
|
||||
await axe.sync();
|
||||
|
||||
for (let i = 0; i < 3; i++) {
|
||||
axe.rotation = 90;
|
||||
await axe.sync();
|
||||
await new Promise(resolve => setTimeout(resolve, 200));
|
||||
|
||||
axe.rotation = 0;
|
||||
await axe.sync();
|
||||
await new Promise(resolve => setTimeout(resolve, 200));
|
||||
}
|
||||
|
||||
onChopped();
|
||||
}
|
||||
|
||||
async function postInfoNotification(message: string) {
|
||||
await miro.board.notifications.showInfo(message);
|
||||
}
|
||||
|
||||
const handleChoppingAction = async ({items}: {items:StickyNote[]}) => {
|
||||
const axe = await findExistingAxe();
|
||||
|
||||
if (items.length === 0) {
|
||||
postInfoNotification("Couldn't find anything to chop 🤔")
|
||||
return;
|
||||
}
|
||||
|
||||
if (!axe) {
|
||||
postInfoNotification('No axe found. Create it first.');
|
||||
return;
|
||||
}
|
||||
|
||||
const target = items[0];
|
||||
playAxeAnimation({
|
||||
axe,
|
||||
stickyNote: target,
|
||||
onChopped: async () => await miro.board.remove(target)
|
||||
});
|
||||
};
|
||||
|
||||
export const findExistingAxe = async () => {
|
||||
const items = await miro.board.get({ type: 'image' });
|
||||
const axe = items.find(item => item.title === 'todo-tree-axe');
|
||||
return axe;
|
||||
};
|
||||
|
||||
|
||||
init();
|
||||
Reference in New Issue
Block a user