diff --git a/tabs/logging.css b/tabs/logging.css index ad749254..bcf3129d 100644 --- a/tabs/logging.css +++ b/tabs/logging.css @@ -25,6 +25,23 @@ line-height: 20px; color: silver; } + .tab-logging .info { + margin-top: 10px; + } + .tab-logging .info dt { + float: left; + width: 120px; + height: 20px; + line-height: 20px; + + font-weight: bold; + } + .tab-logging .info dd { + display: block; + margin-left: 130px; + height: 20px; + line-height: 20px; + } .tab-logging .buttons { margin-top: 10px; } diff --git a/tabs/logging.html b/tabs/logging.html index a3e66a1f..4724ee79 100644 --- a/tabs/logging.html +++ b/tabs/logging.html @@ -1,13 +1,23 @@
- Data will be logged in this tab only, leaving this tab will cancel logging and application will return to its normal "configurator" operation.
- You are free to select the global update period, data will be written into the log file every 1 second. + Data will be logged in this tab only, leaving the tab will cancel + logging and application will return to its normal "configurator" state.
+ You are free to select the global update period, data will be written into the log file every 1 second for performance reasons.
9 columns (accel[x, y, z], gyro[x, y, z], mag[x, y, z])
3 columns (x, y, z)
one column
+
8 columns by default
+
8 columns by default
+
4 columns
+
+
+
+
+
Samples Saved:
0
+
Log Size:
0 kB
diff --git a/tabs/logging.js b/tabs/logging.js index 8e0fb8d2..6dca9bda 100644 --- a/tabs/logging.js +++ b/tabs/logging.js @@ -2,6 +2,8 @@ function tab_initialize_logging() { ga_tracker.sendAppView('Logging'); GUI.active_tab = 'logging'; + var requested_properties = []; + $('#content').load("./tabs/logging.html", process_html); function process_html() { @@ -13,15 +15,106 @@ function tab_initialize_logging() { $('a.logging').click(function() { if (fileEntry.isFile) { - // TODO: - // grab enabled properties - // grab refresh rate - // start data polling timer - // start buffer flushing sequence & timer (keep fileWriter.readyState in mind) + var clicks = $(this).data('clicks'); + + if (!clicks) { + // reset some variables before start + samples = 0; + log_buffer = []; + requested_properties = []; + + $('.properties input:checked').each(function() { + requested_properties.push($(this).prop('name')); + }); + + if (requested_properties.length) { + function poll_data() { + // save current + crunch_data(); + + // request new + for (var i = 0; i < requested_properties.length; i++) { + send_message(MSP_codes[requested_properties[i]]); + + /* this approach could be used if we want to utilize request time compensation + if (i < requested_properties.length -1) { + send_message(requested_properties[i]); + } else { + send_message(requested_properties[i], false, false, poll_data); + } + */ + } + } + + GUI.interval_add('log_data_pull', poll_data, 1000, true); // refresh rate goes here + GUI.interval_add('flush_data', function() { + if (fileWriter.readyState == 0 || fileWriter.readyState == 2) { + append_to_file(log_buffer.join('\n')); + + $('.samples').text(samples += log_buffer.length); + $('.size').text((fileWriter.length / 1024).toFixed(2) + ' kB'); + + log_buffer = []; + } else { + console.log('IO having trouble keeping up with the data flow'); + } + }, 1000); + + $(this).text('Stop Logging'); + $(this).data("clicks", !clicks); + } else { + GUI.log('Please select at least one property to log'); + } + } else { + GUI.interval_remove('log_data_pull'); + GUI.interval_remove('flush_data'); + + $(this).text('Start Logging'); + $(this).data("clicks", !clicks); + } + } else { + GUI.log('Please select log file'); } }); } + var samples = 0; + var log_buffer = []; + function crunch_data() { + var sample = millitime(); + + for (var i = 0; i < requested_properties.length; i++) { + switch (requested_properties[i]) { + case 'MSP_RAW_IMU': + sample += ',' + SENSOR_DATA.gyroscope; + sample += ',' + SENSOR_DATA.accelerometer; + sample += ',' + SENSOR_DATA.magnetometer; + break; + case 'MSP_ATTITUDE': + sample += ',' + SENSOR_DATA.kinematicsX; + sample += ',' + SENSOR_DATA.kinematicsY; + sample += ',' + SENSOR_DATA.kinematicsZ; + break; + case 'MSP_ALTITUDE': + sample += ',' + SENSOR_DATA.altitude; + break; + case 'MSP_RC': + for (var chan = 0; chan < RC.active_channels; chan++) { + sample += ',' + RC.channels[chan]; + } + break; + case 'MSP_MOTOR': + sample += ',' + MOTOR_DATA; + break; + case 'MSP_DEBUG': + sample += ',' + SENSOR_DATA.debug; + break; + } + } + + log_buffer.push(sample); + } + // IO related methods var fileEntry = null; var fileWriter = null;