From c9ed1401b769cb3774f4595f248f7f5a2b1623ef Mon Sep 17 00:00:00 2001 From: Alec Rollison <88508028+aelishRollo@users.noreply.github.com> Date: Thu, 6 Jun 2024 15:37:16 -0400 Subject: [PATCH 01/11] Get basic template working so I can begin developing --- src/App.test.tsx | 201 ----------------------------------------------- src/App.tsx | 63 +-------------- src/Foo.tsx | 8 ++ src/index.tsx | 12 +-- 4 files changed, 13 insertions(+), 271 deletions(-) delete mode 100644 src/App.test.tsx create mode 100644 src/Foo.tsx diff --git a/src/App.test.tsx b/src/App.test.tsx deleted file mode 100644 index 8e27742..0000000 --- a/src/App.test.tsx +++ /dev/null @@ -1,201 +0,0 @@ -import {render, screen, waitFor} from '@testing-library/react'; -import App from './App'; -import {IClient} from './client/IClient'; -import {ProjectData, CommentData, SectionData, EntityType, FileData} from './types'; -import {LocalStorageStore, StoreData} from './store/LocalStorageStore'; -import {MockLocalStorageDependency} from './store/MockLocalStorageDependency'; -import {LocalStorageClient} from './client/LocalStorageClient'; - -// import * as testData from './sampleData' - -window.alert = () => {}; - -const makeTestStore = (): StoreData => { - const initialProjects: ProjectData[] = [ - { - id: 'project-1', - }, - { - id: 'project-2', - }, - ]; - - const initialSections: SectionData[] = [ - { - id: 'section-1', - projectId: 'project-1', - chordProgression: ['C', 'Dm', 'F', 'G'], - description: 'This is the intro', - title: 'Intro', - numRevisions: 3, - } - ]; - - const initialFiles: FileData[] = [ - { - id: 'file-1', - projectId: 'project-1', - entityId: 'section-1', - entityType: EntityType.SECTION, - title: 'Bass.mp3', - }, - { - id: 'file-2', - projectId: 'project-1', - entityId: 'section-1', - entityType: EntityType.SECTION, - title: 'Chunky Monkey.mp3', - }, - ]; - - const initialComments: CommentData[] = [ - { - id: 'comment-1', - projectId: 'project-1', - message: 'Hey what\'s up', - entityType: EntityType.SECTION, - entityId: 'section-1', - username: 'username-1', - }, - { - id: 'comment-2', - projectId: 'project-1', - message: 'Yeah', - entityType: EntityType.FILE, - entityId: 'file-1', - username: 'username-1', - }, - { - id: 'comment-3', - projectId: 'project-1', - message: 'Yeah 3', - entityType: EntityType.FILE, - entityId: 'file-1', - username: 'username-1', - }, - ]; - - return { - projects: initialProjects, - sections: initialSections, - files: initialFiles, - comments: initialComments, - }; -}; - -describe('App', () => { - let client: IClient; - - beforeEach(() => { - const initialStore = makeTestStore(); - - const localStorageDependency = new MockLocalStorageDependency(initialStore); - const store = new LocalStorageStore(localStorageDependency); - client = new LocalStorageClient(store); - }); - - describe('initializing', () => { - it('should show "Loading"', async () => { - // this method is made blocking for this specific test - client.fetchFullDataForProject = (() => new Promise(r => setTimeout(r))); - - render( - - ); - - expect(screen.getByText(/Loading/)).toBeDefined(); - }); - - it('should show client error', async () => { - client.fetchFullDataForProject = jest.fn().mockResolvedValue(new Error('Some error')); - - render( - - ); - - await waitFor(() => { - expect(screen.queryByText(/Loading/)).toBeNull(); - }); - - expect(screen.getByText(/Some error/)).toBeDefined(); - }); - }); - - describe('initialized', () => { - it('should show the section title and description', async () => { - render( - - ); - - await waitFor(() => { - expect(screen.queryByText(/Loading/)).toBeNull(); - }); - - expect(screen.getByText(/Intro/)).toBeDefined(); - expect(screen.getByText(/This is the intro/)).toBeDefined(); - }); - - it('should show the chord progression', async () => { - const {container} = render( - - ); - - await waitFor(() => { - expect(screen.queryByText(/Loading/)).toBeNull(); - }); - - expect(container.querySelector('.chords')?.textContent).toEqual('CDmFG'); - }); - - it('should show files attached to the section', async () => { - const {container} = render( - - ); - - await waitFor(() => { - expect(screen.queryByText(/Loading/)).toBeNull(); - }); - - expect(container.querySelector('.files #file-1')?.textContent).toContain('Bass.mp3'); - expect(container.querySelector('.files #file-1')?.textContent).toContain('2 Comments'); - }); - - it('should show the comments on the section', async () => { - const {container} = render( - - ); - - await waitFor(() => { - expect(screen.queryByText(/Loading/)).toBeNull(); - }); - - expect(container.querySelector('.comments')?.textContent).toContain('1 Comment'); - expect(container.querySelector('.comments #comment-1')?.textContent).toContain('username-1'); - expect(container.querySelector('.comments #comment-1')?.textContent).toContain('Hey what\'s up'); - }); - }); -}); diff --git a/src/App.tsx b/src/App.tsx index df11b80..7d3e3b5 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,68 +1,13 @@ -import {useState} from 'react'; -import './App.css'; -import './css_reset.css' -import './index.css' -import './section_view.css'; -import * as types from './types'; -import {GlobalStoreProvider} from './hooks/useGlobalStore'; -import SectionPage from './SectionPage'; -import {IClient} from './client/IClient'; -import {ClientProvider} from './hooks/useClient'; -import {useMount} from './hooks/useMount'; -type AppProps = { - projectId: string; - sectionId: string; +import Foo from './Foo' - client: IClient; -} - -const App: React.FC = ({projectId, sectionId, client}) => { - const [initialProjectData, setInitialProjectData] = useState(null); - const [error, setError] = useState(''); - - useMount(async () => { - const projectDataOrError = await client.fetchFullDataForProject(projectId); - - if (projectDataOrError instanceof Error) { - alert(projectDataOrError.message); - setError(projectDataOrError.message); - return; - } - setInitialProjectData(projectDataOrError); - }); - - if (error) { - return ( -

- {error} -

- ); - } - - if (!initialProjectData) { - return ( -

- Loading -

- ); - } - - const pageContent = ( - - ); +const App = () => { + return ( - - - {pageContent} - - + ); } diff --git a/src/Foo.tsx b/src/Foo.tsx new file mode 100644 index 0000000..fae4aa2 --- /dev/null +++ b/src/Foo.tsx @@ -0,0 +1,8 @@ + + + +let ChordProgression = () => { + return (

Hello, Universe!

); + }; + + export default ChordProgression diff --git a/src/index.tsx b/src/index.tsx index 7b20240..15f2911 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -11,19 +11,9 @@ window.addEventListener('load', async () => { document.getElementById('root') as HTMLElement ); - const localStore = new LocalStorageStore(localStorage); - const localClient = new LocalStorageClient(localStore); - - const projectId = 'project-1'; - const sectionId = 'section-1'; - root.render( - + ); }); From 5351b3f6d330dd2591b174d7bd0423e2e16c2c86 Mon Sep 17 00:00:00 2001 From: Alec Rollison <88508028+aelishRollo@users.noreply.github.com> Date: Thu, 6 Jun 2024 15:45:34 -0400 Subject: [PATCH 02/11] Prepare to integrate Semantic UI library --- src/index.tsx | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/index.tsx b/src/index.tsx index 15f2911..eef7cf9 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -3,8 +3,6 @@ import ReactDOM from 'react-dom/client'; import './index.css'; import App from './App'; import reportWebVitals from './reportWebVitals'; -import {LocalStorageStore} from './store/LocalStorageStore'; -import {LocalStorageClient} from './client/LocalStorageClient'; window.addEventListener('load', async () => { const root = ReactDOM.createRoot( From 228103346ffc676290608b8d17495e55187b1099 Mon Sep 17 00:00:00 2001 From: Alec Rollison <88508028+aelishRollo@users.noreply.github.com> Date: Thu, 6 Jun 2024 16:30:47 -0400 Subject: [PATCH 03/11] Create static layout --- package-lock.json | 146 ++++++++++++++++++++++++++++++++++++++++++++++ package.json | 2 + src/Foo.tsx | 101 ++++++++++++++++++++++++++++++-- src/index.tsx | 2 + 4 files changed, 247 insertions(+), 4 deletions(-) diff --git a/package-lock.json b/package-lock.json index a3253ef..2a79a83 100644 --- a/package-lock.json +++ b/package-lock.json @@ -23,6 +23,8 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "semantic-ui-css": "^2.5.0", + "semantic-ui-react": "^2.1.5", "typescript": "^4.9.5", "web-vitals": "^2.1.4" } @@ -2402,6 +2404,36 @@ "node": "^12.22.0 || ^14.17.0 || >=16.0.0" } }, + "node_modules/@fluentui/react-component-event-listener": { + "version": "0.63.1", + "resolved": "https://registry.npmjs.org/@fluentui/react-component-event-listener/-/react-component-event-listener-0.63.1.tgz", + "integrity": "sha512-gSMdOh6tI3IJKZFqxfQwbTpskpME0CvxdxGM2tdglmf6ZPVDi0L4+KKIm+2dN8nzb8Ya1A8ZT+Ddq0KmZtwVQg==", + "dependencies": { + "@babel/runtime": "^7.10.4" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17 || ^18", + "react-dom": "^16.8.0 || ^17 || ^18" + } + }, + "node_modules/@fluentui/react-component-ref": { + "version": "0.63.1", + "resolved": "https://registry.npmjs.org/@fluentui/react-component-ref/-/react-component-ref-0.63.1.tgz", + "integrity": "sha512-8MkXX4+R3i80msdbD4rFpEB4WWq2UDvGwG386g3ckIWbekdvN9z2kWAd9OXhRGqB7QeOsoAGWocp6gAMCivRlw==", + "dependencies": { + "@babel/runtime": "^7.10.4", + "react-is": "^16.6.3" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17 || ^18", + "react-dom": "^16.8.0 || ^17 || ^18" + } + }, + "node_modules/@fluentui/react-component-ref/node_modules/react-is": { + "version": "16.13.1", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", + "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==" + }, "node_modules/@fortawesome/fontawesome-common-types": { "version": "6.5.2", "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-common-types/-/fontawesome-common-types-6.5.2.tgz", @@ -3428,6 +3460,15 @@ } } }, + "node_modules/@popperjs/core": { + "version": "2.11.8", + "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz", + "integrity": "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/popperjs" + } + }, "node_modules/@rollup/plugin-babel": { "version": "5.3.1", "resolved": "https://registry.npmjs.org/@rollup/plugin-babel/-/plugin-babel-5.3.1.tgz", @@ -3507,6 +3548,19 @@ "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.10.1.tgz", "integrity": "sha512-S3Kq8e7LqxkA9s7HKLqXGTGck1uwis5vAXan3FnU5yw1Ec5hsSGnq4s/UCaSqABPOnOTg7zASLyst7+ohgWexg==" }, + "node_modules/@semantic-ui-react/event-stack": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/@semantic-ui-react/event-stack/-/event-stack-3.1.3.tgz", + "integrity": "sha512-FdTmJyWvJaYinHrKRsMLDrz4tTMGdFfds299Qory53hBugiDvGC0tEJf+cHsi5igDwWb/CLOgOiChInHwq8URQ==", + "dependencies": { + "exenv": "^1.2.2", + "prop-types": "^15.6.2" + }, + "peerDependencies": { + "react": "^16.0.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^16.0.0 || ^17.0.0 || ^18.0.0" + } + }, "node_modules/@sinclair/typebox": { "version": "0.24.51", "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.24.51.tgz", @@ -5988,6 +6042,14 @@ "wrap-ansi": "^7.0.0" } }, + "node_modules/clsx": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/clsx/-/clsx-1.2.1.tgz", + "integrity": "sha512-EcR6r5a8bj6pu3ycsa/E/cKVGuTgZJZdsyUYHOksG/UHIiKfjxzRxYJpyVBwYaQeOvghal9fcc4PidlgzugAQg==", + "engines": { + "node": ">=6" + } + }, "node_modules/co": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", @@ -8107,6 +8169,11 @@ "url": "https://github.com/sindresorhus/execa?sponsor=1" } }, + "node_modules/exenv": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/exenv/-/exenv-1.2.2.tgz", + "integrity": "sha512-Z+ktTxTwv9ILfgKCk32OX3n/doe+OcLTRtqK9pcL+JsP3J1/VW8Uvl4ZjLlKqeW4rzK4oesDOGMEMRIZqtP4Iw==" + }, "node_modules/exit": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/exit/-/exit-0.1.2.tgz", @@ -12002,6 +12069,11 @@ "jiti": "bin/jiti.js" } }, + "node_modules/jquery": { + "version": "3.7.1", + "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.7.1.tgz", + "integrity": "sha512-m4avr8yL8kmFN8psrbFFFmB/If14iN5o9nw/NgnnM+kybDJpRsAynV2BsfpTYrTRysYUdADVD7CkUUizgkpLfg==" + }, "node_modules/js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", @@ -12166,6 +12238,11 @@ "node": ">=4.0" } }, + "node_modules/keyboard-key": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/keyboard-key/-/keyboard-key-1.1.0.tgz", + "integrity": "sha512-qkBzPTi3rlAKvX7k0/ub44sqOfXeLc/jcnGGmj5c7BJpU8eDrEVPyhCvNYAaoubbsLm9uGWwQJO1ytQK1a9/dQ==" + }, "node_modules/keyv": { "version": "4.5.4", "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", @@ -12296,6 +12373,11 @@ "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" }, + "node_modules/lodash-es": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz", + "integrity": "sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==" + }, "node_modules/lodash.debounce": { "version": "4.0.8", "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", @@ -14935,11 +15017,30 @@ "resolved": "https://registry.npmjs.org/react-error-overlay/-/react-error-overlay-6.0.11.tgz", "integrity": "sha512-/6UZ2qgEyH2aqzYZgQPxEnz33NJ2gNsnHA2o5+o4wW9bLM/JYQitNP9xPhsXwC08hMMovfGe/8retsdDsczPRg==" }, + "node_modules/react-fast-compare": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/react-fast-compare/-/react-fast-compare-3.2.2.tgz", + "integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==" + }, "node_modules/react-is": { "version": "17.0.2", "resolved": "https://registry.npmjs.org/react-is/-/react-is-17.0.2.tgz", "integrity": "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==" }, + "node_modules/react-popper": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/react-popper/-/react-popper-2.3.0.tgz", + "integrity": "sha512-e1hj8lL3uM+sgSR4Lxzn5h1GxBlpa4CQz0XLF8kx4MDrDRWY0Ena4c97PUeSX9i5W3UAfDP0z0FXCTQkoXUl3Q==", + "dependencies": { + "react-fast-compare": "^3.0.1", + "warning": "^4.0.2" + }, + "peerDependencies": { + "@popperjs/core": "^2.0.0", + "react": "^16.8.0 || ^17 || ^18", + "react-dom": "^16.8.0 || ^17 || ^18" + } + }, "node_modules/react-refresh": { "version": "0.11.0", "resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.11.0.tgz", @@ -15605,6 +15706,38 @@ "node": ">=10" } }, + "node_modules/semantic-ui-css": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/semantic-ui-css/-/semantic-ui-css-2.5.0.tgz", + "integrity": "sha512-jIWn3WXXE2uSaWCcB+gVJVRG3masIKtTMNEP2X8Aw909H2rHpXGneYOxzO3hT8TpyvB5/dEEo9mBFCitGwoj1A==", + "dependencies": { + "jquery": "x.*" + } + }, + "node_modules/semantic-ui-react": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/semantic-ui-react/-/semantic-ui-react-2.1.5.tgz", + "integrity": "sha512-nIqmmUNpFHfovEb+RI2w3E2/maZQutd8UIWyRjf1SLse+XF51hI559xbz/sLN3O6RpLjr/echLOOXwKCirPy3Q==", + "dependencies": { + "@babel/runtime": "^7.10.5", + "@fluentui/react-component-event-listener": "~0.63.0", + "@fluentui/react-component-ref": "~0.63.0", + "@popperjs/core": "^2.6.0", + "@semantic-ui-react/event-stack": "^3.1.3", + "clsx": "^1.1.1", + "keyboard-key": "^1.1.0", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "prop-types": "^15.7.2", + "react-is": "^16.8.6 || ^17.0.0 || ^18.0.0", + "react-popper": "^2.3.0", + "shallowequal": "^1.1.0" + }, + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0", + "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, "node_modules/semver": { "version": "7.6.0", "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.0.tgz", @@ -15803,6 +15936,11 @@ "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" }, + "node_modules/shallowequal": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz", + "integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ==" + }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -17267,6 +17405,14 @@ "makeerror": "1.0.12" } }, + "node_modules/warning": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz", + "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==", + "dependencies": { + "loose-envify": "^1.0.0" + } + }, "node_modules/watchpack": { "version": "2.4.1", "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.1.tgz", diff --git a/package.json b/package.json index c2058f8..f69bf67 100644 --- a/package.json +++ b/package.json @@ -18,6 +18,8 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "semantic-ui-css": "^2.5.0", + "semantic-ui-react": "^2.1.5", "typescript": "^4.9.5", "web-vitals": "^2.1.4" }, diff --git a/src/Foo.tsx b/src/Foo.tsx index fae4aa2..cef8c51 100644 --- a/src/Foo.tsx +++ b/src/Foo.tsx @@ -1,8 +1,101 @@ +import React from 'react'; +import { Container, Header, Menu, Dropdown, Grid, Comment, Form, Button, Input, List } from 'semantic-ui-react'; +const SectionView = () => ( + + {/* Menu */} + + +
My section
+
+ + + + Edit title + Edit Progression + Duplicate + Delete + + + +
+ {/* Chord Progression */} +
Progression: C Dm Em F
-let ChordProgression = () => { - return (

Hello, Universe!

); - }; + {/* Grid Layout */} + + + + + + + + Bass.mp3 + 2 comments + + + + + + Guitar.mp3 + 23 comments + + + + + + Guitar.mp3 + 23 comments + + + + + + + + + Guitar.mp3 + 23 comments + + + + + + Guitar.mp3 + 23 comments + + + + + - export default ChordProgression + {/* Comments Section */} +
Comments for section
+ + + + + Dave + Great section! + + + + + + Matthews + Great section! + + + {/* Add more comments as needed */} + + + {/* Comment Form */} +
+ + - {/* Comments Section */} -
Comments for section
- - - - - Dave - Great section! - - - - - - Matthews - Great section! - - - {/* Add more comments as needed */} - + {/* Modal for ProjectView */} + + Select a Project + + + + - {/* Comment Form */} -
- - - - {/* Modal for ProjectView */} - - Select a Project - + + + + } + open={dropdownOpen} + onClick={handleDropdownToggle} + > + - - + + {/* Main Content */} From f9636c6e053c47f02e3c09e3641b841e1f480084 Mon Sep 17 00:00:00 2001 From: Alec Rollison <88508028+aelishRollo@users.noreply.github.com> Date: Sat, 6 Jul 2024 16:42:53 -0400 Subject: [PATCH 11/11] Adjust hamburger menu positioning --- src/SectionView.tsx | 65 +++++++++++++++++++++++---------------------- 1 file changed, 33 insertions(+), 32 deletions(-) diff --git a/src/SectionView.tsx b/src/SectionView.tsx index 866d81c..0f5d75a 100644 --- a/src/SectionView.tsx +++ b/src/SectionView.tsx @@ -11,41 +11,42 @@ const SectionView: React.FC = () => { return ( - {/* Hamburger Menu */} - - - - } - open={dropdownOpen} - onClick={handleDropdownToggle} - > - - - - +
+
+ {/* Hamburger Menu */} + + + + } + open={dropdownOpen} + onClick={handleDropdownToggle} + style={{ marginRight: '1rem' }} + > + + + + + + {/* Section Header */} +
My section
+
+ + {/* Ellipsis Menu */} + + + Edit title + Edit Progression + Duplicate + Delete + + +
{/* Main Content */} - {/* Menu */} - - -
My section
-
- - - - Edit title - Edit Progression - Duplicate - Delete - - - -
- {/* Chord Progression */}
Progression: C Dm Em F