From 2bbf97cbccb2c72e9817a145c89b0c5cc238e74e Mon Sep 17 00:00:00 2001 From: gluaxspeed Date: Fri, 24 Jan 2020 19:52:31 -0500 Subject: [PATCH 1/3] MenuBar and Menu components --- package.json | 4 +- src/components/Menu/RNMenu.ts | 51 + src/components/Menu/index.ts | 43 + src/components/MenuBar/RNMenuBar.ts | 37 + src/components/MenuBar/index.ts | 43 + src/components/Window/RNWindow.ts | 17 +- src/demo.tsx | 68 +- src/index.ts | 2 + yarn.lock | 1586 +++++++++++++++++++++++++++ 9 files changed, 1830 insertions(+), 21 deletions(-) create mode 100644 src/components/Menu/RNMenu.ts create mode 100644 src/components/Menu/index.ts create mode 100644 src/components/MenuBar/RNMenuBar.ts create mode 100644 src/components/MenuBar/index.ts create mode 100644 yarn.lock diff --git a/package.json b/package.json index bd4cefe9..5ab4263a 100644 --- a/package.json +++ b/package.json @@ -22,17 +22,15 @@ "dependencies": { "@types/react-reconciler": "^0.18.0", "phin": "^3.4.1", + "@nodegui/nodegui": ">=0.22.0", "react-deep-force-update": "^2.1.3", "react-proxy": "^2.0.8", "react-reconciler": "^0.25.1" }, "peerDependencies": { - "@nodegui/nodegui": ">=0.17.0", - "@nodegui/qode": "*", "react": "^16.9.0" }, "devDependencies": { - "@nodegui/nodegui": "^0.22.0", "@types/node": "^14.0.12", "prettier": "^2.0.5", "react": "^16.13.1", diff --git a/src/components/Menu/RNMenu.ts b/src/components/Menu/RNMenu.ts new file mode 100644 index 00000000..43c5a503 --- /dev/null +++ b/src/components/Menu/RNMenu.ts @@ -0,0 +1,51 @@ +import { NodeWidget, QAction, QMenu, QMenuSignals } from "@nodegui/nodegui"; +import { ViewProps, setViewProps } from "../View/RNView"; +import { RNWidget } from "../config"; +import { throwUnsupported } from "../../utils/helpers"; + +export interface MenuProps extends ViewProps { + title?: string; + action?: QAction; + actions?: QAction[]; +} + +const setMenuProps = ( + widget: RNMenu, + newProps: MenuProps, + oldProps: MenuProps +) => { + const setter: MenuProps = { + set title(title: string) { + widget.setTitle(title); + }, + set action(action: QAction) { + widget.addAction(action); + }, + set actions(actions: QAction[]) { + actions.forEach(action => { + widget.addAction(action); + }); + } + }; + Object.assign(setter, newProps); + setViewProps(widget, newProps, oldProps); +}; + +export class RNMenu extends QMenu implements RNWidget { + setProps(newProps: MenuProps, oldProps: MenuProps): void { + setMenuProps(this, newProps, oldProps); + } + appendInitialChild(child: NodeWidget): void { + throwUnsupported(this); + } + appendChild(child: NodeWidget): void { + throwUnsupported(this); + } + insertBefore(child: NodeWidget, beforeChild: NodeWidget): void { + throwUnsupported(this); + } + removeChild(child: NodeWidget): void { + throwUnsupported(this); + } + static tagName = "menu"; +}; diff --git a/src/components/Menu/index.ts b/src/components/Menu/index.ts new file mode 100644 index 00000000..e06ee6fd --- /dev/null +++ b/src/components/Menu/index.ts @@ -0,0 +1,43 @@ +import { Fiber } from "react-reconciler"; +import { registerComponent, ComponentConfig } from "../config"; +import { RNMenu, MenuProps } from "./RNMenu"; +import { AppContainer } from "../../reconciler"; +class MenuConfig extends ComponentConfig { + tagName = RNMenu.tagName; + shouldSetTextContent(nextProps: MenuProps): boolean { + return false; + } + createInstance( + newProps: MenuProps, + rootInstance: AppContainer, + context: any, + workInProgress: Fiber + ): RNMenu { + const widget = new RNMenu(); + widget.setProps(newProps, {}); + return widget; + } + commitMount( + instance: RNMenu, + newProps: MenuProps, + internalInstanceHandle: any + ): void { + if (newProps.visible !== false) { + instance.show(); + } + return; + } + commitUpdate( + instance: RNMenu, + updatePayload: any, + oldProps: MenuProps, + newProps: MenuProps, + finishedWork: Fiber + ): void { + instance.setProps(newProps, oldProps); + } +} + +export const Menu = registerComponent( + new MenuConfig() +); diff --git a/src/components/MenuBar/RNMenuBar.ts b/src/components/MenuBar/RNMenuBar.ts new file mode 100644 index 00000000..850f99be --- /dev/null +++ b/src/components/MenuBar/RNMenuBar.ts @@ -0,0 +1,37 @@ +import { NodeWidget, Orientation, QMenu, QMenuBar, QMenuBarSignals } from "@nodegui/nodegui"; +import { ViewProps, setViewProps } from "../View/RNView"; +import { RNWidget } from "../config"; +import { throwUnsupported } from "../../utils/helpers"; + +export interface MenuBarProps extends ViewProps {} + +const setMenuBarProps = ( + widget: RNMenuBar, + newProps: MenuBarProps, + oldProps: MenuBarProps +) => { + const setter: MenuBarProps = { + + }; + Object.assign(setter, newProps); + setViewProps(widget, newProps, oldProps); +}; + +export class RNMenuBar extends QMenuBar implements RNWidget { + setProps(newProps: MenuBarProps, oldProps: MenuBarProps): void { + setMenuBarProps(this, newProps, oldProps); + } + appendInitialChild(child: QMenu): void { + this.addMenu(child); + } + appendChild(child: QMenu): void { + this.addMenu(child); + } + insertBefore(child: NodeWidget, beforeChild: NodeWidget): void { + throwUnsupported(this); + } + removeChild(child: NodeWidget): void { + throwUnsupported(this); + } + static tagName = "menubar"; +}; diff --git a/src/components/MenuBar/index.ts b/src/components/MenuBar/index.ts new file mode 100644 index 00000000..a5114a3f --- /dev/null +++ b/src/components/MenuBar/index.ts @@ -0,0 +1,43 @@ +import { Fiber } from "react-reconciler"; +import { registerComponent, ComponentConfig } from "../config"; +import { RNMenuBar, MenuBarProps } from "./RNMenuBar"; +import { AppContainer } from "../../reconciler"; +class MenuBarConfig extends ComponentConfig { + tagName = RNMenuBar.tagName; + shouldSetTextContent(nextProps: MenuBarProps): boolean { + return false; + } + createInstance( + newProps: MenuBarProps, + rootInstance: AppContainer, + context: any, + workInProgress: Fiber + ): RNMenuBar { + const widget = new RNMenuBar(); + widget.setProps(newProps, {}); + return widget; + } + commitMount( + instance: RNMenuBar, + newProps: MenuBarProps, + internalInstanceHandle: any + ): void { + if (newProps.visible !== false) { + instance.show(); + } + return; + } + commitUpdate( + instance: RNMenuBar, + updatePayload: any, + oldProps: MenuBarProps, + newProps: MenuBarProps, + finishedWork: Fiber + ): void { + instance.setProps(newProps, oldProps); + } +} + +export const MenuBar = registerComponent( + new MenuBarConfig() +); diff --git a/src/components/Window/RNWindow.ts b/src/components/Window/RNWindow.ts index f1403830..dda13f5a 100644 --- a/src/components/Window/RNWindow.ts +++ b/src/components/Window/RNWindow.ts @@ -1,4 +1,4 @@ -import { QMainWindow, NodeWidget, QMainWindowSignals } from "@nodegui/nodegui"; +import { QMainWindow, NodeWidget, QMainWindowSignals, QMenuBar } from "@nodegui/nodegui"; import { setViewProps, ViewProps } from "../View/RNView"; import { RNWidget } from "../config"; @@ -30,12 +30,19 @@ export class RNWindow extends QMainWindow implements RNWidget { } child.close(); } - appendInitialChild(child: NodeWidget): void { - if (this.centralWidget) { - console.warn("MainWindow can't have more than one child node"); + appendInitialChild(child: NodeWidget | QMenuBar): void { + if (this.menuBar() === undefined && child instanceof QMenuBar) { + this.setMenuBar(child); + return; + } + + if (!this.centralWidget && !(child instanceof QMenuBar)) { + this.setCentralWidget(child); + return; + } else { + console.warn("MainWindow can't have more than one child node and more than one menubar."); return; } - this.setCentralWidget(child); } appendChild(child: NodeWidget): void { this.appendInitialChild(child); diff --git a/src/demo.tsx b/src/demo.tsx index 4d1bf3c4..54599eab 100644 --- a/src/demo.tsx +++ b/src/demo.tsx @@ -1,9 +1,34 @@ -import React, { useState } from "react"; -import { Renderer, Window, Button } from "./index"; -import { BoxView } from "./components/BoxView"; +import React from "react"; +import { + Renderer, + Button, + Window, + View, + AnimatedImage, + ComboBox, + Text, + MenuBar, + Menu, +} from "./index"; +import { + QAction, + QApplication, + QIcon, + QVariant, + QPushButtonSignals, +} from "@nodegui/nodegui"; import { useEventHandler } from "./hooks"; import { QPushButtonSignals, Direction } from "@nodegui/nodegui"; +const quitAction = new QAction(); +quitAction.setText("&Quit"); +quitAction.addEventListener("triggered", () => { + const app = QApplication.instance(); + app.exit(0); +}); + +const fileActions: QAction[] = [quitAction]; + const App = () => { const [additionalButtons, setAdditionalButtons] = useState([]); const [direction, setDirection] = useState(Direction.LeftToRight); @@ -21,8 +46,9 @@ const App = () => { const removeHandler = useEventHandler( { - clicked: () => - setAdditionalButtons((buttons) => buttons.slice(0, buttons.length - 1)), + clicked: (clicked) => { + console.log("clicked"); + }, }, [] ); @@ -37,14 +63,30 @@ const App = () => { return ( - -