Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

GSoC 2023: Niloy #392

Closed
wants to merge 47 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
4410878
feat(code-builder): implement `_getBBoxBrick` method for the path
niloysikdar Jul 5, 2023
9fe5f0c
feat(code-builder): implement `_getBBoxNotchArg` method for the path
niloysikdar Jul 12, 2023
3933d68
fix(code-builder): calculation for `_getBBoxNotchInsTop` method for t…
niloysikdar Jul 12, 2023
050749e
fix(code-builder): calculation for `_getBBoxNotchInsBot` method for t…
niloysikdar Jul 12, 2023
b54666f
fix(code-builder): calculation for `_getBBoxNotchInsNestTop` method f…
niloysikdar Jul 12, 2023
2351631
feat(code-builder): implement `_getBBoxArgs` method for the path
niloysikdar Jul 12, 2023
08cba1d
fix(code-builder): remove `hasNotchNest` for generatePath inside `Bri…
niloysikdar Jul 12, 2023
6020732
fix(code-builder): `extent` and `coords` calculation in `path.ts`
niloysikdar Jul 13, 2023
957625d
chore(path): print results in DEV mode
niloysikdar Jul 13, 2023
6c39bc7
feat(code-builder): implement missing getters for `BrickBlock`
niloysikdar Jul 13, 2023
66b90f0
fix(bricks): types for bricks
niloysikdar Jul 13, 2023
c6727c4
refactor(bricks): define `bBoxArgs` getter to get extent and coords
niloysikdar Jul 13, 2023
6e61ab8
refactor(bricks): change `bBoxArgs` to make it more flexible
niloysikdar Jul 13, 2023
df12916
feat(bricks): add `bBoxBrick` getter
niloysikdar Jul 13, 2023
b377687
fix(bricks): convert `SVGpaths` getter to `SVGpath`
niloysikdar Jul 13, 2023
0e5d031
feat(storybook): show visual indicators
niloysikdar Jul 13, 2023
516ecf0
chore(storybook): remove `No Args` story for `Expression Brick`
niloysikdar Jul 13, 2023
5ceffb0
fix(generatePath): `_getBBoxArgs` coords calculation
niloysikdar Jul 13, 2023
f8791bf
feat(bricks): change the model add `bBoxNotchArg` getter
niloysikdar Jul 14, 2023
175a8b4
docs(storybook): add bounding box for notch to `BrickBlock` story
niloysikdar Jul 14, 2023
81e3614
feat(bricks): change the model add `bBoxNotchInsTop` getter
niloysikdar Jul 14, 2023
cc2a6cb
docs(storybook): add bounding box for top ins notch to `BrickBlock` s…
niloysikdar Jul 14, 2023
cbacab6
feat(bricks): change the model add `bBoxNotchInsBot` getter
niloysikdar Jul 14, 2023
c4aa4b6
docs(storybook): add bounding box for bottom ins notch to `BrickBlock…
niloysikdar Jul 14, 2023
0e65883
feat(bricks): change the model to add `bBoxNotchInsNestTop` getter
niloysikdar Jul 14, 2023
0d77023
docs(storybook): add bounding box for top ins notch inside nesting to…
niloysikdar Jul 14, 2023
34aa7fd
fix(bricks): change `BrickData` model to adapt the new type
niloysikdar Jul 14, 2023
35bedd1
docs(storybook): add notch visualization to the `BrickData` stories
niloysikdar Jul 14, 2023
a74f544
fix(bricks): change `BrickExpression` model to adapt the new type
niloysikdar Jul 14, 2023
d5a956c
docs(storybook): add notch and args visualization to the `BrickExpres…
niloysikdar Jul 14, 2023
3a65452
fix(bricks): change `BrickStatement` model to adapt the new type
niloysikdar Jul 14, 2023
e7fc86a
docs(storybook): add notch and args visualization to the `BrickStatem…
niloysikdar Jul 14, 2023
bf93fa6
fix(bricks-path): coords(x) calculation for `_getBBoxArgs`
niloysikdar Jul 14, 2023
0af6fe1
docs(storybook): show overall bounding box of the bricks
niloysikdar Jul 14, 2023
7b3b4aa
refactor(code-builder): [brick] coalesce notch interfaces
meganindya Jul 16, 2023
4ca3071
refactor(code-builder): [brick] draw visual indicators only in storybook
meganindya Jul 16, 2023
e955c4d
chore(code-builder): remove DEV mode logs from `path.ts`
niloysikdar Jul 17, 2023
707bcff
test(code-builder): add missing todo tests for `path.spec.ts`
niloysikdar Jul 17, 2023
2493079
chore(playground): add dummy workspace data
niloysikdar Jul 19, 2023
4a1df20
fix(bricks): fix brick components to accept coords
niloysikdar Jul 19, 2023
c81a7f9
feat(playground): add workspace page and functionality into playground
niloysikdar Jul 19, 2023
66655bf
feat(playground): initialize and configure brick store
niloysikdar Aug 11, 2023
284c879
feat(bricks): modify bricks ho handle drag state
niloysikdar Aug 11, 2023
29ab094
feat(playground): render bricks and drag them
niloysikdar Aug 11, 2023
49de990
feat(playground): refactor bricks to encapsulate drag logic
niloysikdar Aug 11, 2023
5fe5560
feat(playground): recursive function to get below brick IDs
niloysikdar Aug 18, 2023
be31470
feat(playground): detect and update positions of collision areas for …
niloysikdar Aug 30, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion modules/code-builder/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@
"react-dom": "~18.x"
},
"dependencies": {
"@sugarlabs/musicblocks-v4-lib": "^0.2.0"
"@sugarlabs/musicblocks-v4-lib": "^0.2.0",
"react-aria": "^3.26.0",
"zustand": "^4.3.9"
}
}
5 changes: 5 additions & 0 deletions modules/code-builder/playground/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,17 @@ import { createRoot } from 'react-dom/client';
import { createBrowserRouter, Navigate, RouterProvider } from 'react-router-dom';

import PageCollision from './pages/Collision';
import WorkSpace from './pages/WorkSpace';

const router = createBrowserRouter([
{
path: '/collision',
element: <PageCollision />,
},
{
path: '/workspace',
element: <WorkSpace />,
},
{
path: '/',
element: <Navigate to="/collision" />,
Expand Down
185 changes: 185 additions & 0 deletions modules/code-builder/playground/pages/WorkSpace/BrickFactory.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,185 @@
import { useState } from 'react';
import { useMove } from 'react-aria';
import { BrickBlock, BrickData, BrickExpression, BrickStatement } from '@/brick';
import { useBricksCoords } from './BricksCoordsStore';
import { WORKSPACES_DATA } from './data';
import type { Brick } from './data';
import { getBelowBricksIds } from './utils';

const BrickFactory = ({ brickData }: { brickData: Brick }) => {
const CONTAINER_SIZE_X = 800;
const CONTAINER_SIZE_Y = 700;
const BRICK_HEIGHT = brickData.instance.bBoxBrick.extent.height;
const BRICK_WIDTH = brickData.instance.bBoxBrick.extent.width;
const { getCoords, setCoords } = useBricksCoords();
const brickCoords = getCoords(brickData.id)!;
const [color, setColor] = useState(brickData.instance.colorBg as string);

const clampX = (pos: number) => Math.min(Math.max(pos, 0), CONTAINER_SIZE_X - BRICK_WIDTH * 2);
const clampY = (pos: number) => Math.min(Math.max(pos, 0), CONTAINER_SIZE_Y - BRICK_HEIGHT * 2);

const { moveProps } = useMove({
onMoveStart(e) {
console.log(`move start with pointerType = ${e.pointerType}`);
setColor('white');
},
onMove(e) {
const newX = brickCoords.x + e.deltaX;
const newY = brickCoords.y + e.deltaY;
setCoords(brickData.id, { x: clampX(newX), y: clampY(newY) });

brickData.childBricks.forEach((childBrick) => {
const childBrickCoords = getCoords(childBrick)!;
setCoords(childBrick, {
x: childBrickCoords.x + e.deltaX,
y: childBrickCoords.y + e.deltaY,
});
});

const belowBrickIds = getBelowBricksIds(WORKSPACES_DATA[0].data, brickData.id);
belowBrickIds.forEach((belowBrickId) => {
const belowBrickCoords = getCoords(belowBrickId)!;
setCoords(belowBrickId, {
x: belowBrickCoords.x + e.deltaX,
y: belowBrickCoords.y + e.deltaY,
});
});

// Normally, we want to allow the user to continue
// dragging outside the box such that they need to
// drag back over the ball again before it moves.
// This is handled below by clamping during render.
// If using the keyboard, however, we need to clamp
// here so that dragging outside the container and
// then using the arrow keys works as expected.
// if (e.pointerType === 'keyboard') {
// x = clamp(x);
// y = clamp(y);
// }

// setEvents((events) => [
// `move with pointerType = ${e.pointerType}, deltaX = ${e.deltaX}, deltaY = ${e.deltaY}`,
// ...events,
// ]);
},
onMoveEnd(e) {
console.log(`move end with pointerType = ${e.pointerType}`);
setColor(brickData.instance.colorBg as string);
},
});

const VisualIndicators = () => (
<>
{/* Right args bounding box */}
{'bBoxArgs' in brickData.instance && (
<>
{Object.keys(brickData.instance.bBoxArgs).map((name, i) => {
if ('bBoxArgs' in brickData.instance) {
const arg = brickData.instance.bBoxArgs[name];

return (
<rect
key={i}
x={brickCoords.x + arg?.coords.x}
y={brickCoords.y + arg?.coords.y}
height={arg?.extent.height}
width={arg?.extent.width}
fill="green"
opacity={0.8}
/>
);
}
})}
</>
)}

{/* Top instruction notch bounding box */}
{'bBoxNotchInsTop' in brickData.instance && (
<rect
x={brickCoords.x + brickData.instance.bBoxNotchInsTop?.coords.x}
y={brickCoords.y + brickData.instance.bBoxNotchInsTop?.coords.y}
height={brickData.instance.bBoxNotchInsTop?.extent.height}
width={brickData.instance.bBoxNotchInsTop?.extent.width}
fill="green"
opacity={0.9}
/>
)}

{/* Bottom instruction notch bounding box */}
{'bBoxNotchInsBot' in brickData.instance && (
<rect
x={brickCoords.x + brickData.instance.bBoxNotchInsBot?.coords.x}
y={brickCoords.y + brickData.instance.bBoxNotchInsBot?.coords.y}
height={brickData.instance.bBoxNotchInsBot?.extent.height}
width={brickData.instance.bBoxNotchInsBot?.extent.width}
fill="green"
opacity={0.9}
/>
)}

{/* Top instruction notch inside nesting bounding box */}
{'bBoxNotchInsNestTop' in brickData.instance && (
<rect
x={brickCoords.x + brickData.instance.bBoxNotchInsNestTop?.coords.x}
y={brickCoords.y + brickData.instance.bBoxNotchInsNestTop?.coords.y}
height={brickData.instance.bBoxNotchInsNestTop?.extent.height}
width={brickData.instance.bBoxNotchInsNestTop?.extent.width}
fill="green"
opacity={0.9}
/>
)}
</>
);

const getBrick = () => {
switch (brickData.type) {
case 'data':
return (
<BrickData
brickData={brickData}
moveProps={moveProps}
coords={brickCoords}
color={color}
/>
);
case 'expression':
return (
<BrickExpression
brickData={brickData}
moveProps={moveProps}
coords={brickCoords}
color={color}
/>
);
case 'statement':
return (
<BrickStatement
brickData={brickData}
moveProps={moveProps}
coords={brickCoords}
color={color}
/>
);
case 'block':
return (
<BrickBlock
brickData={brickData}
moveProps={moveProps}
coords={brickCoords}
color={color}
/>
);
default:
return <></>;
}
};

return (
<>
<VisualIndicators />
{/* {getBrick()} */}
</>
);
};

export default BrickFactory;
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import { create } from 'zustand';

type CoordsState = {
allCoords: {
brickId: string;
coords: {
x: number;
y: number;
};
}[];
setCoords: (brickId: string, coords: { x: number; y: number }) => void;
getCoords: (brickId: string) => { x: number; y: number } | undefined;
};

const useBricksCoordsStore = create<CoordsState>((set, get) => ({
allCoords: [
{ brickId: '1', coords: { x: 50, y: 50 } },
{ brickId: '2', coords: { x: 68, y: 92 } },
{ brickId: '3', coords: { x: 68, y: 134 } },
{ brickId: '4', coords: { x: 68, y: 176 } },
{ brickId: '5', coords: { x: 86, y: 218 } },
{ brickId: '6', coords: { x: 68, y: 302 } },
],
setCoords: (brickId: string, coords: { x: number; y: number }) =>
set(
(state: {
allCoords: {
brickId: string;
coords: {
x: number;
y: number;
};
}[];
}) => ({
allCoords: state.allCoords.map((item) =>
item.brickId === brickId ? { brickId, coords } : item,
),
}),
),
getCoords: (brickId: string) =>
get().allCoords.find((item) => item.brickId === brickId)?.coords,
}));

export const useBricksCoords = () => {
const allCoords = useBricksCoordsStore((state) => state.allCoords);
const setCoords = useBricksCoordsStore((state) => state.setCoords);
const getCoords = useBricksCoordsStore((state) => state.getCoords);

return { allCoords, setCoords, getCoords };
};
Loading
Loading