Automated settings panel with the JavaScript typeof operator
Tags: dohackathon, webdev, javascript, html
Published: 2020-12-29 12:24:12

To expose JavaScript variables to the UI I came up with a quick automated solution. With a combination of JavaScripts [typeof](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/typeof) operator, [Svelte](https://svelte.dev/) and the HTML Input tag I was able to auto generate a settings panel for primitive data types.

## How?
Let's say we have a settings object like this:
```javascript
const settings: {
  amount: number,
  lengthScale: number,
  lineWidth: number,
  randomColors: boolean
}
```
Which controls the settings for the following drawing:
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/ryj9lk6lb28icu2dwe7q.png)
This drawing is displayed in the parent component. To edit and display the settings object we build a child component in Svelte  named 'SettingsPanel' wich receives the settings as parameter. In the component we then use Sveltes '#each' operator to iterate over the settings keys.
```html
<script lang="ts">
  export let settings;
</script>

<div class="panel-container">
  {#each Object.keys(settings) as key}
    <div class="panel-item">
      {key}: {settings[key]}
    </div>
  {/each}
</div>
```
This will only result in a list of the settings so let's map an input field to the settings type. To do this we use the typeof operator:
```html
<div class="panel-item">
  <label for={key}>{key}:</label>
  {#if typeof settings[key] === 'boolean'}
    <input type="checkbox" bind:checked={settings[key]} id={key} />
  {:else if typeof settings[key] === 'number'}
    <input type="number" bind:value={settings[key]} id={key} />
  {:else}
    <input type="text" bind:value={settings[key]} id={key} />
  {/if}
</div>
```
If you want the parent component to react on the changed settings you can simply emit an event on the click of a button:
```html
<script lang="ts">
  import { createEventDispatcher } from "svelte";
  const dispatch = createEventDispatcher();
  function apply() {
    dispatch("apply");
  }

  export let settings;
</script>
<!-- ... -->
<button on:click={apply}>apply</button>
```
Some styles could be added to the panel to make it look a bit better. Notice how the 'input[type="number"]' selector is used to style only the specified inputs:
```css
.panel-container {
  justify-content: space-between;
  border-radius: 10px 0 0 10px;
}
.panel-item {
  display: flex;
  justify-content: space-between;
  margin: 0.5rem 0;
}
button {
  margin-bottom: 0.5rem;
  background-color: #fff;
  color: #333;
  border-color: #fff;
  border-style: solid;
  border-radius: 5px;
  padding: 0.5rem;
  text-transform: uppercase;
}
h3 {
  text-decoration: underline;
}
input[type="number"] {
  background: #666;
  color: #fff;
  border-color: #fff;
  border-style: solid;
  border-radius: 5px;
  padding-left: 0.5rem;
}
input[type="text"] {
  background: #666;
  color: #fff;
  border-color: #fff;
  border-style: solid;
  border-radius: 5px;
  padding-left: 0.5rem;
}
```
As a last step we import the SettingsPanel Component in the parent component, pass in the settings and react on an emitted event.

```html
<script lang="ts">
  import SettingsPanel from "../components/SettingsPanel.svelte";
  const settings: {
    amount: number,
    lengthScale: number,
    lineWidth: number,
    randomColors: boolean
  };
  function apply() {
    // do something with new settings
	}
</script>
<SettingsPanel {settings} on:apply={apply} />
```
And there we have it. A simple automated settings panel for JS primitives with Svelte.
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/hqs35oj055zj7azozjxr.png)
## Creative Coding Workbench
This article is part of my progress for the Digital Ocean Hackathon Project 'Creative Coding Workbench':
### Used features:
 - ~~draw sketch on HTML canvas~~
 - ~~expose sketch settings to UI~~
 - ~~export sketch for print~~
 - toggle sketch animation
 - save sketch to a library
 - load sketch from a library
 - edit sketch from a library
 - ...

### Used Technologies:
 - Sapper 
 - Digitial Ocean App Platform
 - ...

Stay tuned for updates on this project as there will be posts for each part of it.