diff --git a/object_database/web/content/src/CellHandler.js b/object_database/web/content/src/CellHandler.js index a8a40a5c..9fe7a236 100644 --- a/object_database/web/content/src/CellHandler.js +++ b/object_database/web/content/src/CellHandler.js @@ -519,6 +519,28 @@ class CellHandler { // listent to only devtools content-script messages if (event.data.type == "cells_devtools_CS") { console.log("receiving message from CS: ", event.data); + // when we click on a tree node in devtools we expect info + // about the cell to be sent back (props, source etc) + if (event.data.request == "info") { + const nodeId = event.data.nodeId; + // the cell objet can't be cloned and sent over + // the window message API as is + const cell = this.activeCells[nodeId]; + const dataToSend = cell.props // TODO; + const msg = { + status: "info", + nodeId: nodeId, + data: dataToSend + } + this.sendMessageToDevtools(msg); + } else if (event.data.request == "propChange") { + const nodeId = event.data.nodeId; + const cell = this.activeCells[nodeId]; + const data = cell.props; + data[event.data.name] = event.data.value; + this.updateCell(nodeId, cell.namedChildren, data); + cell.rebuildDomElement(); + } } } }) diff --git a/object_database/web/devtools/background.js b/object_database/web/devtools/background.js index 7e56bad1..7725ce07 100644 --- a/object_database/web/devtools/background.js +++ b/object_database/web/devtools/background.js @@ -2,7 +2,7 @@ * The background script handles communication to and from * the content script, embedded in the document, and * the panel scripts, living in devtools. - * These communiccation are handled by chrome.runtime connection + * These communication are handled by chrome.runtime connection * ports. * The connections are initialized int he content and panel scripts, * respectively. Here we listen for these connection and create diff --git a/object_database/web/devtools/cells_panel.css b/object_database/web/devtools/cells_panel.css index 369acfdb..546b6370 100644 --- a/object_database/web/devtools/cells_panel.css +++ b/object_database/web/devtools/cells_panel.css @@ -7,6 +7,7 @@ body { display: flex; flex-direction: row; margin: 0px; + background-color: black; } div#main { @@ -19,12 +20,34 @@ div#main { div#cell-info { display: flex; + flex-direction: column; justify-content: center; align-items: center; min-width: 30%; text-align: center; font-family: Roboto; font-size: 20px; + color: white; + border-left: 1px ridge rgb(135, 210, 173); +} + +div#cell-info span#node-args { + border-bottom: 1px solid rgb(135, 210, 173); + margin-top: 5px; + margin-bottom: 5px; + color: rgb(135, 210, 173); +} + +div#cell-info > table { + border: 1px dotted; +} + +div#cell-info > table td { + border: 1px solid rgb(135, 210, 173); +} + +div#cell-info > table input { + border: 1px solid rgb(135, 210, 173); } .node { diff --git a/object_database/web/devtools/cells_panel.html b/object_database/web/devtools/cells_panel.html index b53cefe6..8ac18bee 100644 --- a/object_database/web/devtools/cells_panel.html +++ b/object_database/web/devtools/cells_panel.html @@ -10,7 +10,7 @@
-
some cells data here
+
Click on a tree node to get more info
diff --git a/object_database/web/devtools/js/cell_panel.js b/object_database/web/devtools/js/cell_panel.js index 5f692b88..e212376c 100644 --- a/object_database/web/devtools/js/cell_panel.js +++ b/object_database/web/devtools/js/cell_panel.js @@ -30,6 +30,10 @@ function handleMessageFromBackground(msg){ cellsTreeDisplay(msg.cells); console.log(msg.cells); } + break; + case "info": + handleInfoFromBackground(msg); + break; } } @@ -57,6 +61,8 @@ const clearDisplay = () => { // display the tree const cellsTreeDisplay = (cells) => { clearDisplay(); + const info = document.getElementById("cell-info"); + info.textContent = "click on a node to see more info"; // init and run // NOTE: the tree class itself attaches the // svg element to #main @@ -103,13 +109,15 @@ const cellsTreeDisplay = (cells) => { // info panel display const updateInfoPanel = (node) => { const infoPanel = document.getElementById("cell-info"); + // clear it out first + infoPanel.textContent = null; + const infoSpan = document.createElement("span"); const id = node.getAttribute("data-original-id"); // we need to retrieve the source code for the node window.sendMessageToBackground({ action: "notifyCS", event: "click", nodeId: id, - request: "source" }) const name = node.name; let info = `${name}\ncell-id: ${id}`; @@ -119,6 +127,79 @@ const updateInfoPanel = (node) => { info = `${info}\nsubscribed to cell-id: ${parentSubtree.id}`; } - infoPanel.innerText = info; + infoSpan.innerText = info; + infoPanel.append(infoSpan); + // args/props section + const span = document.createElement('span'); + span.textContent = "Cell Arguments"; + span.setAttribute("id", "node-args"); + infoPanel.append(span); +} + + +const createPropsTable = (msg) => { + const propsDict = msg.data; + const id = msg.nodeId; + const table = document.createElement('table'); + // header + const thead = document.createElement('thead'); + const tr = document.createElement('tr'); + const thName = document.createElement('th'); + const thVal = document.createElement('th'); + thead.append(tr); + tr.append(thName); + tr.append(thVal); + thName.textContent = "Name"; + thVal.textContent = "Val"; + table.append(thead); + // body + const tbody = document.createElement('tbody'); + table.append(tbody); + Object.keys(propsDict).forEach((key) => { + const tr = document.createElement('tr'); + tr.setAttribute("data-nodeId", id); + const tdKey = document.createElement('td'); + const tdValue = document.createElement('input'); + tdValue.addEventListener('keydown', handlePropChange); + tdValue.setAttribute("type", "text"); + tdKey.textContent = key; + tdValue.setAttribute("placeholder", propsDict[key]); + tr.append(tdKey); + tr.append(tdValue); + tbody.append(tr); + }); + + return table; } +const handlePropChange = (event) => { + console.log("changing prop val", event.key); + if (event.shiftKey && event.key == "Enter") { + window.sendMessageToBackground({ + action: "notifyCS", + event: "propChange", + nodeId: event.target.parentElement.getAttribute("data-nodeId"), + details: { + "name": event.target.parentElement.firstChild.textContent, + "value": event.target.value + } + }) + } +} + +// I handle incoming background 'info' messages +// ie generally these are coming from a devtools request +// to the target application and response from the target app +// returning via content script -> background +const handleInfoFromBackground = (msg) => { + console.log("message from backgound", msg) + const infoPanel = document.getElementById("cell-info"); + if (Object.keys(msg.data).length) { + const table = createPropsTable(msg); + infoPanel.append(table); + } else { + const span = document.createElement('span'); + span.textContent = "This node takes no args"; + infoPanel.append(span); + } +} diff --git a/object_database/web/devtools/js/inspect_window_utils.js b/object_database/web/devtools/js/inspect_window_utils.js index ba696cd4..75493ca2 100644 --- a/object_database/web/devtools/js/inspect_window_utils.js +++ b/object_database/web/devtools/js/inspect_window_utils.js @@ -18,7 +18,11 @@ const handleBackgroundMessage = (msg) => { case "click": onClick(msg.nodeId); + + case "propChange": + onPropChange(msg.nodeId, msg.details.name, msg.details.value); } + } // Helpers @@ -59,8 +63,20 @@ const onClick = (id) => { // get the source code for the cell and send over the devtools const msg = { type: "cells_devtools_CS", - request: "source", + request: "info", nodeId: id }; window.postMessage(msg); } + +const onPropChange = (id, name, value) => { + // get the source code for the cell and send over the devtools + const msg = { + type: "cells_devtools_CS", + request: "propChange", + nodeId: id, + name: name, + value: value + }; + window.postMessage(msg); +}