Skip to content

Commit

Permalink
make json collapsible
Browse files Browse the repository at this point in the history
  • Loading branch information
adolfdaniel committed Sep 12, 2023
1 parent 2754bdd commit e054c31
Show file tree
Hide file tree
Showing 3 changed files with 105 additions and 43 deletions.
56 changes: 56 additions & 0 deletions manifest-generator/components/manifest-view/json-array.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
const template = document.createElement('template');
template.innerHTML = `
<style>
.node {
display: flex;
flex-direction: column;
margin-bottom: 1rem;
}
.node::before {
content: '[';
}
.node::after {
content: ']';
}
</style>
<div class="node"></div>
`;

class JSONArray extends HTMLElement {
constructor() {
super();
this.attachShadow({ mode: 'open' });
this.shadowRoot.appendChild(template.content.cloneNode(true));
}

connectedCallback() {
console.log('connected');
const jsonValue = this.getAttribute('json');
this.json = JSON.parse(decodeURIComponent(jsonValue));
this.render();
}

disconnectedCallback() {
console.log('disconnected');
}

render() {
const jsonValue = this.json;
const arrayNode = this.shadowRoot.querySelector('.node');
for (let json of jsonValue) {
const node = document.createElement('json-view');
node.setAttribute('json', encodeURIComponent(JSON.stringify(json)));
arrayNode.appendChild(node);
}
}

observedAttributes() {
return ['json'];
}
}

customElements.define('json-array', JSONArray);

export default JSONArray;
29 changes: 24 additions & 5 deletions manifest-generator/components/manifest-view/json.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import Node from "./node.js";
import "./node.js";

// Define a custom element for representing a JSON document
const template = document.createElement('template');
Expand All @@ -10,6 +10,12 @@ template.innerHTML = `
max-width: 600px;
margin: 0 auto;
}
.json::before {
content: '{';
}
.json::after {
content: '}';
}
</style>
<div class="json"></div>
`;
Expand All @@ -19,13 +25,12 @@ class JSONView extends HTMLElement {
super();
this.attachShadow({ mode: 'open' });
this.shadowRoot.appendChild(template.content.cloneNode(true));

const jsonValue = this.getAttribute('json');
this.json = JSON.parse(decodeURIComponent(jsonValue));
}

connectedCallback() {
console.log('connected');
const jsonValue = this.getAttribute('json');
this.json = JSON.parse(decodeURIComponent(jsonValue));
this.render();
}

Expand All @@ -34,9 +39,23 @@ class JSONView extends HTMLElement {
}

render() {
const json = this.json;
const jsonView = this.shadowRoot.querySelector('.json');
jsonView.addEventListener('click', (e) => {
const isCollapsed = jsonView.getAttribute('collapsed') !== null;
jsonView.toggleAttribute('collapsed');
if (isCollapsed) {
jsonView.innerHTML = '';
this.renderNodes(jsonView, this.json);
} else {
jsonView.innerHTML = '...';
}
e.stopPropagation();
});

this.renderNodes(jsonView, this.json);
}

renderNodes(jsonView, json) {
Object.keys(json).forEach(key => {
const node = document.createElement('json-node');
var nodeType = typeof json[key];
Expand Down
63 changes: 25 additions & 38 deletions manifest-generator/components/manifest-view/node.js
Original file line number Diff line number Diff line change
@@ -1,46 +1,28 @@
import './json-array.js';

// Define a custom element for representing a JSON node
const template = document.createElement('template');
template.innerHTML = `
<style>
.node {
display: flex;
flex-direction: column;
flex-direction: row;
margin-bottom: 1rem;
}
.node[collapsed] .value {
display: none;
}
.node .collapser::before {
content: '-';
}
.node[collapsed] .collapser::before {
content: '+';
}
.node .key {
color: #a71d5d;
font-weight: bold;
margin-left: 1rem;
white-space: nowrap;
}
.node .value {
margin-left: 1rem;
}
.node .collapser {
cursor: pointer;
user-select: none;
font-size: 1.5rem;
color: #a71d5d;
}
</style>
<div class="node">
<div>
<span class="collapser"></span>
<span class="key"></span>
</div>
<span class="value"></span>
</div>
`;
Expand All @@ -55,9 +37,6 @@ class Node extends HTMLElement {
console.log('connected');
this.key = this.getAttribute('key');
this.value = this.getAttribute('value');
if (this.getAttribute('type') === 'array') {
this.shadowRoot.querySelector('.node').setAttribute('collapsed', '');
}
this.render();
}

Expand All @@ -71,30 +50,38 @@ class Node extends HTMLElement {

render() {
const node = this.shadowRoot.querySelector('.node');
node.addEventListener('click', (e) => {
node.toggleAttribute('collapsed');
e.stopPropagation();
});

const type = this.getAttribute('type');
const key = this.shadowRoot.querySelector('.key');
const value = this.shadowRoot.querySelector('.value');
key.textContent = this.key;
key.textContent = `"${this.key}" : `;
if (type === 'object' || type === 'array') {
node.addEventListener('click', (e) => {
const isCollapsed = node.getAttribute('collapsed') !== null;
node.toggleAttribute('collapsed');
if (!isCollapsed) {
value.innerHTML = '...';
} else {
this.renderValue(value, type, this.value);
}
e.stopPropagation();
});
}
this.renderValue(value, type, this.value);
}

renderValue(element, type, value) {
if (type === 'array') {
const jsonValue = JSON.parse(decodeURIComponent(this.value));
for (let json of jsonValue) {
document.createElement('json-view');
value.innerHTML += `<json-view json="${encodeURIComponent(JSON.stringify(json))}"></json-view>`;
}
element.innerHTML = `<json-array json="${value}"></json-array>`;
return;
}
if (type === 'object') {
document.createElement('json-view');
value.innerHTML = `<json-view json="${encodeURIComponent(this.value)}"></json-view>`;
element.innerHTML = `<json-view json="${value}"></json-view>`;
return;
}
value.textContent = this.value;
element.textContent = value;
}

}

customElements.define('json-node', Node);
Expand Down

0 comments on commit e054c31

Please sign in to comment.