An X-Y-Z analysis tool

A tool for visualising single x-y-z planar data

by Jonathon Mascorella

HTML

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<div class="container">
  <div class="row">
    <div class="c1">
      <h1>
        Data Visualiser
      </h1>
      <h3>
        Instructions
      </h3>
      <ul>
        <li>Copy all data rows, including the header, from Excel/Sheets.</li>
        <li>Header row must be x y z (see test data).</li>
        <li>Use <a href="https://csvjson.com/csv2json" target="_blank" class="link">CSV to JSON</a> to convert the data to JSON.
        </li>
        <li>Paste it into the box below</li>
        <li>Click "Validate"</li>
        <li>Data will confirm and draw first line</li>
        <li>Adjust position with "Position" inputs</li>
        <li>Change Frame Delay if desired (35 is ok). A lower number represents a faster speed, and a higher number is a slower speed.</li>
        <li>If all seems ok, then click "Simulate".</li>
        <li>Clicking simulate will re-start the simulation.</li>
      </ul>

      <p><a href="#" id="useTestData" class="uploadButton">Use test data</a> or enter JSON data:</p>
      <textarea id="jsonData"></textarea>
    </div>
    <div class="c2">
      <div class="data_types">
        <span>Data types:</span><br />
        <input type="radio" id="accel" name="multiplier" value=170 checked>
        <label for="accel">Accelerometer</label>
        <input type="radio" id="gyro" name="multiplier" value=4>
        <label for="gyro">Gyroscope</label>
        <input type="radio" id="other" name="multiplier" value=0>
        <label for="other">Other</label>
      </div>

      <div id="xy_multiplier" class="xy_multiplier">
        <span>Multipliers: <em>Displays defaults or can be changed</em></span><br />
        <div class="input_row">
          <span>X: </span><input type="number" step=10 id="x_multi">
          <span>Y: </span><input type="number" step=10 id="y_multi">
          <span>Z: </span><input type="number" step=1 id="z_multi">
        </div>

   ...

CSS

canvas {
    border: 1px dotted black;
}

body {
  font-family: arial, sans-serif;
  font-size: 10pt;
}

.container {
  width: 100%;
 }

.warning {
  color: red;
}

.xy_multiplier, .xy_position, .ani_speed, .data_types {
  padding: 5px 0px;
}

textarea {
  width: 100%;
  height: 220px;
	border: 3px solid #cccccc;
	padding: 5px;
	font-family: arial, sans-serif;
}

input {
  width: 50px;
  box-sizing: border-box;
}

.input_row {
  padding: 5px 0px;
}

.row {
  display: flex;
  margin: 0;
  padding: 0;
}

.c1 {
  flex: 40%;
  margin: 10px;
  padding-right: 10px;
}

.c2 {
  flex: 55%;
  margin: 10px;
}

.uploadButton {
  margin: 5px 2px;
	box-shadow: inset 0px 1px 0px 0px #ffffff;
	background: linear-gradient(to bottom, #f9f9f9 5%, #e9e9e9 100%);
	background-color: #f9f9f9;
	border-radius: 6px;
	border: 1px solid #dcdcdc;
	display: inline-block;
	cursor: pointer;
	color: #666666;
	font-family: Arial, sans-serif;
	font-size: 12px;
	font-weight: bold;
	padding: 4px 12px;
	text-decoration: none;
	text-shadow: 0px 1px 0px #ffffff;
}
.uploadButton:hover {
	background: linear-gradient(to bottom, #e9e9e9 5%, #f9f9f9 100%);
	background-color: #e9e9e9;
}
.uploadButton:active {
	position: relative;
	top: 1px;
}

.redBorder {
  border: 1px solid #ff0000;
}

.greenBorder {
  border: 1px solid #009900;
}

#canvas {
  margin: auto;
  width: 100%;
}

.footer {
  margin-bottom: 30px;
}

JavaScript

// Canvas for drawing
var my_canvas = document.getElementById('canvas'),
  context = my_canvas.getContext("2d");

// Data variables
// Test (static) data
let a_data = [
{
    "x": -0.009,
    "y": 0.906,
    "z": 0.365
  }, {
    "x": -0.004,
    "y": 0.916,
    "z": 0.366
  },
  {
    "x": -0.008,
    "y": 0.91,
    "z": 0.37
  },
  {
    "x": -0.003,
    "y": 0.908,
    "z": 0.368
  },
  {
    "x": -0.002,
    "y": 0.911,
    "z": 0.373
  },
  {
    "x": -0.019,
    "y": 0.912,
    "z": 0.369
  },
  {
    "x": -0.025,
    "y": 0.912,
    "z": 0.369
  },
  {
    "x": -0.015,
    "y": 0.906,
    "z": 0.373
  },
  {
    "x": 0.009,
    "y": 0.908,
    "z": 0.373
  },
  {
    "x": 0.005,
    "y": 0.909,
    "z": 0.374
  },
  {
    "x": -0.006,
    "y": 0.911,
    "z": 0.374
  },
  {
    "x": -0.003,
    "y": 0.917,
    "z": 0.376
  },
  {
    "x": 0.006,
    "y": 0.913,
    "z": 0.367
  },
  {
    "x": 0.011,
    "y": 0.9,
    "z": 0.384
  },
  {
    "x": 0.016,
    "y": 0.902,
    "z": 0.383
  },
  {
    "x": 0.012,
    "y": 0.91,
    "z": 0.372
  },
  {
    "x": 0.004,
    "y": 0.909,
    "z": 0.366
  },
  {
    "x": -0.014,
    "y": 0.904,
    "z": 0.379
  },
  {
    "x": -0.013,
    "y": 0.906,
    "z": 0.375
  },
  {
    "x": 0,
    "y": 0.906,
    "z": 0.362
  },
  {
    "x": 0.015,
    "y": 0.905,
    "z": 0.353
  },
  {
    "x": 0.006,
    "y": 0.917,
    "z": 0.348
  },
  {
    "x": -0.009,
    "y": 0.922,
    "z": 0.355
  },
  {
    "x": -0.006,
    "y": 0.915,
    "z": 0.364
  },
  {
    "x": -0.019,
    "y": 0.911,
    "z": 0.366
  },
  {
    "x": -0.028,
    "y": 0.912,
    "z": 0.364
  },
  {
    "x": -0.041,
    "y": 0.921,
    "z": 0.369
  },
  {
    "x": -0.023,
    "y": 0.921,
    "z": 0.362
  },
  {
    "x": -0.008,
    "y": 0.927,
    "z": 0.359
  },
  {
    "x": 0.007,
    "y": 0.931,
    "z": 0.35
  },
  {
    "x": 0.003,
    "y": 0.906,
    "z": 0.359
  },
  {
    "x": -0.008,
    "y": 0.906,
    "z": 0.375
  },
  {
    "x": -0.016,
    "y":...