Skip to content

Commit 0819102

Browse files
authored
Merge pull request #41 from betaflight/Dshot-Blackbox
Fix Motor Scaling on Blackbox Log when D-Shot is used
2 parents 563b655 + 0b36d92 commit 0819102

File tree

9 files changed

+56
-11
lines changed

9 files changed

+56
-11
lines changed

changelog.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ <h2> 2.5.8 - Minor Bug Fixes and UI layout</h2>
5151
<li>Fix Issue #36; viewer was not parsing version number correctly for filter scaling. Refactored functions to use library semver.</li>
5252
<li>UI Overhall; improved handling for smaller screens.</li>
5353
<li>Changelog added to Welcome screen</li>
54-
<li>Add DShot to header dialog</li>
54+
<li>Add DShot to header dialog and scale motors independently to rcCommand[Throttle]</li>
5555
<li>Update to gyro scale for BF 3.1.0; logged data is now scaled in the flight controller.</li>
5656
</ul>
5757

index.html

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1041,7 +1041,16 @@ <h5 class="modal-title-craft"></h5>
10411041
</tr>
10421042
</tbody>
10431043
</table>
1044-
</div>
1044+
<table class="parameter cf">
1045+
<tbody>
1046+
<tr>
1047+
<td name="digitalIdleOffset"><label>D-Shot Offset (%)</label><input type="number" step="0.01" min="0" max="1" /></td>
1048+
<td name="motorOutputLow"><label>D-Shot Motor Low</label><input type="number" step="10" min="0" max="2047" /></td>
1049+
<td name="motorOutputHigh"><label>D-Shot Motor High</label><input type="number" step="10" min="0" max="2047" /></td>
1050+
</tr>
1051+
</tbody>
1052+
</table>
1053+
</div>
10451054
</div>
10461055
<div class="gui_box grey voltagecurrent">
10471056
<div class="gui_box_titlebar">

js/craft_2d.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -227,7 +227,7 @@ function Craft2D(flightLog, canvas, propColors) {
227227

228228
canvasContext.moveTo(0, 0);
229229
canvasContext.arc(0, 0, bladeRadius, -Math.PI / 2, -Math.PI / 2 + Math.PI * 2
230-
* Math.max(motorValue - sysConfig.minthrottle, 0) / (sysConfig.maxthrottle - sysConfig.minthrottle), false);
230+
* Math.max(motorValue - sysConfig.motorOutput[0], 0) / (sysConfig.motorOutput[1] - sysConfig.motorOutput[0]), false);
231231

232232
canvasContext.fill();
233233

js/craft_3d.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -287,7 +287,7 @@ function Craft3D(flightLog, canvas, propColors) {
287287
propShells[i].remove(props[i]);
288288

289289
var
290-
throttlePos = Math.min(Math.max(frame[frameFieldIndexes["motor[" + motorOrder[i] + "]"]] - sysInfo.minthrottle, 0) / (sysInfo.maxthrottle - sysInfo.minthrottle), 1.0),
290+
throttlePos = Math.min(Math.max(frame[frameFieldIndexes["motor[" + motorOrder[i] + "]"]] - sysInfo.motorOutput[0], 0) / (sysInfo.motorOutput[1] - sysInfo.motorOutput[0]), 1.0),
291291
propLevel = Math.round(throttlePos * (NUM_PROP_LEVELS - 1)),
292292
geometry = propGeometry[propLevel],
293293
prop = new THREE.Mesh(geometry, propMaterials[motorOrder[i]]);

js/flightlog.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1080,6 +1080,11 @@ FlightLog.prototype.rcCommandRawToThrottle = function(value) {
10801080
return Math.min(Math.max(((value - this.getSysConfig().minthrottle) / (this.getSysConfig().maxthrottle - this.getSysConfig().minthrottle)) * 100.0, 0.0),100.0);
10811081
};
10821082

1083+
FlightLog.prototype.rcMotorRawToPct = function(value) {
1084+
// Motor displayed as percentage
1085+
return Math.min(Math.max(((value - this.getSysConfig().motorOutput[0]) / (this.getSysConfig().motorOutput[1] - this.getSysConfig().motorOutput[0])) * 100.0, 0.0),100.0);
1086+
};
1087+
10831088
FlightLog.prototype.getPIDPercentage = function(value) {
10841089
// PID components and outputs are displayed as percentage (raw value is 0-1000)
10851090
return (value / 10.0);

js/flightlog_fields_presenter.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -257,15 +257,16 @@ function FlightLogFieldPresenter() {
257257
return Math.round(flightLog.rcCommandRawToDegreesPerSecond(value,2), currentFlightMode) + " deg/s";
258258

259259
case 'rcCommand[3]':
260-
case 'motor[0]':
260+
return Math.round(flightLog.rcCommandRawToThrottle(value)) + " %";
261+
case 'motor[0]':
261262
case 'motor[1]':
262263
case 'motor[2]':
263264
case 'motor[3]':
264265
case 'motor[4]':
265266
case 'motor[5]':
266267
case 'motor[6]':
267268
case 'motor[7]':
268-
return Math.round(flightLog.rcCommandRawToThrottle(value)) + " %";
269+
return Math.round(flightLog.rcMotorRawToPct(value)) + " %";
269270

270271
case 'rcCommands[0]':
271272
case 'rcCommands[1]':

js/flightlog_parser.js

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,9 @@ var FlightLogParser = function(logData) {
5555
//Predict the last time value written in the main stream
5656
FLIGHT_LOG_FIELD_PREDICTOR_LAST_MAIN_FRAME_TIME = 10,
5757

58+
//Predict that this field is minthrottle
59+
FLIGHT_LOG_FIELD_PREDICTOR_MINMOTOR = 11,
60+
5861
//Home coord predictors appear in pairs (two copies of FLIGHT_LOG_FIELD_PREDICTOR_HOME_COORD). Rewrite the second
5962
//one we see to this to make parsing easier
6063
FLIGHT_LOG_FIELD_PREDICTOR_HOME_COORD_1 = 256,
@@ -256,6 +259,8 @@ var FlightLogParser = function(logData) {
256259
debug_mode:null, // Selected Debug Mode
257260
features:null, // Activated features (e.g. MOTORSTOP etc)
258261
Craft_name:null, // Craft Name
262+
motorOutput:[null,null], // Minimum and maximum outputs to motor's
263+
digitalIdleOffset:null, // min throttle for d-shot (as a percentage)
259264
unknownHeaders : [] // Unknown Extra Headers
260265
},
261266

@@ -405,7 +410,13 @@ var FlightLogParser = function(logData) {
405410

406411
// Betaflight Log Header Parameters
407412
case "minthrottle":
413+
that.sysConfig[fieldName] = parseInt(fieldValue, 10);
414+
that.sysConfig.motorOutput[0] = that.sysConfig[fieldName]; // by default, set the minMotorOutput to match minThrottle
415+
break;
408416
case "maxthrottle":
417+
that.sysConfig[fieldName] = parseInt(fieldValue, 10);
418+
that.sysConfig.motorOutput[1] = that.sysConfig[fieldName]; // by default, set the maxMotorOutput to match maxThrottle
419+
break;
409420
case "rcRate":
410421
case "rcExpo":
411422
case "rcYawExpo":
@@ -485,6 +496,8 @@ var FlightLogParser = function(logData) {
485496
}
486497
break;
487498

499+
case "digitalIdleOffset":
500+
that.sysConfig[fieldName] = parseInt(fieldValue, 10) / 100.0;
488501

489502
/** Cleanflight Only log headers **/
490503
case "dterm_cut_hz":
@@ -515,6 +528,7 @@ var FlightLogParser = function(logData) {
515528
case "navrPID":
516529
case "levelPID":
517530
case "velPID":
531+
case "motorOutput":
518532
that.sysConfig[fieldName] = parseCommaSeparatedString(fieldValue);
519533
break;
520534
case "magPID":
@@ -927,6 +941,15 @@ var FlightLogParser = function(logData) {
927941
*/
928942
value = (value | 0) + that.sysConfig.minthrottle;
929943
break;
944+
case FLIGHT_LOG_FIELD_PREDICTOR_MINMOTOR:
945+
/*
946+
* Force the value to be a *signed* 32-bit integer. Encoded motor values can be negative when motors are
947+
* below minthrottle, but despite this motor[0] is encoded in I-frames using *unsigned* encoding (to
948+
* save space for positive values). So we need to convert those very large unsigned values into their
949+
* corresponding 32-bit signed values.
950+
*/
951+
value = (value | 0) + (that.sysConfig.motorOutput[0] | 0); // motorOutput[0] is the min motor output
952+
break;
930953
case FLIGHT_LOG_FIELD_PREDICTOR_1500:
931954
value += 1500;
932955
break;

js/graph_config.js

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -233,9 +233,9 @@ GraphConfig.load = function(config) {
233233
try {
234234
if (fieldName.match(/^motor\[/)) {
235235
return {
236-
offset: -(sysConfig.maxthrottle + sysConfig.minthrottle) / 2,
236+
offset: -(sysConfig.motorOutput[1] + sysConfig.motorOutput[0]) / 2,
237237
power: 1.0,
238-
inputRange: (sysConfig.maxthrottle - sysConfig.minthrottle) / 2,
238+
inputRange: (sysConfig.motorOutput[1] - sysConfig.motorOutput[0]) / 2,
239239
outputRange: 1.0
240240
};
241241
} else if (fieldName.match(/^servo\[/)) {
@@ -362,9 +362,9 @@ GraphConfig.load = function(config) {
362362
};
363363
case 'MIXER':
364364
return {
365-
offset: -(sysConfig.maxthrottle + sysConfig.minthrottle) / 2,
365+
offset: -(sysConfig.motorOutput[1] + sysConfig.motorOutput[0]) / 2,
366366
power: 1.0,
367-
inputRange: (sysConfig.maxthrottle - sysConfig.minthrottle) / 2,
367+
inputRange: (sysConfig.motorOutput[1] - sysConfig.motorOutput[0]) / 2,
368368
outputRange: 1.0
369369
};
370370
case 'BATTERY':

js/header_dialog.js

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,10 @@ function HeaderDialog(dialog, onSave) {
5151
{name:'debug_mode' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.0.0', max:'999.9.9'},
5252
{name:'gyro_notch_hz_2' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.0.1', max:'999.9.9'},
5353
{name:'gyro_notch_cutoff_2' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.0.1', max:'999.9.9'},
54-
{name:'pidController' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'0.0.0', max:'3.0.1'}
54+
{name:'pidController' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'0.0.0', max:'3.0.1'},
55+
{name:'motorOutputLow' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.1.0', max:'999.9.9'},
56+
{name:'motorOutputHigh' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.1.0', max:'999.9.9'},
57+
{name:'digitalIdleOffset' , type:FIRMWARE_TYPE_BETAFLIGHT, min:'3.1.0', max:'999.9.9'}
5558

5659
];
5760

@@ -460,6 +463,10 @@ function HeaderDialog(dialog, onSave) {
460463
setParameter('rateAccelLimit' ,sysConfig.rateAccelLimit,0);
461464
renderSelect('gyro_soft_type' ,sysConfig.gyro_soft_type, FILTER_TYPE);
462465
renderSelect('debug_mode' ,sysConfig.debug_mode, DEBUG_MODE);
466+
setParameter('motorOutputLow' ,sysConfig.motorOutput[0],0);
467+
setParameter('motorOutputHigh' ,sysConfig.motorOutput[1],0);
468+
setParameter('digitalIdleOffset' ,sysConfig.digitalIdleOffset,2);
469+
463470
/* Packed Flags */
464471

465472
builtFeaturesList(sysConfig);

0 commit comments

Comments
 (0)