(a: T[]) => {
2 | for (let i = a.length - 1; i > 0; i--) {
3 | const j = Math.floor(Math.random() * (i + 1));
4 | [a[i], a[j]] = [a[j], a[i]];
5 | }
6 | return a;
7 | };
8 |
--------------------------------------------------------------------------------
/packages/name-that-dog/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "esModuleInterop": true,
4 | "outDir": "lib",
5 | "jsx": "react"
6 | }
7 | }
8 |
--------------------------------------------------------------------------------
/packages/name-that-dog/yarn.lock:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shiftyp/objects/51bfb23fabd76acd77146b3498d0ff7447ec7057/packages/name-that-dog/yarn.lock
--------------------------------------------------------------------------------
/packages/notebook/.gitignore:
--------------------------------------------------------------------------------
1 | .DS_STORE
2 | dist
3 | node_modules
4 | .cache
5 |
--------------------------------------------------------------------------------
/packages/notebook/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "notebook",
3 | "version": "0.0.1",
4 | "description": "Your private notebook",
5 | "main": "src/index.tsx",
6 | "scripts": {
7 | "start": "parcel ./src/index.html",
8 | "build": "parcel build ./src/index.html"
9 | },
10 | "dependencies": {
11 | "@types/draft-js": "^0.10.40",
12 | "@types/react-select": "^3.0.11",
13 | "classnames": "^2.2.6",
14 | "draft-js": "^0.11.5",
15 | "object-hooks": "^0.0.4",
16 | "react": "^16.13.1",
17 | "react-dom": "16.13.1",
18 | "react-select": "^3.1.0"
19 | },
20 | "devDependencies": {
21 | "@types/react": "16.9.19",
22 | "@types/react-dom": "16.9.5",
23 | "parcel-bundler": "1.12.4",
24 | "sass": "1.26.3",
25 | "typescript": "^3.8.3"
26 | },
27 | "private": true
28 | }
29 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/App.scss:
--------------------------------------------------------------------------------
1 | body {
2 | margin: 0;
3 | }
4 |
5 | .app-body {
6 | max-width: 35em;
7 | min-height: 100vh;
8 | padding: 1em;
9 | border-left: 1px dotted #ccc;
10 | border-right: 1px dotted #ccc;
11 | margin: 0 auto;
12 | box-sizing: border-box;
13 | }
14 |
15 | .app-header {
16 | display: flex;
17 | flex-direction: row;
18 | border-bottom: 1px dotted #ccc;
19 | padding-bottom: 10px;
20 | box-sizing: border-box;
21 |
22 | & > button {
23 | margin-left: 10px;
24 | }
25 |
26 | & > :nth-child(2) {
27 | flex: 1;
28 | margin-left: 0;
29 | }
30 | font-family: sans-serif;
31 | }
32 |
33 | .app-title {
34 | margin: 0;
35 | padding: 0 10px 0 0;
36 | height: 1em;
37 | }
38 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/App.tsx:
--------------------------------------------------------------------------------
1 | import React from 'react';
2 |
3 | import { NoteEditor } from './NoteEditor';
4 | import { useNotebooks } from '../hooks/useNotebooks';
5 | import { NoteSelect } from './NoteSelect';
6 | import { StyleButton } from './StyleButton';
7 |
8 | import './App.scss';
9 |
10 | export const App: React.FC = () => {
11 | const { editor, selector } = useNotebooks();
12 | return (
13 |
14 |
21 | {editor.currentNote && }
22 |
23 | );
24 | };
25 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/NoteEditor.scss:
--------------------------------------------------------------------------------
1 | .note-editor-container {
2 | display: flex;
3 | flex-direction: column;
4 | justify-content: stretch;
5 | padding: 14px;
6 | margin: 14px 0 0 0;
7 | & * {
8 | z-index: 0;
9 | }
10 | font-size: 1.1em;
11 | border: 1px solid #eee;
12 | }
13 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/NoteEditor.tsx:
--------------------------------------------------------------------------------
1 | import React from 'react';
2 | import { Editor, getDefaultKeyBinding } from 'draft-js';
3 | import { EditorLogic } from '../logic/EditorLogic';
4 |
5 | import 'draft-js/dist/Draft.css';
6 |
7 | import './NoteEditor.scss';
8 |
9 | export const NoteEditor: React.FC<{ editor: EditorLogic }> = ({ editor }) => {
10 | return (
11 |
12 | getDefaultKeyBinding(e)}
16 | handleKeyCommand={(command, editorState) => {
17 | editor.updateFromCommand(command);
18 |
19 | if (editor.editorState !== editorState) {
20 | return 'handled';
21 | }
22 | return 'not-handled';
23 | }}
24 | />
25 |
26 | );
27 | };
28 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/NoteSelect.scss:
--------------------------------------------------------------------------------
1 | .note-select-option {
2 | display: flex;
3 | justify-content: space-between;
4 | padding: 14px 10px;
5 | border-bottom: 1px dotted #ccc;
6 |
7 | &:last-child {
8 | border-bottom: none;
9 | }
10 | }
11 |
--------------------------------------------------------------------------------
/packages/notebook/src/components/NoteSelect.tsx:
--------------------------------------------------------------------------------
1 | import React from 'react';
2 | import Select from 'react-select/creatable';
3 |
4 | import { EditorLogic } from '../logic/EditorLogic';
5 | import { NotebookSelectorLogic } from '../logic/NotebookSelectorLogic';
6 |
7 | import './NoteSelect.scss';
8 |
9 | export const NoteSelect: React.FC<{
10 | editor: EditorLogic;
11 | selector: NotebookSelectorLogic;
12 | }> = ({ editor, selector }) => {
13 | const options = selector.currentNotes
14 | ? selector.currentNotes.map(({ id, name, updated }) => ({
15 | value: id,
16 | label: name,
17 | updated: updated,
18 | }))
19 | : [];
20 | const selectedOption =
21 | editor.currentNote &&
22 | options.find((opt) => opt.value === editor.currentNote.id);
23 | return (
24 |