1&&\"string\"==typeof v&&!d.checkClone&&De.test(v))return e.each((function(i){var o=e.eq(i);y&&(t[0]=v.call(this,i,o.html())),Re(o,t,n,r)}));if(p&&(a=(i=xe(t,e[0].ownerDocument,!1,e,r)).firstChild,1===i.childNodes.length&&(i=a),a||r)){for(u=(s=b.map(ve(i,\"script\"),Le)).length;f0&&ye(a,!u&&ve(e,\"script\")),s},cleanData:function(e){for(var t,n,r,i=b.event.special,o=0;void 0!==(n=e[o]);o++)if(X(n)){if(t=n[G.expando]){if(t.events)for(r in t.events)i[r]?b.event.remove(n,r):b.removeEvent(n,r,t.handle);n[G.expando]=void 0}n[Y.expando]&&(n[Y.expando]=void 0)}}}),b.fn.extend({detach:function(e){return Me(this,e,!0)},remove:function(e){return Me(this,e)},text:function(e){return B(this,(function(e){return void 0===e?b.text(this):this.empty().each((function(){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||(this.textContent=e)}))}),null,e,arguments.length)},append:function(){return Re(this,arguments,(function(e){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||qe(this,e).appendChild(e)}))},prepend:function(){return Re(this,arguments,(function(e){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var t=qe(this,e);t.insertBefore(e,t.firstChild)}}))},before:function(){return Re(this,arguments,(function(e){this.parentNode&&this.parentNode.insertBefore(e,this)}))},after:function(){return Re(this,arguments,(function(e){this.parentNode&&this.parentNode.insertBefore(e,this.nextSibling)}))},empty:function(){for(var e,t=0;null!=(e=this[t]);t++)1===e.nodeType&&(b.cleanData(ve(e,!1)),e.textContent=\"\");return this},clone:function(e,t){return e=null!=e&&e,t=null==t?e:t,this.map((function(){return b.clone(this,e,t)}))},html:function(e){return B(this,(function(e){var t=this[0]||{},n=0,r=this.length;if(void 0===e&&1===t.nodeType)return t.innerHTML;if(\"string\"==typeof e&&!Ne.test(e)&&!ge[(de.exec(e)||[\"\",\"\"])[1].toLowerCase()]){e=b.htmlPrefilter(e);try{for(;n3,ne.removeChild(t)),s}}))}();var ze=[\"Webkit\",\"Moz\",\"ms\"],Ue=v.createElement(\"div\").style,Xe={};function Ve(e){var t=b.cssProps[e]||Xe[e];return t||(e in Ue?e:Xe[e]=function(e){for(var t=e[0].toUpperCase()+e.slice(1),n=ze.length;n--;)if((e=ze[n]+t)in Ue)return e}(e)||e)}var Ge=/^(none|table(?!-c[ea]).+)/,Ye=/^--/,Qe={position:\"absolute\",visibility:\"hidden\",display:\"block\"},Je={letterSpacing:\"0\",fontWeight:\"400\"};function Ke(e,t,n){var r=ee.exec(t);return r?Math.max(0,r[2]-(n||0))+(r[3]||\"px\"):t}function Ze(e,t,n,r,i,o){var a=\"width\"===t?1:0,s=0,u=0;if(n===(r?\"border\":\"content\"))return 0;for(;a<4;a+=2)\"margin\"===n&&(u+=b.css(e,n+te[a],!0,i)),r?(\"content\"===n&&(u-=b.css(e,\"padding\"+te[a],!0,i)),\"margin\"!==n&&(u-=b.css(e,\"border\"+te[a]+\"Width\",!0,i))):(u+=b.css(e,\"padding\"+te[a],!0,i),\"padding\"!==n?u+=b.css(e,\"border\"+te[a]+\"Width\",!0,i):s+=b.css(e,\"border\"+te[a]+\"Width\",!0,i));return!r&&o>=0&&(u+=Math.max(0,Math.ceil(e[\"offset\"+t[0].toUpperCase()+t.slice(1)]-o-u-s-.5))||0),u}function et(e,t,n){var r=We(e),i=(!d.boxSizingReliable()||n)&&\"border-box\"===b.css(e,\"boxSizing\",!1,r),o=i,a=$e(e,t,r),s=\"offset\"+t[0].toUpperCase()+t.slice(1);if(Ie.test(a)){if(!n)return a;a=\"auto\"}return(!d.boxSizingReliable()&&i||!d.reliableTrDimensions()&&k(e,\"tr\")||\"auto\"===a||!parseFloat(a)&&\"inline\"===b.css(e,\"display\",!1,r))&&e.getClientRects().length&&(i=\"border-box\"===b.css(e,\"boxSizing\",!1,r),(o=s in e)&&(a=e[s])),(a=parseFloat(a)||0)+Ze(e,t,n||(i?\"border\":\"content\"),o,r,a)+\"px\"}function tt(e,t,n,r,i){return new tt.prototype.init(e,t,n,r,i)}b.extend({cssHooks:{opacity:{get:function(e,t){if(t){var n=$e(e,\"opacity\");return\"\"===n?\"1\":n}}}},cssNumber:{animationIterationCount:!0,columnCount:!0,fillOpacity:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,gridArea:!0,gridColumn:!0,gridColumnEnd:!0,gridColumnStart:!0,gridRow:!0,gridRowEnd:!0,gridRowStart:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{},style:function(e,t,n,r){if(e&&3!==e.nodeType&&8!==e.nodeType&&e.style){var i,o,a,s=U(t),u=Ye.test(t),l=e.style;if(u||(t=Ve(s)),a=b.cssHooks[t]||b.cssHooks[s],void 0===n)return a&&\"get\"in a&&void 0!==(i=a.get(e,!1,r))?i:l[t];\"string\"===(o=typeof n)&&(i=ee.exec(n))&&i[1]&&(n=ae(e,t,i),o=\"number\"),null!=n&&n==n&&(\"number\"!==o||u||(n+=i&&i[3]||(b.cssNumber[s]?\"\":\"px\")),d.clearCloneStyle||\"\"!==n||0!==t.indexOf(\"background\")||(l[t]=\"inherit\"),a&&\"set\"in a&&void 0===(n=a.set(e,n,r))||(u?l.setProperty(t,n):l[t]=n))}},css:function(e,t,n,r){var i,o,a,s=U(t);return Ye.test(t)||(t=Ve(s)),(a=b.cssHooks[t]||b.cssHooks[s])&&\"get\"in a&&(i=a.get(e,!0,n)),void 0===i&&(i=$e(e,t,r)),\"normal\"===i&&t in Je&&(i=Je[t]),\"\"===n||n?(o=parseFloat(i),!0===n||isFinite(o)?o||0:i):i}}),b.each([\"height\",\"width\"],(function(e,t){b.cssHooks[t]={get:function(e,n,r){if(n)return!Ge.test(b.css(e,\"display\"))||e.getClientRects().length&&e.getBoundingClientRect().width?et(e,t,r):Fe(e,Qe,(function(){return et(e,t,r)}))},set:function(e,n,r){var i,o=We(e),a=!d.scrollboxSize()&&\"absolute\"===o.position,s=(a||r)&&\"border-box\"===b.css(e,\"boxSizing\",!1,o),u=r?Ze(e,t,r,s,o):0;return s&&a&&(u-=Math.ceil(e[\"offset\"+t[0].toUpperCase()+t.slice(1)]-parseFloat(o[t])-Ze(e,t,\"border\",!1,o)-.5)),u&&(i=ee.exec(n))&&\"px\"!==(i[3]||\"px\")&&(e.style[t]=n,n=b.css(e,t)),Ke(0,n,u)}}})),b.cssHooks.marginLeft=_e(d.reliableMarginLeft,(function(e,t){if(t)return(parseFloat($e(e,\"marginLeft\"))||e.getBoundingClientRect().left-Fe(e,{marginLeft:0},(function(){return e.getBoundingClientRect().left})))+\"px\"})),b.each({margin:\"\",padding:\"\",border:\"Width\"},(function(e,t){b.cssHooks[e+t]={expand:function(n){for(var r=0,i={},o=\"string\"==typeof n?n.split(\" \"):[n];r<4;r++)i[e+te[r]+t]=o[r]||o[r-2]||o[0];return i}},\"margin\"!==e&&(b.cssHooks[e+t].set=Ke)})),b.fn.extend({css:function(e,t){return B(this,(function(e,t,n){var r,i,o={},a=0;if(Array.isArray(t)){for(r=We(e),i=t.length;a1)}}),b.Tween=tt,tt.prototype={constructor:tt,init:function(e,t,n,r,i,o){this.elem=e,this.prop=n,this.easing=i||b.easing._default,this.options=t,this.start=this.now=this.cur(),this.end=r,this.unit=o||(b.cssNumber[n]?\"\":\"px\")},cur:function(){var e=tt.propHooks[this.prop];return e&&e.get?e.get(this):tt.propHooks._default.get(this)},run:function(e){var t,n=tt.propHooks[this.prop];return this.options.duration?this.pos=t=b.easing[this.easing](e,this.options.duration*e,0,1,this.options.duration):this.pos=t=e,this.now=(this.end-this.start)*t+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),n&&n.set?n.set(this):tt.propHooks._default.set(this),this}},tt.prototype.init.prototype=tt.prototype,tt.propHooks={_default:{get:function(e){var t;return 1!==e.elem.nodeType||null!=e.elem[e.prop]&&null==e.elem.style[e.prop]?e.elem[e.prop]:(t=b.css(e.elem,e.prop,\"\"))&&\"auto\"!==t?t:0},set:function(e){b.fx.step[e.prop]?b.fx.step[e.prop](e):1!==e.elem.nodeType||!b.cssHooks[e.prop]&&null==e.elem.style[Ve(e.prop)]?e.elem[e.prop]=e.now:b.style(e.elem,e.prop,e.now+e.unit)}}},tt.propHooks.scrollTop=tt.propHooks.scrollLeft={set:function(e){e.elem.nodeType&&e.elem.parentNode&&(e.elem[e.prop]=e.now)}},b.easing={linear:function(e){return e},swing:function(e){return.5-Math.cos(e*Math.PI)/2},_default:\"swing\"},b.fx=tt.prototype.init,b.fx.step={};var nt,rt,it=/^(?:toggle|show|hide)$/,ot=/queueHooks$/;function at(){rt&&(!1===v.hidden&&e.requestAnimationFrame?e.requestAnimationFrame(at):e.setTimeout(at,b.fx.interval),b.fx.tick())}function st(){return e.setTimeout((function(){nt=void 0})),nt=Date.now()}function ut(e,t){var n,r=0,i={height:e};for(t=t?1:0;r<4;r+=2-t)i[\"margin\"+(n=te[r])]=i[\"padding\"+n]=e;return t&&(i.opacity=i.width=e),i}function lt(e,t,n){for(var r,i=(ct.tweeners[t]||[]).concat(ct.tweeners[\"*\"]),o=0,a=i.length;o1)},removeAttr:function(e){return this.each((function(){b.removeAttr(this,e)}))}}),b.extend({attr:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return void 0===e.getAttribute?b.prop(e,t,n):(1===o&&b.isXMLDoc(e)||(i=b.attrHooks[t.toLowerCase()]||(b.expr.match.bool.test(t)?ft:void 0)),void 0!==n?null===n?void b.removeAttr(e,t):i&&\"set\"in i&&void 0!==(r=i.set(e,n,t))?r:(e.setAttribute(t,n+\"\"),n):i&&\"get\"in i&&null!==(r=i.get(e,t))?r:null==(r=b.find.attr(e,t))?void 0:r)},attrHooks:{type:{set:function(e,t){if(!d.radioValue&&\"radio\"===t&&k(e,\"input\")){var n=e.value;return e.setAttribute(\"type\",t),n&&(e.value=n),t}}}},removeAttr:function(e,t){var n,r=0,i=t&&t.match(O);if(i&&1===e.nodeType)for(;n=i[r++];)e.removeAttribute(n)}}),ft={set:function(e,t,n){return!1===t?b.removeAttr(e,n):e.setAttribute(n,n),n}},b.each(b.expr.match.bool.source.match(/\\w+/g),(function(e,t){var n=pt[t]||b.find.attr;pt[t]=function(e,t,r){var i,o,a=t.toLowerCase();return r||(o=pt[a],pt[a]=i,i=null!=n(e,t,r)?a:null,pt[a]=o),i}}));var dt=/^(?:input|select|textarea|button)$/i,ht=/^(?:a|area)$/i;function gt(e){return(e.match(O)||[]).join(\" \")}function vt(e){return e.getAttribute&&e.getAttribute(\"class\")||\"\"}function yt(e){return Array.isArray(e)?e:\"string\"==typeof e&&e.match(O)||[]}b.fn.extend({prop:function(e,t){return B(this,b.prop,e,t,arguments.length>1)},removeProp:function(e){return this.each((function(){delete this[b.propFix[e]||e]}))}}),b.extend({prop:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return 1===o&&b.isXMLDoc(e)||(t=b.propFix[t]||t,i=b.propHooks[t]),void 0!==n?i&&\"set\"in i&&void 0!==(r=i.set(e,n,t))?r:e[t]=n:i&&\"get\"in i&&null!==(r=i.get(e,t))?r:e[t]},propHooks:{tabIndex:{get:function(e){var t=b.find.attr(e,\"tabindex\");return t?parseInt(t,10):dt.test(e.nodeName)||ht.test(e.nodeName)&&e.href?0:-1}}},propFix:{for:\"htmlFor\",class:\"className\"}}),d.optSelected||(b.propHooks.selected={get:function(e){var t=e.parentNode;return t&&t.parentNode&&t.parentNode.selectedIndex,null},set:function(e){var t=e.parentNode;t&&(t.selectedIndex,t.parentNode&&t.parentNode.selectedIndex)}}),b.each([\"tabIndex\",\"readOnly\",\"maxLength\",\"cellSpacing\",\"cellPadding\",\"rowSpan\",\"colSpan\",\"useMap\",\"frameBorder\",\"contentEditable\"],(function(){b.propFix[this.toLowerCase()]=this})),b.fn.extend({addClass:function(e){var t,n,r,i,o,a,s,u=0;if(h(e))return this.each((function(t){b(this).addClass(e.call(this,t,vt(this)))}));if((t=yt(e)).length)for(;n=this[u++];)if(i=vt(n),r=1===n.nodeType&&\" \"+gt(i)+\" \"){for(a=0;o=t[a++];)r.indexOf(\" \"+o+\" \")<0&&(r+=o+\" \");i!==(s=gt(r))&&n.setAttribute(\"class\",s)}return this},removeClass:function(e){var t,n,r,i,o,a,s,u=0;if(h(e))return this.each((function(t){b(this).removeClass(e.call(this,t,vt(this)))}));if(!arguments.length)return this.attr(\"class\",\"\");if((t=yt(e)).length)for(;n=this[u++];)if(i=vt(n),r=1===n.nodeType&&\" \"+gt(i)+\" \"){for(a=0;o=t[a++];)for(;r.indexOf(\" \"+o+\" \")>-1;)r=r.replace(\" \"+o+\" \",\" \");i!==(s=gt(r))&&n.setAttribute(\"class\",s)}return this},toggleClass:function(e,t){var n=typeof e,r=\"string\"===n||Array.isArray(e);return\"boolean\"==typeof t&&r?t?this.addClass(e):this.removeClass(e):h(e)?this.each((function(n){b(this).toggleClass(e.call(this,n,vt(this),t),t)})):this.each((function(){var t,i,o,a;if(r)for(i=0,o=b(this),a=yt(e);t=a[i++];)o.hasClass(t)?o.removeClass(t):o.addClass(t);else void 0!==e&&\"boolean\"!==n||((t=vt(this))&&G.set(this,\"__className__\",t),this.setAttribute&&this.setAttribute(\"class\",t||!1===e?\"\":G.get(this,\"__className__\")||\"\"))}))},hasClass:function(e){var t,n,r=0;for(t=\" \"+e+\" \";n=this[r++];)if(1===n.nodeType&&(\" \"+gt(vt(n))+\" \").indexOf(t)>-1)return!0;return!1}});var mt=/\\r/g;b.fn.extend({val:function(e){var t,n,r,i=this[0];return arguments.length?(r=h(e),this.each((function(n){var i;1===this.nodeType&&(null==(i=r?e.call(this,n,b(this).val()):e)?i=\"\":\"number\"==typeof i?i+=\"\":Array.isArray(i)&&(i=b.map(i,(function(e){return null==e?\"\":e+\"\"}))),(t=b.valHooks[this.type]||b.valHooks[this.nodeName.toLowerCase()])&&\"set\"in t&&void 0!==t.set(this,i,\"value\")||(this.value=i))}))):i?(t=b.valHooks[i.type]||b.valHooks[i.nodeName.toLowerCase()])&&\"get\"in t&&void 0!==(n=t.get(i,\"value\"))?n:\"string\"==typeof(n=i.value)?n.replace(mt,\"\"):null==n?\"\":n:void 0}}),b.extend({valHooks:{option:{get:function(e){var t=b.find.attr(e,\"value\");return null!=t?t:gt(b.text(e))}},select:{get:function(e){var t,n,r,i=e.options,o=e.selectedIndex,a=\"select-one\"===e.type,s=a?null:[],u=a?o+1:i.length;for(r=o<0?u:a?o:0;r-1)&&(n=!0);return n||(e.selectedIndex=-1),o}}}}),b.each([\"radio\",\"checkbox\"],(function(){b.valHooks[this]={set:function(e,t){if(Array.isArray(t))return e.checked=b.inArray(b(e).val(),t)>-1}},d.checkOn||(b.valHooks[this].get=function(e){return null===e.getAttribute(\"value\")?\"on\":e.value})})),d.focusin=\"onfocusin\"in e;var xt=/^(?:focusinfocus|focusoutblur)$/,bt=function(e){e.stopPropagation()};b.extend(b.event,{trigger:function(t,n,r,i){var o,a,s,u,l,f,p,d,y=[r||v],m=c.call(t,\"type\")?t.type:t,x=c.call(t,\"namespace\")?t.namespace.split(\".\"):[];if(a=d=s=r=r||v,3!==r.nodeType&&8!==r.nodeType&&!xt.test(m+b.event.triggered)&&(m.indexOf(\".\")>-1&&(x=m.split(\".\"),m=x.shift(),x.sort()),l=m.indexOf(\":\")<0&&\"on\"+m,(t=t[b.expando]?t:new b.Event(m,\"object\"==typeof t&&t)).isTrigger=i?2:3,t.namespace=x.join(\".\"),t.rnamespace=t.namespace?new RegExp(\"(^|\\\\.)\"+x.join(\"\\\\.(?:.*\\\\.|)\")+\"(\\\\.|$)\"):null,t.result=void 0,t.target||(t.target=r),n=null==n?[t]:b.makeArray(n,[t]),p=b.event.special[m]||{},i||!p.trigger||!1!==p.trigger.apply(r,n))){if(!i&&!p.noBubble&&!g(r)){for(u=p.delegateType||m,xt.test(u+m)||(a=a.parentNode);a;a=a.parentNode)y.push(a),s=a;s===(r.ownerDocument||v)&&y.push(s.defaultView||s.parentWindow||e)}for(o=0;(a=y[o++])&&!t.isPropagationStopped();)d=a,t.type=o>1?u:p.bindType||m,(f=(G.get(a,\"events\")||Object.create(null))[t.type]&&G.get(a,\"handle\"))&&f.apply(a,n),(f=l&&a[l])&&f.apply&&X(a)&&(t.result=f.apply(a,n),!1===t.result&&t.preventDefault());return t.type=m,i||t.isDefaultPrevented()||p._default&&!1!==p._default.apply(y.pop(),n)||!X(r)||l&&h(r[m])&&!g(r)&&((s=r[l])&&(r[l]=null),b.event.triggered=m,t.isPropagationStopped()&&d.addEventListener(m,bt),r[m](),t.isPropagationStopped()&&d.removeEventListener(m,bt),b.event.triggered=void 0,s&&(r[l]=s)),t.result}},simulate:function(e,t,n){var r=b.extend(new b.Event,n,{type:e,isSimulated:!0});b.event.trigger(r,null,t)}}),b.fn.extend({trigger:function(e,t){return this.each((function(){b.event.trigger(e,t,this)}))},triggerHandler:function(e,t){var n=this[0];if(n)return b.event.trigger(e,t,n,!0)}}),d.focusin||b.each({focus:\"focusin\",blur:\"focusout\"},(function(e,t){var n=function(e){b.event.simulate(t,e.target,b.event.fix(e))};b.event.special[t]={setup:function(){var r=this.ownerDocument||this.document||this,i=G.access(r,t);i||r.addEventListener(e,n,!0),G.access(r,t,(i||0)+1)},teardown:function(){var r=this.ownerDocument||this.document||this,i=G.access(r,t)-1;i?G.access(r,t,i):(r.removeEventListener(e,n,!0),G.remove(r,t))}}}));var wt=e.location,Tt={guid:Date.now()},Ct=/\\?/;b.parseXML=function(t){var n;if(!t||\"string\"!=typeof t)return null;try{n=(new e.DOMParser).parseFromString(t,\"text/xml\")}catch(e){n=void 0}return n&&!n.getElementsByTagName(\"parsererror\").length||b.error(\"Invalid XML: \"+t),n};var Et=/\\[\\]$/,St=/\\r?\\n/g,kt=/^(?:submit|button|image|reset|file)$/i,At=/^(?:input|select|textarea|keygen)/i;function Nt(e,t,n,r){var i;if(Array.isArray(t))b.each(t,(function(t,i){n||Et.test(e)?r(e,i):Nt(e+\"[\"+(\"object\"==typeof i&&null!=i?t:\"\")+\"]\",i,n,r)}));else if(n||\"object\"!==x(t))r(e,t);else for(i in t)Nt(e+\"[\"+i+\"]\",t[i],n,r)}b.param=function(e,t){var n,r=[],i=function(e,t){var n=h(t)?t():t;r[r.length]=encodeURIComponent(e)+\"=\"+encodeURIComponent(null==n?\"\":n)};if(null==e)return\"\";if(Array.isArray(e)||e.jquery&&!b.isPlainObject(e))b.each(e,(function(){i(this.name,this.value)}));else for(n in e)Nt(n,e[n],t,i);return r.join(\"&\")},b.fn.extend({serialize:function(){return b.param(this.serializeArray())},serializeArray:function(){return this.map((function(){var e=b.prop(this,\"elements\");return e?b.makeArray(e):this})).filter((function(){var e=this.type;return this.name&&!b(this).is(\":disabled\")&&At.test(this.nodeName)&&!kt.test(e)&&(this.checked||!pe.test(e))})).map((function(e,t){var n=b(this).val();return null==n?null:Array.isArray(n)?b.map(n,(function(e){return{name:t.name,value:e.replace(St,\"\\r\\n\")}})):{name:t.name,value:n.replace(St,\"\\r\\n\")}})).get()}});var Dt=/%20/g,jt=/#.*$/,qt=/([?&])_=[^&]*/,Lt=/^(.*?):[ \\t]*([^\\r\\n]*)$/gm,Ht=/^(?:GET|HEAD)$/,Ot=/^\\/\\//,Pt={},Rt={},Mt=\"*/\".concat(\"*\"),It=v.createElement(\"a\");function Wt(e){return function(t,n){\"string\"!=typeof t&&(n=t,t=\"*\");var r,i=0,o=t.toLowerCase().match(O)||[];if(h(n))for(;r=o[i++];)\"+\"===r[0]?(r=r.slice(1)||\"*\",(e[r]=e[r]||[]).unshift(n)):(e[r]=e[r]||[]).push(n)}}function Ft(e,t,n,r){var i={},o=e===Rt;function a(s){var u;return i[s]=!0,b.each(e[s]||[],(function(e,s){var l=s(t,n,r);return\"string\"!=typeof l||o||i[l]?o?!(u=l):void 0:(t.dataTypes.unshift(l),a(l),!1)})),u}return a(t.dataTypes[0])||!i[\"*\"]&&a(\"*\")}function Bt(e,t){var n,r,i=b.ajaxSettings.flatOptions||{};for(n in t)void 0!==t[n]&&((i[n]?e:r||(r={}))[n]=t[n]);return r&&b.extend(!0,e,r),e}It.href=wt.href,b.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:wt.href,type:\"GET\",isLocal:/^(?:about|app|app-storage|.+-extension|file|res|widget):$/.test(wt.protocol),global:!0,processData:!0,async:!0,contentType:\"application/x-www-form-urlencoded; charset=UTF-8\",accepts:{\"*\":Mt,text:\"text/plain\",html:\"text/html\",xml:\"application/xml, text/xml\",json:\"application/json, text/javascript\"},contents:{xml:/\\bxml\\b/,html:/\\bhtml/,json:/\\bjson\\b/},responseFields:{xml:\"responseXML\",text:\"responseText\",json:\"responseJSON\"},converters:{\"* text\":String,\"text html\":!0,\"text json\":JSON.parse,\"text xml\":b.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(e,t){return t?Bt(Bt(e,b.ajaxSettings),t):Bt(b.ajaxSettings,e)},ajaxPrefilter:Wt(Pt),ajaxTransport:Wt(Rt),ajax:function(t,n){\"object\"==typeof t&&(n=t,t=void 0),n=n||{};var r,i,o,a,s,u,l,c,f,p,d=b.ajaxSetup({},n),h=d.context||d,g=d.context&&(h.nodeType||h.jquery)?b(h):b.event,y=b.Deferred(),m=b.Callbacks(\"once memory\"),x=d.statusCode||{},w={},T={},C=\"canceled\",E={readyState:0,getResponseHeader:function(e){var t;if(l){if(!a)for(a={};t=Lt.exec(o);)a[t[1].toLowerCase()+\" \"]=(a[t[1].toLowerCase()+\" \"]||[]).concat(t[2]);t=a[e.toLowerCase()+\" \"]}return null==t?null:t.join(\", \")},getAllResponseHeaders:function(){return l?o:null},setRequestHeader:function(e,t){return null==l&&(e=T[e.toLowerCase()]=T[e.toLowerCase()]||e,w[e]=t),this},overrideMimeType:function(e){return null==l&&(d.mimeType=e),this},statusCode:function(e){var t;if(e)if(l)E.always(e[E.status]);else for(t in e)x[t]=[x[t],e[t]];return this},abort:function(e){var t=e||C;return r&&r.abort(t),S(0,t),this}};if(y.promise(E),d.url=((t||d.url||wt.href)+\"\").replace(Ot,wt.protocol+\"//\"),d.type=n.method||n.type||d.method||d.type,d.dataTypes=(d.dataType||\"*\").toLowerCase().match(O)||[\"\"],null==d.crossDomain){u=v.createElement(\"a\");try{u.href=d.url,u.href=u.href,d.crossDomain=It.protocol+\"//\"+It.host!=u.protocol+\"//\"+u.host}catch(e){d.crossDomain=!0}}if(d.data&&d.processData&&\"string\"!=typeof d.data&&(d.data=b.param(d.data,d.traditional)),Ft(Pt,d,n,E),l)return E;for(f in(c=b.event&&d.global)&&0==b.active++&&b.event.trigger(\"ajaxStart\"),d.type=d.type.toUpperCase(),d.hasContent=!Ht.test(d.type),i=d.url.replace(jt,\"\"),d.hasContent?d.data&&d.processData&&0===(d.contentType||\"\").indexOf(\"application/x-www-form-urlencoded\")&&(d.data=d.data.replace(Dt,\"+\")):(p=d.url.slice(i.length),d.data&&(d.processData||\"string\"==typeof d.data)&&(i+=(Ct.test(i)?\"&\":\"?\")+d.data,delete d.data),!1===d.cache&&(i=i.replace(qt,\"$1\"),p=(Ct.test(i)?\"&\":\"?\")+\"_=\"+Tt.guid+++p),d.url=i+p),d.ifModified&&(b.lastModified[i]&&E.setRequestHeader(\"If-Modified-Since\",b.lastModified[i]),b.etag[i]&&E.setRequestHeader(\"If-None-Match\",b.etag[i])),(d.data&&d.hasContent&&!1!==d.contentType||n.contentType)&&E.setRequestHeader(\"Content-Type\",d.contentType),E.setRequestHeader(\"Accept\",d.dataTypes[0]&&d.accepts[d.dataTypes[0]]?d.accepts[d.dataTypes[0]]+(\"*\"!==d.dataTypes[0]?\", \"+Mt+\"; q=0.01\":\"\"):d.accepts[\"*\"]),d.headers)E.setRequestHeader(f,d.headers[f]);if(d.beforeSend&&(!1===d.beforeSend.call(h,E,d)||l))return E.abort();if(C=\"abort\",m.add(d.complete),E.done(d.success),E.fail(d.error),r=Ft(Rt,d,n,E)){if(E.readyState=1,c&&g.trigger(\"ajaxSend\",[E,d]),l)return E;d.async&&d.timeout>0&&(s=e.setTimeout((function(){E.abort(\"timeout\")}),d.timeout));try{l=!1,r.send(w,S)}catch(e){if(l)throw e;S(-1,e)}}else S(-1,\"No Transport\");function S(t,n,a,u){var f,p,v,w,T,C=n;l||(l=!0,s&&e.clearTimeout(s),r=void 0,o=u||\"\",E.readyState=t>0?4:0,f=t>=200&&t<300||304===t,a&&(w=function(e,t,n){for(var r,i,o,a,s=e.contents,u=e.dataTypes;\"*\"===u[0];)u.shift(),void 0===r&&(r=e.mimeType||t.getResponseHeader(\"Content-Type\"));if(r)for(i in s)if(s[i]&&s[i].test(r)){u.unshift(i);break}if(u[0]in n)o=u[0];else{for(i in n){if(!u[0]||e.converters[i+\" \"+u[0]]){o=i;break}a||(a=i)}o=o||a}if(o)return o!==u[0]&&u.unshift(o),n[o]}(d,E,a)),!f&&b.inArray(\"script\",d.dataTypes)>-1&&(d.converters[\"text script\"]=function(){}),w=function(e,t,n,r){var i,o,a,s,u,l={},c=e.dataTypes.slice();if(c[1])for(a in e.converters)l[a.toLowerCase()]=e.converters[a];for(o=c.shift();o;)if(e.responseFields[o]&&(n[e.responseFields[o]]=t),!u&&r&&e.dataFilter&&(t=e.dataFilter(t,e.dataType)),u=o,o=c.shift())if(\"*\"===o)o=u;else if(\"*\"!==u&&u!==o){if(!(a=l[u+\" \"+o]||l[\"* \"+o]))for(i in l)if((s=i.split(\" \"))[1]===o&&(a=l[u+\" \"+s[0]]||l[\"* \"+s[0]])){!0===a?a=l[i]:!0!==l[i]&&(o=s[0],c.unshift(s[1]));break}if(!0!==a)if(a&&e.throws)t=a(t);else try{t=a(t)}catch(e){return{state:\"parsererror\",error:a?e:\"No conversion from \"+u+\" to \"+o}}}return{state:\"success\",data:t}}(d,w,E,f),f?(d.ifModified&&((T=E.getResponseHeader(\"Last-Modified\"))&&(b.lastModified[i]=T),(T=E.getResponseHeader(\"etag\"))&&(b.etag[i]=T)),204===t||\"HEAD\"===d.type?C=\"nocontent\":304===t?C=\"notmodified\":(C=w.state,p=w.data,f=!(v=w.error))):(v=C,!t&&C||(C=\"error\",t<0&&(t=0))),E.status=t,E.statusText=(n||C)+\"\",f?y.resolveWith(h,[p,C,E]):y.rejectWith(h,[E,C,v]),E.statusCode(x),x=void 0,c&&g.trigger(f?\"ajaxSuccess\":\"ajaxError\",[E,d,f?p:v]),m.fireWith(h,[E,C]),c&&(g.trigger(\"ajaxComplete\",[E,d]),--b.active||b.event.trigger(\"ajaxStop\")))}return E},getJSON:function(e,t,n){return b.get(e,t,n,\"json\")},getScript:function(e,t){return b.get(e,void 0,t,\"script\")}}),b.each([\"get\",\"post\"],(function(e,t){b[t]=function(e,n,r,i){return h(n)&&(i=i||r,r=n,n=void 0),b.ajax(b.extend({url:e,type:t,dataType:i,data:n,success:r},b.isPlainObject(e)&&e))}})),b.ajaxPrefilter((function(e){var t;for(t in e.headers)\"content-type\"===t.toLowerCase()&&(e.contentType=e.headers[t]||\"\")})),b._evalUrl=function(e,t,n){return b.ajax({url:e,type:\"GET\",dataType:\"script\",cache:!0,async:!1,global:!1,converters:{\"text script\":function(){}},dataFilter:function(e){b.globalEval(e,t,n)}})},b.fn.extend({wrapAll:function(e){var t;return this[0]&&(h(e)&&(e=e.call(this[0])),t=b(e,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&t.insertBefore(this[0]),t.map((function(){for(var e=this;e.firstElementChild;)e=e.firstElementChild;return e})).append(this)),this},wrapInner:function(e){return h(e)?this.each((function(t){b(this).wrapInner(e.call(this,t))})):this.each((function(){var t=b(this),n=t.contents();n.length?n.wrapAll(e):t.append(e)}))},wrap:function(e){var t=h(e);return this.each((function(n){b(this).wrapAll(t?e.call(this,n):e)}))},unwrap:function(e){return this.parent(e).not(\"body\").each((function(){b(this).replaceWith(this.childNodes)})),this}}),b.expr.pseudos.hidden=function(e){return!b.expr.pseudos.visible(e)},b.expr.pseudos.visible=function(e){return!!(e.offsetWidth||e.offsetHeight||e.getClientRects().length)},b.ajaxSettings.xhr=function(){try{return new e.XMLHttpRequest}catch(e){}};var $t={0:200,1223:204},_t=b.ajaxSettings.xhr();d.cors=!!_t&&\"withCredentials\"in _t,d.ajax=_t=!!_t,b.ajaxTransport((function(t){var n,r;if(d.cors||_t&&!t.crossDomain)return{send:function(i,o){var a,s=t.xhr();if(s.open(t.type,t.url,t.async,t.username,t.password),t.xhrFields)for(a in t.xhrFields)s[a]=t.xhrFields[a];for(a in t.mimeType&&s.overrideMimeType&&s.overrideMimeType(t.mimeType),t.crossDomain||i[\"X-Requested-With\"]||(i[\"X-Requested-With\"]=\"XMLHttpRequest\"),i)s.setRequestHeader(a,i[a]);n=function(e){return function(){n&&(n=r=s.onload=s.onerror=s.onabort=s.ontimeout=s.onreadystatechange=null,\"abort\"===e?s.abort():\"error\"===e?\"number\"!=typeof s.status?o(0,\"error\"):o(s.status,s.statusText):o($t[s.status]||s.status,s.statusText,\"text\"!==(s.responseType||\"text\")||\"string\"!=typeof s.responseText?{binary:s.response}:{text:s.responseText},s.getAllResponseHeaders()))}},s.onload=n(),r=s.onerror=s.ontimeout=n(\"error\"),void 0!==s.onabort?s.onabort=r:s.onreadystatechange=function(){4===s.readyState&&e.setTimeout((function(){n&&r()}))},n=n(\"abort\");try{s.send(t.hasContent&&t.data||null)}catch(e){if(n)throw e}},abort:function(){n&&n()}}})),b.ajaxPrefilter((function(e){e.crossDomain&&(e.contents.script=!1)})),b.ajaxSetup({accepts:{script:\"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript\"},contents:{script:/\\b(?:java|ecma)script\\b/},converters:{\"text script\":function(e){return b.globalEval(e),e}}}),b.ajaxPrefilter(\"script\",(function(e){void 0===e.cache&&(e.cache=!1),e.crossDomain&&(e.type=\"GET\")})),b.ajaxTransport(\"script\",(function(e){var t,n;if(e.crossDomain||e.scriptAttrs)return{send:function(r,i){t=b(\""
],
"text/plain": [
"Row\n",
" [0] Column\n",
" [0] Toggle(button_type='success', name='ACQUIRE', width=100)\n",
" [1] Button(button_type='danger', name='STOP', width=100)\n",
" [1] Spacer(width=15)\n",
" [2] Column\n",
" [0] StaticText(name='Data points received', value='0')\n",
" [1] StaticText(name='Status', value='Awaiting data a...)"
]
},
"execution_count": 16,
"metadata": {
"application/vnd.holoviews_exec.v0+json": {
"id": "1101"
}
},
"output_type": "execute_result"
}
],
"source": [
"arduino = open_arduino(port)\n",
"\n",
"pn.Row(\n",
" pn.Column(acquire_toggle, stop_button),\n",
" pn.Spacer(width=15),\n",
" pn.Column(received_text, status_text),\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"After hitting \"ACQUIRE\", turning the potentiometer knob a few times, and then hitting \"STOP\", I got my data. Let's take a look."
]
},
{
"cell_type": "code",
"execution_count": 17,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"d92ace25-ec47-4b1d-a527-97f459bf2cf2\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"1638\"}],\"center\":[{\"id\":\"1641\"},{\"id\":\"1645\"}],\"frame_height\":175,\"frame_width\":500,\"left\":[{\"id\":\"1642\"}],\"renderers\":[{\"id\":\"1663\"}],\"title\":{\"id\":\"1674\"},\"toolbar\":{\"id\":\"1653\"},\"x_range\":{\"id\":\"1630\"},\"x_scale\":{\"id\":\"1634\"},\"y_range\":{\"id\":\"1632\"},\"y_scale\":{\"id\":\"1636\"}},\"id\":\"1629\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"1661\",\"type\":\"Line\"},{\"attributes\":{},\"id\":\"1647\",\"type\":\"WheelZoomTool\"},{\"attributes\":{\"overlay\":{\"id\":\"1652\"}},\"id\":\"1648\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"1649\",\"type\":\"SaveTool\"},{\"attributes\":{},\"id\":\"1650\",\"type\":\"ResetTool\"},{\"attributes\":{},\"id\":\"1636\",\"type\":\"LinearScale\"},{\"attributes\":{},\"id\":\"1651\",\"type\":\"HelpTool\"},{\"attributes\":{\"axis_label\":\"time (s)\",\"formatter\":{\"id\":\"1676\"},\"ticker\":{\"id\":\"1639\"}},\"id\":\"1638\",\"type\":\"LinearAxis\"},{\"attributes\":{\"axis\":{\"id\":\"1642\"},\"dimension\":1,\"ticker\":null},\"id\":\"1645\",\"type\":\"Grid\"},{\"attributes\":{\"data_source\":{\"id\":\"1660\"},\"glyph\":{\"id\":\"1661\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"1662\"},\"selection_glyph\":null,\"view\":{\"id\":\"1664\"}},\"id\":\"1663\",\"type\":\"GlyphRenderer\"},{\"attributes\":{},\"id\":\"1639\",\"type\":\"BasicTicker\"},{\"attributes\":{\"text\":\"\"},\"id\":\"1674\",\"type\":\"Title\"},{\"attributes\":{},\"id\":\"1676\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"line_alpha\":0.1,\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"1662\",\"type\":\"Line\"},{\"attributes\":{},\"id\":\"1643\",\"type\":\"BasicTicker\"},{\"attributes\":{},\"id\":\"1681\",\"type\":\"Selection\"},{\"attributes\":{\"axis\":{\"id\":\"1638\"},\"ticker\":null},\"id\":\"1641\",\"type\":\"Grid\"},{\"attributes\":{\"axis_label\":\"voltage (V)\",\"formatter\":{\"id\":\"1678\"},\"ticker\":{\"id\":\"1643\"}},\"id\":\"1642\",\"type\":\"LinearAxis\"},{\"attributes\":{\"range_padding\":0},\"id\":\"1630\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"1678\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"1682\",\"type\":\"UnionRenderers\"},{\"attributes\":{\"source\":{\"id\":\"1660\"}},\"id\":\"1664\",\"type\":\"CDSView\"},{\"attributes\":{},\"id\":\"1632\",\"type\":\"DataRange1d\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"1652\",\"type\":\"BoxAnnotation\"},{\"attributes\":{},\"id\":\"1634\",\"type\":\"LinearScale\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"1646\"},{\"id\":\"1647\"},{\"id\":\"1648\"},{\"id\":\"1649\"},{\"id\":\"1650\"},{\"id\":\"1651\"}]},\"id\":\"1653\",\"type\":\"Toolbar\"},{\"attributes\":{\"data\":{\"x\":{\"__ndarray__\":\"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\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[513]},\"y\":{\"__ndarray__\":\"DC+88MIL/z/43nvvvff+P/jee++99/4/+N577733/j/43nvvvff+PwwvvPDCC/8/+N577733/j/43nvvvff+PwwvvPDCC/8/+N577733/j8ML7zwwgv/P/jee++99/4/DC+88MIL/z/43nvvvff+P/jee++99/4/DC+88MIL/z8ML7zwwgv/PwwvvPDCC/8/DC+88MIL/z8ML7zwwgv/P/jee++99/4/+N577733/j8ML7zwwgv/PwwvvPDCC/8/DC+88MIL/z/43nvvvff+P/jee++99/4/DC+88MIL/z9IH3300Uf/P2ywwQYbbABA5JBDDjnkAEAWWWSRRRYBQCmppJJKKgFA88knn3zyAUCrq6666qoDQEYVVVRRRQVAHG+88cYbB0B111133XUHQHXXXXfddQdAa6+99tprB0BEDz300EMHQOqmm2666QZAN9ZYY401BkDDDDPMMMMEQAsrrLDCCgNAl2GGGWaYAUDaaKONNtoAQIEAAggggABAgQACCCCAAECBAAIIIIAAQIEAAggggABAgQACCCCAAECBAAIIIIAAQIoooogiigBArLHGGmusAUA33HDDDTcEQOqmm2666QZAvO++++67B0DaZ5999tkHQNpnn3322QdAxhdffPHFB0CKJ5544okHQGuvvfbaawdARA899NBDB0DWVltttdUGQPnll19++QVAMsUUU0wxBUDDDDPMMMMEQK+88sorrwRApZRSSimlBECllFJKKaUEQKWUUkoppQRApZRSSimlBECllFJKKaUEQK+88sorrwRARhVVVFFFBUD433///fcHQJprrrnmmgtAFlxwwQUXEEAmlVRSSSURQGCFFVZYYRFAXHHFFVdcEUBXXXXVVVcRQEghhRRSSBFAKamkkkoqEUDWVFNNNdUQQBZccMEFFxBAba655pprDkAEDTTQQAMNQJprrrnmmgtAjTLKKKOMCkDssccee+wJQEMJJZRQQglAtdhiiy22CEA00EADDTQIQNE///zzzwdAnnfeeeedB0Ced955550HQJ533nnnnQdA+N9///33B0DooIMOOugIQGWSSSaZZApAE0wwwQQTDEAEDTTQQAMNQCGFFFJIIQ1AIYUUUkghDUAhhRRSSCENQPvkk08++QxA22yzzTbbDECffPLJJ58MQOyrr7766gtAzTPPPPPMC0DNM88888wLQAckkEACCQxA0UQTTTTRDEAnllhiiSUOQCyssMIKKxBAu/DCCy+8EEDMLLPMMssQQMwss8wyyxBAzCyzzDLLEEDMLLPMMssQQMwss8wyyxBAxhhjjDHGEECttNJKK60QQIEAAggggBBApI022mijDUDJIossssgKQNE///zzzwdAWGWVVVZZBUDyww8//PADQKeaaqqppgJAl2GGGWaYAUCKKKKIIooAQAwvvPDCC/8/FEwwwQQT/D9++eWXX375Pz744IMPPvg/Kqigggoq+D8++OCDDz74P3rooYceevg/zjnnnHPO+T8bbrjhhhv+P7HCCiussAJA/fbbb7/9BkBbaqmllloKQFlkkUUWWQxA0UQTTTTRDEA11VRTTTUNQHHFFVdccQ1Ajz322GOPDUCPPfbYY48NQJpllllmmQ1Ajz322GOPDUCPPfbYY48NQI899thjjw1AhRVWWGGFDUBpnXXWWWcNQCuttNJKKw1Adtxxxx13DEB54oknnngKQIUQQgghhAhAfO655557BkCHHHLIIYcEQFZaaaWVVgJAiiiiiCKKAEC43Xbbbbf9P++888477/w/BA000EAD/T8WXXTRRRf9P/LNN9988/0/L7rooosuAkAdddRRRx0FQI444ogjjghAtdJKK620CkB0yy233HILQJFDDjnkkAtAmmuuueaaC0Clk0466aQLQKWTTjrppAtAr7vuuuuuC0DDCy+88MILQP/777///gtAJ5xwwgknDEBZZJFFFlkMQIwsssgiiwxA8LzzzjvvDEBpnXXWWWcNQBtuuOGGGw5AvO666667DkBIH3300UcPQOmff/755w9AOuiggw46EEB22GGHHXYQQNpoo4022hBAL7300ksvEUCiiSaaaKIRQCqmmGKKKRJAp5pqqqmmEkBRQw011FATQNxzzz333BNA3HPPPffcE0Dcc88999wTQNxzzz333BNA3HPPPffcE0Dcc88999wTQNxzzz333BNA3HPPPffcE0Dhhx9++OETQNxzzz333BNA3HPPPffcE0D77rvvvvsSQN9555133hFAjjzyyCOPEEAgf/zxxx8PQCuttNJKKw1A7KuvvvrqC0AGE0wwwQQLQDTKKKOMMgpAOOGEE044CUDaZ5999tkHQIYWWmihhQZAgQUWWGCBBUDDDDPMMMMEQC200EILLQRA8sMPP/zwA0B544033ngDQOSKK6644gJAVlpppZVWAkCOOeaYY44BQOSQQw455ABAOuiggw46AEAif/zxxx//P99999133/0/Y4wxxhhj/D+XWmqppZb6P95444033vg/Jpdccskl9z/llVdeeeX1P2mkkUYaafQ/nnLKKaec8j9ssMEGG2zwP5A99thjj+0/b7rppptu6j+99dZbb73lP+SQQw455OA/RRVVVFFF1T+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarPwYZZJBBBqk/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/ddJJJ5100j8ttNBCCy3kPy+++OKLL+4//PHHH3/88T864ogjjjjyPyWSSCKJJPI/1FFHHXXU8T+UUEIJJZTwPw422GCDDeY/qJ566qmn3j/YW2+99dbbPyeccMIJJ9w/d9xxxx133D8ONthggw3mP9liiy222PI/oogiiiii+D8zyiijjDL6PzPKKKOMMvo/CyqooIIK+j+66aabbrr5PwUZZJBBBvk/ddddd9119z8655xzzjn3PzrnnHPOOfc/Ouecc8459z9hhx122GH3Pz744IMPPvg/tdhiiy22+D8zyiijjDL6P+urr7766vs/oo022mij/T/kjjvuuOP+PyeYYIIJJgBADDHEEEMMAUCsscYaa6wBQJJKKqmkkgJARxtttNFGA0Dom2+++eYDQHPMMccccwRA11xzzTXXBEAdddRRRx0FQJVVVllllQVABA444IADBkBonnnmmWcGQKSOOuqoowZACB988MEHB0BXX3311VcHQKiffvrppwdANNBAAw00CEC/AAMMMMAIQBpppJFGGglAfvnll19+CUDDEUccccQJQB966KGHHgpAcLrppptuCkDnmmuuueYKQJFDDjnkkAtABySQQAIJDEANNdRQQw0NQMstt9xyyw1A7bbbbrvtDkAIIIAAAggQQHbYYYcddhBA0EADDTTQEED44IMPPvgQQAcddNBBBxFABx100EEHEUADCSSQQAIRQPjggw8++BBA1lRTTTXVEECyyCKLLLIQQHHEEUcccRBACCCAAAIIEEA0zzzzzDMPQMstt9xyyw1AvvTSSy+9DEAss8wyyywLQFZZZZVVVglAJ5dccsklB0CqpZZaaqkFQIcccsghhwRAoIMOOuigA0AVU0wxxRQDQLHCCiussAJAddJJJ510AkAcaqihhhoCQKKJJppoogFAPvnkk08+AUDGGGOMMcYAQBJIIIEEEgBA5I477rjj/j/bbLPNNtv8P0srrbTSSvs/zjnnnHPO+T8FGWSQQQb5P7XYYosttvg/jjjiiCOO+D+iiCKKKKL4P6KIIoooovg/tdhiiy22+D/eeOONN974P1ZZZZVVVvk/uummm266+T9caqmlllr6PwD877///vs/Zp111lln/T80zzzzzDP/P4EAAggggABArLHGGmusAUC76qqrrroCQNRLL7300gNAwwwzzDDDBECMLbbYYosFQDfWWGONNQZA9M4777zzBkBihx122GEHQMYXX3zxxQdANNBAAw00CECZYIIJJpgIQP3www8//AhAQwkllFBCCUDPOeecc84JQFBCCSWUUApA55prrrnmCkBfe+21114LQKWTTjrppAtAzTPPPPPMC0D/+++///4LQCeccMIJJwxAHXTQQQcdDEAddNBBBx0MQB100EEHHQxABySQQAIJDEDsq6+++uoLQM0zzzzzzAtAwwsvvPDCC0Ass8wyyywLQH755ZdffglADTDAAAMMCEA31lhjjTUGQNdcc8011wRAeeONN954A0BrqqmmmmoCQPzxxx9//AFA/PHHH3/8AUD88ccff/wBQBxqqKGGGgJAkkoqqaSSAkCvvPLKK68EQIYWWmihhQZAmWCCCSaYCED22WefffYJQCSLLLLIIgtAbbTRRhttDEANNdRQQw0NQBZddNFFFw1ADTXUUEMNDUAEDTTQQAMNQMccc8wxxwxAwwsvvPDCC0DiiSeeeOIJQLzvvvvuuwdA0UUXXXTRBUD766+//voDQBVTTDHFFANAiSKKKKKIAkD88ccff/wBQI455phjjgFAZplllllmAUBmmWWWWWYBQHDBBRdccAFAl2GGGWaYAUAvuuiiiy4CQFVUUUUVVQRA9M4777zzBkA44YQTTjgJQIcbbrjhhgtAIYUUUkghDUARRhhhhBEOQMYWW2yxxQ5AF1dcccUVD0AXV1xxxRUPQBdXXHHFFQ9AF1dcccUVD0AXV1xxxRUPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AXV1xxxRUPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAMHHHDAAQ9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9AF1dcccUVD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9AF1dcccUVD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQAwvvPDCCw9ADC+88MILD0AML7zwwgsPQBdXXHHFFQ9A\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[513]}},\"selected\":{\"id\":\"1681\"},\"selection_policy\":{\"id\":\"1682\"}},\"id\":\"1660\",\"type\":\"ColumnDataSource\"},{\"attributes\":{},\"id\":\"1646\",\"type\":\"PanTool\"}],\"root_ids\":[\"1629\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"d92ace25-ec47-4b1d-a527-97f459bf2cf2\",\"root_ids\":[\"1629\"],\"roots\":{\"1629\":\"61d6614b-411e-4ac9-99c6-dc73ee178cea\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "1629"
}
},
"output_type": "display_data"
}
],
"source": [
"df = pd.read_csv('test_potentiometer_daq.csv')\n",
"\n",
"p = bokeh.plotting.figure(\n",
" x_axis_label='time (s)',\n",
" y_axis_label='voltage (V)',\n",
" frame_height=175,\n",
" frame_width=500,\n",
")\n",
"p.x_range.range_padding = 0\n",
"\n",
"p.line(df['time (ms)'] / 1000, df['voltage (V)'])\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Lovely!\n",
"\n",
"Let's think for a moment about how we get data from the device. We use Python-based timing to do periodic requests for data. The request is sent over the serial connection to the device. The device parses the request and sends data back over over the serial connection. The data packet is then parsed and processed. This set of operations might result in unreliable timing, since there are lots of operations that happen to get the results.\n",
"\n",
"To check how well we did with timing, we can plot the ECDF of the timing differences."
]
},
{
"cell_type": "code",
"execution_count": 18,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"82f44f15-0c14-49d4-9e1b-3a7205b01fd8\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"1746\"}],\"center\":[{\"id\":\"1749\"},{\"id\":\"1753\"},{\"id\":\"1783\"}],\"left\":[{\"id\":\"1750\"}],\"plot_height\":300,\"plot_width\":400,\"renderers\":[{\"id\":\"1772\"}],\"title\":{\"id\":\"1774\"},\"toolbar\":{\"id\":\"1761\"},\"x_range\":{\"id\":\"1738\"},\"x_scale\":{\"id\":\"1742\"},\"y_range\":{\"id\":\"1740\"},\"y_scale\":{\"id\":\"1744\"}},\"id\":\"1737\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{\"axis_label\":\"ECDF\",\"formatter\":{\"id\":\"1778\"},\"ticker\":{\"id\":\"1751\"}},\"id\":\"1750\",\"type\":\"LinearAxis\"},{\"attributes\":{\"text\":\"\"},\"id\":\"1774\",\"type\":\"Title\"},{\"attributes\":{},\"id\":\"1751\",\"type\":\"BasicTicker\"},{\"attributes\":{\"axis\":{\"id\":\"1750\"},\"dimension\":1,\"ticker\":null},\"id\":\"1753\",\"type\":\"Grid\"},{\"attributes\":{\"data_source\":{\"id\":\"1768\"},\"glyph\":{\"id\":\"1770\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"1771\"},\"selection_glyph\":null,\"view\":{\"id\":\"1773\"}},\"id\":\"1772\",\"type\":\"GlyphRenderer\"},{\"attributes\":{},\"id\":\"1738\",\"type\":\"DataRange1d\"},{\"attributes\":{\"axis_label\":\"time between acquisitions (ms)\",\"formatter\":{\"id\":\"1776\"},\"ticker\":{\"id\":\"1747\"}},\"id\":\"1746\",\"type\":\"LinearAxis\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"1760\",\"type\":\"BoxAnnotation\"},{\"attributes\":{\"items\":[{\"id\":\"1784\"}],\"visible\":false},\"id\":\"1783\",\"type\":\"Legend\"},{\"attributes\":{\"fill_color\":{\"value\":\"#1f77b3\"},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"1770\",\"type\":\"Circle\"},{\"attributes\":{\"source\":{\"id\":\"1768\"}},\"id\":\"1773\",\"type\":\"CDSView\"},{\"attributes\":{},\"id\":\"1754\",\"type\":\"PanTool\"},{\"attributes\":{},\"id\":\"1776\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"1740\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"1755\",\"type\":\"WheelZoomTool\"},{\"attributes\":{},\"id\":\"1782\",\"type\":\"UnionRenderers\"},{\"attributes\":{\"fill_alpha\":{\"value\":0.1},\"fill_color\":{\"value\":\"#1f77b3\"},\"line_alpha\":{\"value\":0.1},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"1771\",\"type\":\"Circle\"},{\"attributes\":{\"data\":{\"__ECDF\":{\"__ndarray__\":\"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AAAAAADw6z8AAAAAAGDaPwAAAAAAgNo/AAAAAAAA7D8AAAAAAKDaPwAAAAAAwOc/AAAAAAAAsD8AAAAAANDnPwAAAAAA4Oc/AAAAAADA2j8AAAAAABDsPwAAAAAA4No/AAAAAAAA4z8AAAAAABDjPwAAAAAAANs/AAAAAADQ7j8AAAAAACDbPwAAAAAAQNs/AAAAAABg2z8AAAAAAPDnPwAAAAAAgNs/AAAAAADg7j8AAAAAAEDNPwAAAAAA8O4/AAAAAACAsD8AAAAAACDsPwAAAAAAoNs/AAAAAACAzT8AAAAAAADoPwAAAAAAMOw/AAAAAADAzT8AAAAAABDoPwAAAAAAIOM/AAAAAADA2z8AAAAAADDjPwAAAAAAQOw/AAAAAADg2z8AAAAAAADcPwAAAAAAIOg/AAAAAAAg3D8AAAAAAEDcPwAAAAAAUOw/AAAAAABA4z8AAAAAAGDcPwAAAAAAgNw/AAAAAAAA8D8AAAAAAADOPwAAAAAAUOM/AAAAAABg4z8AAAAAAKDcPwAAAAAAAO8/AAAAAABAzj8AAAAAAGDsPwAAAAAAcOM/AAAAAACA4z8AAAAAAACxPwAAAAAAMOg/AAAAAABA6D8AAAAAAJDjPwAAAAAAgM4/AAAAAAAQ7z8AAAAAAICxPw==\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[512]},\"__dummy_cat\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"__label\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"index\":[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,441,442,443,444,445,446,447,448,449,450,451,452,453,454,455,456,457,458,459,460,461,462,463,464,465,466,467,468,469,470,471,472,473,474,475,476,477,478,479,480,481,482,483,484,485,486,487,488,489,490,491,492,493,494,495,496,497,498,499,500,501,502,503,504,505,506,507,508,509,510,511],\"x\":[20,19,21,19,19,22,18,20,22,19,20,20,21,19,18,24,17,22,19,19,20,21,19,19,21,23,18,18,24,18,22,18,19,20,19,24,18,19,19,22,21,18,20,22,19,23,18,20,18,21,23,17,19,20,21,22,19,18,20,21,22,19,19,20,21,21,20,17,22,21,18,21,21,20,17,24,18,20,20,19,23,19,17,20,21,20,22,17,23,18,21,19,20,22,19,19,23,18,22,20,21,18,18,23,18,23,17,20,21,18,23,17,21,22,17,20,22,18,21,20,19,22,19,21,19,22,20,17,22,18,24,18,19,19,21,22,19,20,20,19,21,21,19,19,20,24,18,19,22,16,24,17,20,20,21,22,19,18,20,20,23,19,18,23,19,21,18,21,18,20,24,18,19,22,17,21,21,20,18,21,23,16,21,19,20,23,20,20,18,19,24,18,19,22,18,22,21,18,19,20,22,19,19,20,20,22,19,19,22,19,22,18,21,18,21,21,20,18,22,17,22,21,18,23,19,20,19,20,21,18,24,18,19,21,20,19,21,19,19,21,23,19,18,22,18,23,18,18,23,18,23,17,20,21,19,22,18,19,23,19,22,18,18,21,19,24,18,19,22,18,23,19,18,23,18,23,16,21,21,17,22,18,22,20,19,22,19,22,17,20,24,18,20,20,18,24,17,19,20,22,21,18,19,22,19,23,18,19,21,20,22,17,19,23,19,21,18,19,22,19,23,17,20,22,21,17,20,23,17,20,21,20,19,21,19,23,18,19,22,19,22,18,20,22,20,17,22,19,21,18,24,18,20,19,23,17,21,20,18,21,23,18,19,21,18,22,20,19,22,19,19,21,19,23,17,22,19,18,23,18,23,17,20,20,21,21,20,18,23,18,20,20,18,23,20,18,22,20,20,21,20,19,18,22,19,23,16,20,20,20,22,18,21,22,18,20,21,18,21,20,23,18,19,22,18,23,18,19,19,21,22,20,18,22,17,21,21,21,19,20,22,17,21,18,21,23,18,19,22,18,22,19,19,22,19,21,17,21,21,19,22,19,20,20,19,23,19,19,19,21,19,23,18,23,17,22,19,18,21,22,18,21,20,19,20,22,19,19,21,19,19,22,20,19,19,24,18,20,20,19,23,18,22,20,20,17,21,21,20,18,23,17]},\"selected\":{\"id\":\"1781\"},\"selection_policy\":{\"id\":\"1782\"}},\"id\":\"1768\",\"type\":\"ColumnDataSource\"},{\"attributes\":{\"overlay\":{\"id\":\"1760\"}},\"id\":\"1756\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"1757\",\"type\":\"SaveTool\"},{\"attributes\":{},\"id\":\"1778\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"1742\",\"type\":\"LinearScale\"},{\"attributes\":{},\"id\":\"1758\",\"type\":\"ResetTool\"},{\"attributes\":{\"label\":{\"value\":\" \"},\"renderers\":[{\"id\":\"1772\"}]},\"id\":\"1784\",\"type\":\"LegendItem\"},{\"attributes\":{},\"id\":\"1759\",\"type\":\"HelpTool\"},{\"attributes\":{},\"id\":\"1747\",\"type\":\"BasicTicker\"},{\"attributes\":{},\"id\":\"1781\",\"type\":\"Selection\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"1754\"},{\"id\":\"1755\"},{\"id\":\"1756\"},{\"id\":\"1757\"},{\"id\":\"1758\"},{\"id\":\"1759\"}]},\"id\":\"1761\",\"type\":\"Toolbar\"},{\"attributes\":{\"axis\":{\"id\":\"1746\"},\"ticker\":null},\"id\":\"1749\",\"type\":\"Grid\"},{\"attributes\":{},\"id\":\"1744\",\"type\":\"LinearScale\"}],\"root_ids\":[\"1737\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"82f44f15-0c14-49d4-9e1b-3a7205b01fd8\",\"root_ids\":[\"1737\"],\"roots\":{\"1737\":\"9ad96d22-322a-497d-b537-7e9f7ed0623f\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "1737"
}
},
"output_type": "display_data"
}
],
"source": [
"p = bokeh_catplot.ecdf(\n",
" np.diff(df['time (ms)'].values),\n",
" x_axis_label='time between acquisitions (ms)',\n",
")\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Yes, the median time between acquisitions is 20 ms, but we do see substantial spread. This may be acceptable for many applications and nothing to worry about. However, we may want to keep the timing of acquisitions as close to our target as possible. That is, we want Arduino to be constantly pushing data out using its timing. "
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Streaming acquisition with toggle and button controls\n",
"\n",
"We can update our app to receive streaming data by changing the way we read in data. Instead of reading in a single line (that is, a set of bytes that ends with a newline), we can read all of the data that has been sent across the serial connection. The `read()` method of a `Serial` instance reads in a set number of bytes. If the prescribed number of bytes are not available, it attempts to read for the amount of time given by the set timeout. Using this behavior, here is our strategy to read streaming data.\n",
"\n",
"1. Set a timeout for reading that is short.\n",
"2. Initialize the output to be the bytes we have already read in (the `read_buffer` kwarg in the function below). \n",
"3. Read in a **chunk** of data of a given size and append it to the output.\n",
"4. Check the size of the chunk. If it is less than the number of bytes asked for, we hit a timeout, so we know we have read all of the data. Return the output. Otherwise, goto 3.\n",
"\n",
"The function below accomplishes reading in all of the unread data that has been sent over the serial connection."
]
},
{
"cell_type": "code",
"execution_count": 19,
"metadata": {},
"outputs": [],
"source": [
"def read_all(ser, chunk_size=100, read_buffer=b\"\", timeout=0.001):\n",
" \"\"\"Real all available bytes from serial port \n",
" and append to the read buffer. \n",
" \n",
" Parameters\n",
" ----------\n",
" ser : serial.Serial() instance\n",
" The devise we are reading from.\n",
" chunk_size : int, default 100\n",
" Size of chunks of streaming data to read in.\n",
" read_buffer : bytes, default b''\n",
" Previous read buffer that is appended to.\n",
" timeout : float, default 0.001\n",
" Timeout for reading in data stream in seconds. It should be\n",
" smaller than the rate of data streaming in because if data \n",
" continues to stream in, the read will continue, posibly\n",
" forever.\n",
" \n",
" Returns\n",
" -------\n",
" output : bytes\n",
" Bytes object that contains read.\n",
" \"\"\"\n",
" # Set timeout\n",
" previous_timeout = ser.timeout\n",
" ser.timeout = timeout\n",
"\n",
" # Read chunk or until timeout\n",
" chunk = ser.read(size=chunk_size)\n",
" out = read_buffer + chunk\n",
"\n",
" # Keep reading chunks until they're exhausted\n",
" while len(chunk) == chunk_size:\n",
" chunk = ser.read(size=chunk_size)\n",
" out += chunk\n",
"\n",
" # Reset to previous timeout\n",
" ser.timeout = previous_timeout\n",
"\n",
" return out"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"If we are going to use this in our acquisition, we also need to have a parser to convert these longer byte strings to data. For our example with the Arduino potentiometer, the byte strings we read in will looks something like:\n",
"\n",
" b'1032,541\\r\\n1052,542\\r\\n1073,554\\r\\n1093,5'\n",
" \n",
"Recall that the first number is the time in milliseconds and the second number is a voltage, going from 0 to 1023. The `\\r\\n` separate individual data pairs. In this case, we have three complete data pairs, but we didn't quite get the fourth; it got cut off. So, parsing this, we want to add `1032`, `1052` and `1073` to our list of times, `541`, `542`, and `554` to our list of voltages, and store `b'1093,5'` as the read buffer that we will add to the next time we attempt to read.\n",
"\n",
"Here is a function to do that. We use a `try` block to ignore anything that does not parse properly."
]
},
{
"cell_type": "code",
"execution_count": 20,
"metadata": {},
"outputs": [],
"source": [
"def parse_read(read):\n",
" time_ms = []\n",
" voltage = []\n",
" \n",
" raw_list = read.decode().split('\\r\\n')\n",
"\n",
" for raw in raw_list[:-1]:\n",
" try:\n",
" t, V = raw.split(',')\n",
" time_ms.append(int(t))\n",
" voltage.append(int(V) * 5 / 1023)\n",
" except:\n",
" pass\n",
" \n",
" return time_ms, voltage, raw_list[-1].encode()"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Now that we have these functions, we can rebuild our acquisition app. We'll start by getting fresh widgets."
]
},
{
"cell_type": "code",
"execution_count": 21,
"metadata": {},
"outputs": [],
"source": [
"acquire_toggle = pn.widgets.Toggle(\n",
" name=\"ACQUIRE\", value=False, button_type=\"success\", width=100,\n",
")\n",
"\n",
"stop_button = pn.widgets.Button(name=\"STOP\", button_type=\"danger\", width=100)\n",
"\n",
"received_text = pn.widgets.StaticText(\n",
" name=\"Data points received\", value=str(0)\n",
")\n",
"\n",
"status_text = pn.widgets.StaticText(\n",
" name=\"Status\", value=\"Awaiting data acquisition.\"\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We first have to update our data acquisition function (it's no longer a request). Note that we need to keep track of the read buffer (the left over stuff from each read that we need to prepend to the next read). To do this, it needs to be mutable, something that can be updated within functions and still used outside. We therefore put the read buffer in a list."
]
},
{
"cell_type": "code",
"execution_count": 22,
"metadata": {},
"outputs": [],
"source": [
"read_buffer = [b\"\"]\n",
"\n",
"\n",
"def daq_stream(event=None):\n",
" \"\"\"Process a stream of data\"\"\"\n",
" if acquire_toggle.value: \n",
" # Wait for data to arrive\n",
" while arduino.in_waiting < 0:\n",
" pass\n",
"\n",
" # Read in the data\n",
" read = read_all(arduino, chunk_size=100, read_buffer=read_buffer[0])\n",
" \n",
" # Parse and add data set\n",
" t, V, read_buffer[0] = parse_read(read)\n",
" time_ms.append(t)\n",
" voltage.append(V)\n",
" \n",
" # Report that we got more data\n",
" received_text.value = str(int(received_text.value) + len(t))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"To get data acquisition, we should add a callback to the \"ACQUIRE\" toggle that turns data streaming on and off from Arduino. This should happen every time the state of the \"ACQUIRE\" toggle changes. As before, we set up a watcher."
]
},
{
"cell_type": "code",
"execution_count": 23,
"metadata": {},
"outputs": [],
"source": [
"def stream_control(event):\n",
" \"\"\"Turn on the data stream\"\"\" \n",
" if event.new:\n",
" status_text.value = \"Acquiring data.\"\n",
"\n",
" arduino.write(bytes([READ_DAQ_DELAY]) + (str(delay) + \"x\").encode())\n",
" arduino.write(bytes([STREAM]))\n",
" else:\n",
" arduino.write(bytes([ON_REQUEST]))\n",
" status_text.value = \"Awaiting data acquisition.\"\n",
" \n",
" \n",
"# Add callback to widget\n",
"acquire_watcher = acquire_toggle.param.watch(stream_control, 'value')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Because we are reading in chunks of data and appending chucks to the `time_ms` and `voltage` lists, we need to change the shutdown operation to concatenate the results into a single Numpy array before putting them in a data frame."
]
},
{
"cell_type": "code",
"execution_count": 24,
"metadata": {},
"outputs": [],
"source": [
"def shutdown_and_save(event=None):\n",
" \"\"\"Stop procedures\"\"\"\n",
" # Stop the periodic callback\n",
" pc.stop()\n",
"\n",
" # Disable toggles\n",
" acquire_toggle.value = False\n",
" acquire_toggle.disabled = True\n",
" stop_button.disabled = True\n",
"\n",
" # Report status\n",
" status_text.value = \"Arduino connection closed; app terminated.\"\n",
"\n",
" # Close the connection to Arduino\n",
" try:\n",
" arduino.reset_input_buffer()\n",
" arduino.close()\n",
" except:\n",
" pass\n",
"\n",
" # Write the resulting data out to disk\n",
" pd.DataFrame(\n",
" data={\n",
" \"time (ms)\": np.concatenate(time_ms),\n",
" \"voltage (V)\": np.concatenate(voltage),\n",
" }\n",
" ).to_csv(outfile, index=False)\n",
"\n",
" # Reset the lists storing data\n",
" time_ms.clear()\n",
" voltage.clear()\n",
" \n",
" \n",
"# Connect STOP button to this new function\n",
"stop_button.on_click(shutdown_and_save)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Now, we need to connect a periodic callback to our text widget for data acquisition. We will set the delay *longer* than the delay from streaming, but not so long that we accumulate too much data in the buffer coming from the device. We do not need to ask for every data point when it is sent, and it is easier on the Python side to ask less frequently. So, we will do the periodic callback every 110 ms, while Arduino writes data every 20 ms."
]
},
{
"cell_type": "code",
"execution_count": 25,
"metadata": {},
"outputs": [],
"source": [
"pc = received_text.add_periodic_callback(daq_stream, period=110)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Finally, we can open the port and layout the app!"
]
},
{
"cell_type": "code",
"execution_count": 26,
"metadata": {},
"outputs": [
{
"data": {},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.holoviews_exec.v0+json": "",
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
"
\n",
"
\n",
""
],
"text/plain": [
"Row\n",
" [0] Column\n",
" [0] Toggle(button_type='success', name='ACQUIRE', width=100)\n",
" [1] Button(button_type='danger', name='STOP', width=100)\n",
" [1] Spacer(width=15)\n",
" [2] Column\n",
" [0] StaticText(name='Data points received', value='0')\n",
" [1] StaticText(name='Status', value='Awaiting data a...)"
]
},
"execution_count": 26,
"metadata": {
"application/vnd.holoviews_exec.v0+json": {
"id": "1866"
}
},
"output_type": "execute_result"
}
],
"source": [
"arduino = open_arduino(port)\n",
"\n",
"pn.Row(\n",
" pn.Column(acquire_toggle, stop_button),\n",
" pn.Spacer(width=15),\n",
" pn.Column(received_text, status_text),\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let's take a look to make sure acquisition went ok."
]
},
{
"cell_type": "code",
"execution_count": 27,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"e22f210e-a4c0-473c-bc97-8d6a484f253d\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"1975\"}],\"center\":[{\"id\":\"1978\"},{\"id\":\"1982\"}],\"frame_height\":175,\"frame_width\":500,\"left\":[{\"id\":\"1979\"}],\"renderers\":[{\"id\":\"2000\"}],\"title\":{\"id\":\"2029\"},\"toolbar\":{\"id\":\"1990\"},\"x_range\":{\"id\":\"1967\"},\"x_scale\":{\"id\":\"1971\"},\"y_range\":{\"id\":\"1969\"},\"y_scale\":{\"id\":\"1973\"}},\"id\":\"1966\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{},\"id\":\"1969\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"1984\",\"type\":\"WheelZoomTool\"},{\"attributes\":{\"text\":\"\"},\"id\":\"2029\",\"type\":\"Title\"},{\"attributes\":{\"axis_label\":\"voltage (V)\",\"formatter\":{\"id\":\"2033\"},\"ticker\":{\"id\":\"1980\"}},\"id\":\"1979\",\"type\":\"LinearAxis\"},{\"attributes\":{\"data_source\":{\"id\":\"1997\"},\"glyph\":{\"id\":\"1998\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"1999\"},\"selection_glyph\":null,\"view\":{\"id\":\"2001\"}},\"id\":\"2000\",\"type\":\"GlyphRenderer\"},{\"attributes\":{\"source\":{\"id\":\"1997\"}},\"id\":\"2001\",\"type\":\"CDSView\"},{\"attributes\":{},\"id\":\"1988\",\"type\":\"HelpTool\"},{\"attributes\":{\"overlay\":{\"id\":\"1989\"}},\"id\":\"1985\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"2031\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"axis\":{\"id\":\"1979\"},\"dimension\":1,\"ticker\":null},\"id\":\"1982\",\"type\":\"Grid\"},{\"attributes\":{},\"id\":\"2036\",\"type\":\"Selection\"},{\"attributes\":{},\"id\":\"1973\",\"type\":\"LinearScale\"},{\"attributes\":{},\"id\":\"1971\",\"type\":\"LinearScale\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"1989\",\"type\":\"BoxAnnotation\"},{\"attributes\":{},\"id\":\"1976\",\"type\":\"BasicTicker\"},{\"attributes\":{},\"id\":\"1980\",\"type\":\"BasicTicker\"},{\"attributes\":{\"data\":{\"x\":{\"__ndarray__\":\"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\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[446]},\"y\":{\"__ndarray__\":\"AwcccMABD0ADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQAMHHHDAAQ9A+N577733DkADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQAMHHHDAAQ9AAwcccMABD0ADBxxwwAEPQPjee++99w5A5I477rjjDkDttttuu+0OQPjee++99w5AAwcccMABD0D43nvvvfcOQPjee++99w5A+N577733DkD43nvvvfcOQO2222677Q5A+N577733DkD43nvvvfcOQPjee++99w5Ara+++uqrD0CUUEIJJZQQQI455phjjhFAf/rpp59+EkDTSy+99NITQNNLL7300hNAzjfffPPNE0DTSy+99NITQMkjjzzyyBNA00svvfTSE0B0zz333HMTQOONN9544xFASiSRRBJJEEAnllhiiSUOQMstt9xyyw1A1lVXXXXVDUDWVVddddUNQPLNN9988w1AJ5ZYYoklDkA0zzzzzDMPQCyssMIKKxBAZ5xxxhlnEEC78MILL7wQQOSQQw455BBA5JBDDjnkEEDffPPNN98QQNBAAw000BBAt9xyyy23EECZZJJJJpkQQEQQQQQRRBBADTTQQAMNEEDKJ5988skPQMonn3zyyQ9AyieffPLJD0CEFFJIIYUQQNNLL7300hNA00svvfTSE0DTSy+99NITQNNLL7300hNA00svvfTSE0DTSy+99NITQNNLL7300hNA00svvfTSE0DTSy+99NITQCWSSCKJJBJAAwkkkEACEUB77LHHHnsQQCGEEEIIIRBAooceeuihD0Arp5xyyikPQBdXXHHFFQ9AIH/88ccfD0A/99xzzz0PQHrnnXfeeQ9Agw8++OCDD0Ctr7766qsPQLbXXnvttQ9Awf/++++/D0C211577bUPQNNPP/300w9ACCCAAAIIEEAIIIAAAggQQAMMMMAAAxBA8scff/zxD0Cihx566KEPQNZVV1111Q1ANMooo4wyCkAsrrjiiisGQPLDDz/88ANAZZNNNtlkA0Baa6211loDQGWTTTbZZANAl1tuueWWA0AOPPDAAw8EQLnkkksuuQRAQP74448/BkCKJ5544okHQIUQQgghhAhAJJFEEkkkCUB++eWXX34JQKeZZppppglAsMEGG2ywCUC66aabbroJQLrppptuuglAuummm266CUC66aabbroJQLDBBhtssAlAuummm266CUCwwQYbbLAJQLDBBhtssAlAsMEGG2ywCUCwwQYbbLAJQJxxxhlnnAlATDHFFFNMCUANMMAAAwwIQPXUU0899QRA33nnnXfeAUDTTz/99NP/P22uueaaa/4/L7744osv/j8vvvjiiy/+Py+++OKLL/4/SB999NFH/z+FEUYYYYQBQAkllFBCCQVACB988MEHB0Anl1xyySUHQAgffPDBBwdAmWaaaaaZBkAyxRRTTDEFQFFDDTXUUANAEUIIIYQQAkAMMcQQQwwBQDrooIMOOgBAcb/99ttv/z9bb7311lv/P3G//fbbb/8/cb/99ttv/z8HIIAAAggAQFhggQUWWABAAwkkkEACAUA++eSTTz4BQIURRhhhhAFAJZJIIokkAkCSSiqppJICQIkiiiiiiAJAkkoqqaSSAkCJIooooogCQE0yySSTTAJAHGqooYYaAkBSSSWVVFIBQDTPPPPMM/8/O+ywww47/D+12GKLLbb4PzfWWGONNfY/pZRSSiml9D/cc88999zzP7XTTjvttPM/eeONN9548z8BAwwwwADzP+OQQw455PA/xxxzzDHH7D8MMcQQQwzhPwceeOCBB64/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz/FEkssscTCP7XTTjvttNM/+N5777333j/11FNPPfXkP2aYYYYZZug///vvv//+6z8gf/zxxx/vPzDAAAMMMPA/u/DCCy+88D/jkEMOOeTwP9BAAw000PA/45BDDjnk8D/44IMPPvjwPwwxxBBDDPE/0EADDTTQ8D8wwAADDDDwP99999133+0/Pvjggw8+6D/pn3/++effPwUZZJBBBsk/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP+SQQw455NA/d9xxxx133D+NM84444zjP5533nnnnec/Lrnkkksu6T9++eWXX37pP84555xzzuk/pplmmmmm6T+mmWaaaabpP1ZZZZVVVuk/VllllVVW6T/ut99+++3nP6622mqrreY/vfXWW2+95T+100477bTjP+mff/75598/xhdffPHF1z910kknnXTSPzTRRBNNNNE/NNFEE0000T910kknnXTSP8YXX3zxxdc/7bLLLrvs4j9A/fTTTz/tPzriiCOOOPI/PPPMM8888z8888wzzzzzPzzzzDPPPPM/KaOMMsoo8z/tsssuu+zyP7HCCiussPI/YYIJJphg8j/QQAMNNNDwP6ieeuqpp+4/r7vuuuuu6z/OOeecc87pPz744IMPPug/Jpdccskl5z821lhjjTXmP7311ltvveU/bbXVVltt5T9FFVVUUUXlP/XUU0899eQ/pZRSSiml5D9VVFFFFVXkP91zzz333OM/FVNMMcUU4z+UUEIJJZTgP8ccc8wxx9w/2FtvvfXW2z/HHHPMMcfcP6ieeuqpp94/jTPOOOOM4z/eeOONN97oP++888477+w/+N5777337j/QPvvss8/uP1deeeWVV+4/33333Xff7T/22WefffbpP1522WWXXeY/vfXWW2+95T+99dZbb73lP1522WWXXeY/3njjjTfe6D/QPvvss8/uPzTRRBNNNPE/scIKK6yw8j9QQw011FDzP7XTTjvttPM/tdNOO+208z+100477bTzP7XTTjvttPM/eeONN9548z9lk0022WTzPwgggAACCPA/7rfffvvt5z8HHnjggQfeP2WTTTbZZMM/hxtuuOGGqz+HG2644YarPwceeOCBB64/hxtuuOGGqz8HHnjggQeuP4cbbrjhhqs/hxtuuOGGqz8HHnjggQeuP4cbbrjhhqs/1FFHHXXU0T8HHnjggQfeP/zxxx9//OE//PHHH3/84T+EEUYYYYThP1xxxRVXXOE/V1lllVVW2T/GF1988cXHP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz8HHnjggQeuPwceeOCBB64/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz8HHnjggQeuP5daaqmllto/LbTQQgst5D8++OCDDz7oP84555xzzuk/zjnnnHPO6T/OOeecc87pP6aZZppppuk/pplmmmmm6T8++OCDDz7oPw422GCDDeY/HXXUUUcd5T8dddRRRx3lPx111FFHHeU/NtZYY4015j9WWWWVVVbpP2idddZZZ+0/EUIIIYQQ8j8FFFBAAQX0P1lllVVWWfU/qqWWWmqp9T+VVVZZZZX1P0UVVVRRRfU/VVRRRRVV9D+XYYYZZpjxP2idddZZZ+0/zjnnnHPO6T8WWGCBBRboP5533nnnnec/xhdffPHF5z+OOOKII47oP5daaqmlluo/gAACCCCA8D/JI4888sjzP4YWWmihhfY/euihhx56+D9WWWWVVVb5P7rppptuuvk/zjnnnHPO+T/OOeecc875P84555xzzvk/4oknnnji+T/OOeecc875P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5Pw==\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[446]}},\"selected\":{\"id\":\"2036\"},\"selection_policy\":{\"id\":\"2037\"}},\"id\":\"1997\",\"type\":\"ColumnDataSource\"},{\"attributes\":{\"range_padding\":0},\"id\":\"1967\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"1987\",\"type\":\"ResetTool\"},{\"attributes\":{},\"id\":\"1983\",\"type\":\"PanTool\"},{\"attributes\":{},\"id\":\"1986\",\"type\":\"SaveTool\"},{\"attributes\":{},\"id\":\"2037\",\"type\":\"UnionRenderers\"},{\"attributes\":{},\"id\":\"2033\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"1983\"},{\"id\":\"1984\"},{\"id\":\"1985\"},{\"id\":\"1986\"},{\"id\":\"1987\"},{\"id\":\"1988\"}]},\"id\":\"1990\",\"type\":\"Toolbar\"},{\"attributes\":{\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"1998\",\"type\":\"Line\"},{\"attributes\":{\"axis\":{\"id\":\"1975\"},\"ticker\":null},\"id\":\"1978\",\"type\":\"Grid\"},{\"attributes\":{\"axis_label\":\"time (s)\",\"formatter\":{\"id\":\"2031\"},\"ticker\":{\"id\":\"1976\"}},\"id\":\"1975\",\"type\":\"LinearAxis\"},{\"attributes\":{\"line_alpha\":0.1,\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"1999\",\"type\":\"Line\"}],\"root_ids\":[\"1966\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"e22f210e-a4c0-473c-bc97-8d6a484f253d\",\"root_ids\":[\"1966\"],\"roots\":{\"1966\":\"b1f5ebdc-eaa1-4266-989b-f16f0a777e08\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "1966"
}
},
"output_type": "display_data"
}
],
"source": [
"df = pd.read_csv('test_potentiometer_daq.csv')\n",
"\n",
"p = bokeh.plotting.figure(\n",
" x_axis_label='time (s)',\n",
" y_axis_label='voltage (V)',\n",
" frame_height=175,\n",
" frame_width=500,\n",
")\n",
"p.x_range.range_padding = 0\n",
"\n",
"p.line(df['time (ms)'] / 1000, df['voltage (V)'])\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"This looks good. And we should again check the timing. We expect our timing to be better, with 20 or 21 ms between data points."
]
},
{
"cell_type": "code",
"execution_count": 28,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"f4b27cab-87ea-4741-b2d4-17e420ac29d2\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"2101\"}],\"center\":[{\"id\":\"2104\"},{\"id\":\"2108\"},{\"id\":\"2138\"}],\"left\":[{\"id\":\"2105\"}],\"plot_height\":300,\"plot_width\":400,\"renderers\":[{\"id\":\"2127\"}],\"title\":{\"id\":\"2129\"},\"toolbar\":{\"id\":\"2116\"},\"x_range\":{\"id\":\"2093\"},\"x_scale\":{\"id\":\"2097\"},\"y_range\":{\"id\":\"2095\"},\"y_scale\":{\"id\":\"2099\"}},\"id\":\"2092\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{},\"id\":\"2131\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"2115\",\"type\":\"BoxAnnotation\"},{\"attributes\":{},\"id\":\"2102\",\"type\":\"BasicTicker\"},{\"attributes\":{\"axis\":{\"id\":\"2105\"},\"dimension\":1,\"ticker\":null},\"id\":\"2108\",\"type\":\"Grid\"},{\"attributes\":{\"axis_label\":\"ECDF\",\"formatter\":{\"id\":\"2133\"},\"ticker\":{\"id\":\"2106\"}},\"id\":\"2105\",\"type\":\"LinearAxis\"},{\"attributes\":{},\"id\":\"2093\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"2137\",\"type\":\"UnionRenderers\"},{\"attributes\":{\"data_source\":{\"id\":\"2123\"},\"glyph\":{\"id\":\"2125\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"2126\"},\"selection_glyph\":null,\"view\":{\"id\":\"2128\"}},\"id\":\"2127\",\"type\":\"GlyphRenderer\"},{\"attributes\":{},\"id\":\"2133\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"2110\",\"type\":\"WheelZoomTool\"},{\"attributes\":{},\"id\":\"2095\",\"type\":\"DataRange1d\"},{\"attributes\":{\"source\":{\"id\":\"2123\"}},\"id\":\"2128\",\"type\":\"CDSView\"},{\"attributes\":{},\"id\":\"2106\",\"type\":\"BasicTicker\"},{\"attributes\":{\"axis\":{\"id\":\"2101\"},\"ticker\":null},\"id\":\"2104\",\"type\":\"Grid\"},{\"attributes\":{\"items\":[{\"id\":\"2139\"}],\"visible\":false},\"id\":\"2138\",\"type\":\"Legend\"},{\"attributes\":{\"text\":\"\"},\"id\":\"2129\",\"type\":\"Title\"},{\"attributes\":{},\"id\":\"2109\",\"type\":\"PanTool\"},{\"attributes\":{\"fill_color\":{\"value\":\"#1f77b3\"},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"2125\",\"type\":\"Circle\"},{\"attributes\":{},\"id\":\"2136\",\"type\":\"Selection\"},{\"attributes\":{\"overlay\":{\"id\":\"2115\"}},\"id\":\"2111\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"2099\",\"type\":\"LinearScale\"},{\"attributes\":{},\"id\":\"2113\",\"type\":\"ResetTool\"},{\"attributes\":{},\"id\":\"2112\",\"type\":\"SaveTool\"},{\"attributes\":{\"data\":{\"__ECDF\":{\"__ndarray__\":\"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\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[445]},\"__dummy_cat\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"__label\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"index\":[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,441,442,443,444],\"x\":[21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20]},\"selected\":{\"id\":\"2136\"},\"selection_policy\":{\"id\":\"2137\"}},\"id\":\"2123\",\"type\":\"ColumnDataSource\"},{\"attributes\":{},\"id\":\"2097\",\"type\":\"LinearScale\"},{\"attributes\":{\"axis_label\":\"time between acquisitions (ms)\",\"formatter\":{\"id\":\"2131\"},\"ticker\":{\"id\":\"2102\"}},\"id\":\"2101\",\"type\":\"LinearAxis\"},{\"attributes\":{\"label\":{\"value\":\" \"},\"renderers\":[{\"id\":\"2127\"}]},\"id\":\"2139\",\"type\":\"LegendItem\"},{\"attributes\":{\"fill_alpha\":{\"value\":0.1},\"fill_color\":{\"value\":\"#1f77b3\"},\"line_alpha\":{\"value\":0.1},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"2126\",\"type\":\"Circle\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"2109\"},{\"id\":\"2110\"},{\"id\":\"2111\"},{\"id\":\"2112\"},{\"id\":\"2113\"},{\"id\":\"2114\"}]},\"id\":\"2116\",\"type\":\"Toolbar\"},{\"attributes\":{},\"id\":\"2114\",\"type\":\"HelpTool\"}],\"root_ids\":[\"2092\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"f4b27cab-87ea-4741-b2d4-17e420ac29d2\",\"root_ids\":[\"2092\"],\"roots\":{\"2092\":\"b47a96c9-a9e6-4f9f-95a1-460405886249\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "2092"
}
},
"output_type": "display_data"
}
],
"source": [
"p = bokeh_catplot.ecdf(\n",
" np.diff(df['time (ms)'].values),\n",
" x_axis_label='time between acquisitions (ms)',\n",
")\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Indeed, this is what we get!"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### A primitive app with graphics\n",
"\n",
"While control with buttons is useful, we would like to have a live plot displayed. We can do this using techniques we have learned so far in our dashboarding experience. We can make a function to produce a plot of the voltage trace over time and link it to the widget that gets updated by the periodic callback (in this case the `received_text` widget).\n",
"\n",
"We'll start by making fresh widgets and link them to the appropriate callbacks."
]
},
{
"cell_type": "code",
"execution_count": 29,
"metadata": {},
"outputs": [],
"source": [
"acquire_toggle = pn.widgets.Toggle(\n",
" name=\"ACQUIRE\", value=False, button_type=\"success\", width=100,\n",
")\n",
"\n",
"stop_button = pn.widgets.Button(name=\"STOP\", button_type=\"danger\", width=100)\n",
"\n",
"received_text = pn.widgets.StaticText(\n",
" name=\"Data points received\", value=str(0)\n",
")\n",
"\n",
"status_text = pn.widgets.StaticText(\n",
" name=\"Status\", value=\"Awaiting data acquisition.\"\n",
")\n",
"\n",
"acquire_watcher = acquire_toggle.param.watch(stream_control, 'value')\n",
"stop_button.on_click(shutdown_and_save)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Because we are live plotting, and we need to re-render a plot each time we trigger the periodic callback, we will set it up with a half-second period. Otherwise, the plotting cannot keep up with the pace of the periodic updates."
]
},
{
"cell_type": "code",
"execution_count": 30,
"metadata": {},
"outputs": [],
"source": [
"# Periodic callback\n",
"pc = received_text.add_periodic_callback(daq_stream, period=500)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Next, we'll make our plotting function and link it to the `received_text` widget using a `@pn.depends` decorator as we did in the [dashboarding lesson](l29_dashboards.ipynb). Recall that the `received_text` widget will get a periodic callback, so it will get updated every time the callback.\n",
"\n",
"When we make the plot, we will only display the last 400 points, so the plot will roll along with the more updated data as opposed to scrunching the whole signal."
]
},
{
"cell_type": "code",
"execution_count": 31,
"metadata": {},
"outputs": [],
"source": [
"@pn.depends(received_text.param.value)\n",
"def plot_voltage(dummy_arg):\n",
" p = bokeh.plotting.figure(\n",
" frame_height=175,\n",
" frame_width=500,\n",
" x_axis_label='time (s)',\n",
" y_axis_label='voltage (V)',\n",
" y_range=[-0.2, 5.2],\n",
" )\n",
" p.x_range.range_padding = 0\n",
" \n",
" try:\n",
" t = np.concatenate(time_ms) / 1000\n",
" V = np.concatenate(voltage)\n",
" ind = -min(len(t), 400)\n",
" t = t[ind:]\n",
" V = V[ind:]\n",
" except:\n",
" t = []\n",
" V = []\n",
" \n",
" p.line(t, V)\n",
" \n",
" return p"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Now we can open up a serial connection and display our app!"
]
},
{
"cell_type": "code",
"execution_count": 32,
"metadata": {},
"outputs": [
{
"data": {},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.holoviews_exec.v0+json": "",
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
"
\n",
"
\n",
""
],
"text/plain": [
"Column\n",
" [0] Row\n",
" [0] Column\n",
" [0] Toggle(button_type='success', name='ACQUIRE', width=100)\n",
" [1] Button(button_type='danger', name='STOP', width=100)\n",
" [1] Spacer(width=15)\n",
" [2] Column\n",
" [0] StaticText(name='Data points received', value='0')\n",
" [1] StaticText(name='Status', value='Awaiting data a...)\n",
" [1] Spacer(height=15)\n",
" [2] ParamFunction(function)"
]
},
"execution_count": 32,
"metadata": {
"application/vnd.holoviews_exec.v0+json": {
"id": "2275"
}
},
"output_type": "execute_result"
}
],
"source": [
"arduino = open_arduino(port)\n",
"\n",
"pn.Column(\n",
" pn.Row(\n",
" pn.Column(acquire_toggle, stop_button),\n",
" pn.Spacer(width=15),\n",
" pn.Column(received_text, status_text),\n",
" ),\n",
" pn.Spacer(height=15),\n",
" plot_voltage,\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Having the live plot is nice, but we of course still want all of the data collected from the device. That is still available, as it was written to disk. We can still load it in and plot the entire time series."
]
},
{
"cell_type": "code",
"execution_count": 33,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"518056f2-8d76-47e7-a1c8-1c63877c593f\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"5521\"}],\"center\":[{\"id\":\"5524\"},{\"id\":\"5528\"}],\"frame_height\":175,\"frame_width\":500,\"left\":[{\"id\":\"5525\"}],\"renderers\":[{\"id\":\"5546\"}],\"title\":{\"id\":\"5593\"},\"toolbar\":{\"id\":\"5536\"},\"x_range\":{\"id\":\"5513\"},\"x_scale\":{\"id\":\"5517\"},\"y_range\":{\"id\":\"5515\"},\"y_scale\":{\"id\":\"5519\"}},\"id\":\"5512\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{},\"id\":\"5530\",\"type\":\"WheelZoomTool\"},{\"attributes\":{},\"id\":\"5595\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"overlay\":{\"id\":\"5535\"}},\"id\":\"5531\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"5532\",\"type\":\"SaveTool\"},{\"attributes\":{},\"id\":\"5601\",\"type\":\"UnionRenderers\"},{\"attributes\":{},\"id\":\"5533\",\"type\":\"ResetTool\"},{\"attributes\":{\"range_padding\":0},\"id\":\"5513\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"5534\",\"type\":\"HelpTool\"},{\"attributes\":{\"data\":{\"x\":{\"__ndarray__\":\"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\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[808]},\"y\":{\"__ndarray__\":\"zjnnnHPO+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P84555xzzvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P84555xzzvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P84555xzzvk/uummm266+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P84555xzzvk/zjnnnHPO+T+66aabbrr5P7rppptuuvk/uummm266+T+66aabbrr5P1ZZZZVVVvk/Lbnkkksu+T9mmGGGGWb4PxJHHHHEEfc/MsUUU0wx9T+hgw466KDzP7HCCiussPI/OuKII4448j8lkkgiiSTyP6yxxhprrPE/RBBBBBFE8D+QPfbYY4/tP1A88cQTT+w/UDzxxBNP7D9QPPHEE0/sP1A88cQTT+w/UDzxxBNP7D9QPPHEE0/sPyeccMIJJ+w/r7vuuuuu6z9fe+21117rP7/66quvvuo/fvnll19+6T+ed955553nP/XUU0899eQ/ddJJJ5104j+onnrqqafeP7XYYostttg/5JBDDjnk0D8HHnjggQeuP4cbbrjhhqs/hxtuuOGGqz8HHnjggQeuP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/hxtuuOGGqz+HG2644YarP4cbbrjhhqs/Bx544IEHrj+100477bTTP9hbb7311ts/hBFGGGGE4T8ttNBCCy3kPyaXXHLJJec/zjnnnHPO6T9onXXWWWftPxxwwAEHHPA/DDHEEEMM8T864ogjjjjyP3njjTfeePM/ueSSSy659D+GFlpooYX2P1JIIYUUUvg/Lbnkkksu+T8zyiijjDL6P9NKK6200vo/SyuttNJK+z+ba6655pr7P+urr7766vs/FEwwwQQT/D8UTDDBBBP8PxRMMMEEE/w/FEwwwQQT/D8UTDDBBBP8PxRMMMEEE/w/FEwwwQQT/D8UTDDBBBP8PxRMMMEEE/w/FEwwwQQT/D8UTDDBBBP8P+urr7766vs/r7vuuuuu+z+vu+666677P5trrrnmmvs/m2uuueaa+z+GG2644Yb7P4Ybbrjhhvs/hhtuuOGG+z90yy233HL7P4Ybbrjhhvs/dMstt9xy+z/XW2+99db7P2OMMcYYY/w/RQ455JBD/j/QQAMNNNAAQNpiiy222AJAhxxyyCGHBECMLbbYYosFQKqlllpqqQVAqqWWWmqpBUCfffbZZ58FQHfddddddwVAYo011lhjBUBYZZVVVlkFQBJNNNFEEwVASyyxxBJLBECOM84444wDQLvqqquuugJAvwEHHHDAAUDkkEMOOeQAQOmff/755/8/qJ566qmn/j+PPfbYY4/9P4ssssgii/w/11tvvfXW+z9fe+211177P0srrbTSSvs/SyuttNJK+z9LK6200kr7P0srrbTSSvs/SyuttNJK+z+GG2644Yb7P1A88cQTT/w/yy233HLL/T866KCDDjoAQN9555133gFAFVNMMcUUA0AOPPDAAw8EQCaddNJJJwVA5ZVXXnnlBUA31lhjjTUGQED++OOPPwZAQP74448/BkBA/vjjjz8GQED++OOPPwZAN9ZYY401BkAhhhhiiCEGQPnll19++QVABA444IADBkC89dZbb70FQCaddNJJJwVAc8wxxxxzBEDJI4888sgDQO2yyy677AJAL7rooosuAkBJIYUUUkgBQE044YQTTgBA5I477rjj/j9mnXXWWWf9PxRMMMEEE/w/++qrr776+j+66aabbrr5P2aYYYYZZvg/rrbaaqut9j/ONNNMM830PxVTTDHFFPM/ddJJJ5108j910kknnXTyP4kiiiiiiPI/xRJLLLHE8j+hgw466KDzP7311ltvvfU/uummm266+T8HHnjggQf+P7vwwgsvvABA/PHHH3/8AUCSSiqppJICQKeaaqqppgJAnnLKKaecAkCecsopp5wCQJ5yyimnnAJAnnLKKaecAkCnmmqqqaYCQJ5yyimnnAJAnnLKKaecAkCJIooooogCQH/66aeffgJAddJJJ510AkBrqqmmmmoCQC+66KKLLgJAookmmmiiAUD44IMPPvgAQE044YQTTgBAW2+99dZb/z9ZXnnllVf+P2adddZZZ/0/77zzzjvv/D+yzDLLLLP8P5988sknn/w/n3zyySef/D+yzDLLLLP8P3rttddee/0/DC+88MIL/z966aWXXnoBQIMLLrjgggNATz311FNPBUCkjjrqqKMGQDvnnHPOOQdARA899NBDB0A755xzzjkHQEQPPfTQQwdAO+ecc845B0Axv/zyyy8HQCeXXHLJJQdACB988MEHB0Dhfvvtt98GQEommWSSSQZAvPXWW2+9BUAdddRRRx0FQGmkkUYaaQRA1EsvvfTSA0A988wzzzwDQMQSSyyxxAJAJZJIIokkAkCiiSaaaKIBQD755JNPPgFAIIEEEkggAUAggQQSSCABQCCBBBJIIAFAIIEEEkggAUA00UQTTTQBQFxxxRVXXAFA88knn3zyAUB544033ngDQIEFFlhggQVAvO++++67B0BlkkkmmWQKQG200UYbbQxAhRVWWGGFDUCkjTbaaKMNQKSNNtpoow1Ajz322GOPDUBpnXXWWWcNQFJNNdVUUw1AFl100UUXDUCyzDLLLLMMQJprrrnmmgtAcLrppptuCkCSSSaZZJIJQGaYYYYZZghAHG+88cYbB0D55ZdffvkFQLnkkksuuQRAjjPOOOOMA0CnmmqqqaYCQMopp5xyygFA5JBDDjnkAEAnmGCCCSYAQG2uueaaa/4/22yzzTbb/D8PO+ywww77P/LII4888vg/rrbaaqut9j9VVFFFFVX0P9liiy222PI/iSKKKKKI8j+JIooooojyP7HCCiussPI/eeONN9548z/llVdeeeX1PzvssMMOO/w/hRFGGGGEAUB99NFHH30EQCeXXHLJJQdAYIEFFlhgCUBbaqmllloKQGWSSSaZZApAZZJJJplkCkBlkkkmmWQKQFBCCSWUUApANMooo4wyCkDYYYcddtgJQBpppJFGGglAvO++++67B0CGFlpooYUGQFhllVVWWQVAQQQRRBBBBEBRQw011FADQIkiiiiiiAJA6KGHHnroAUBwwQUXXHABQAMJJJBAAgFAbLDBBhtsAECXX3755Zf/P4D++eeff/4/QP30008//T+vu+666677P7rppptuuvk/Pvjggw8++D/aZ5999tn3P8YXX3zxxfc/77fffvvt9z8ZaaSRRhr5PxZddNFFF/0/lFBCCSWUAEA64ogjjjgCQJ5yyimnnAJAp5pqqqmmAkCnmmqqqaYCQJ5yyimnnAJAkkoqqaSSAkBrqqmmmmoCQFJJJZVUUgFAl19++eWX/z+LLLLIIov8Px966KGHHvo/BRlkkEEG+T8FGWSQQQb5PwUZZJBBBvk/VllllVVW+T9fe+211177P0UOOeSQQ/4/iiiiiCKKAECOOeaYY44BQKKJJppoogFAookmmmiiAUCiiSaaaKIBQHrppZdeegFAKamkkkoqAUDB//7777//P0D99NNPP/0/++qrr776+j9CCSWUUEL5P95444033vg/3njjjTfe+D/eeOONN974PwUZZJBBBvk/9tlnn332+T+PPfbYY4/9P2OIIYYYYgBABxpooIEGAkCDCy644IIDQOGEE0444QRAGF544YUXBkDDBhtssMEGQAgffPDBBwdACB988MEHB0D99ttvv/0GQOF+++233wZAuN566623BkCZZpppppkGQNFFF1100QVAr7zyyiuvBECXW2655ZYDQKeaaqqppgJA6KGHHnroAUCXYYYZZpgBQIURRhhhhAFAeumll156AUB66aWXXnoBQHDBBRdccAFAeumll156AUBwwQUXXHABQHDBBRdccAFAcMEFF1xwAUBwwQUXXHABQHrppZdeegFA33nnnXfeAUCXW2655ZYDQFhllVVWWQVAaJ555plnBkB87rnnnnsGQHLGGWeccQZAaJ555plnBkBUTjnllFMGQFROOeWUUwZAs80222yzBUAkjDDCCCMEQOSKK6644gJAnnLKKaecAkAcaqihhhoCQKyxxhprrAFA7rjjjjvuAEAWWWSRRRYBQAMJJJBAAgFA5JBDDjnkAEDQQAMNNNAAQMYYY4wxxgBAu/DCCy+8AECyyCKLLLIAQLLIIosssgBAssgiiyyyAEC78MILL7wAQLvwwgsvvABAxhhjjDHGAEDGGGOMMcYAQO6444477gBAcMEFF1xwAUDom2+++eYDQHzuueeeewZAPvjggw8+CECOOOKII44IQJlgggkmmAhAjjjiiCOOCECed955550HQGaYYYYZZghAddddd911B0BonnnmmWcGQAkllFBCCQVAl1tuueWWA0BgggkmmGACQHrppZdeegFA0EADDTTQAEBYYIEFFlgAQDrooIMOOgBAMMAAAwwwAEAwwAADDDAAQEQQQQQRRABA2mijjTbaAEAlkkgiiSQCQOSKK6644gJAKaOMMsooA0Apo4wyyigDQCmjjDLKKANAFVNMMcUUA0DkiiuuuOICQDriiCOOOAJAKamkkkoqAUAHIIAAAggAQKKNNtpoo/0/66uvvvrq+z+ba6655pr7P6+77rrrrvs/r7vuuuuu+z/vvPPOO+/8P2ywwQYbbABAzjrrrLPOAkCHHHLIIYcEQO+999577wVAkD766KOPBkDDBhtssMEGQLjeeuuttwZArbbaaqutBkCkjjrqqKMGQJlmmmmmmQZAmWaaaaaZBkByxhlnnHEGQDfWWGONNQZARhVVVFFFBUBLLLHEEksEQJdbbrnllgNAKaOMMsooA0DOOuuss84CQLHCCiussAJAp5pqqqmmAkCecsopp5wCQJ5yyimnnAJAnnLKKaecAkCecsopp5wCQKeaaqqppgJAp5pqqqmmAkDaYostttgCQM4666yzzgJAzjrrrLPOAkDkiiuuuOICQD3zzDPPPANA4YQTTjjhBECGFlpooYUGQIonnnjiiQdA0T///PPPB0DRP//8888HQNpnn3322QdA0T///PPPB0CKJ5544okHQPTOO++88wZAxx133HHHBUBLLLHEEksEQCmjjDLKKANAJZJIIokkAkBwwQUXXHABQNpoo4022gBAgQACCCCAAEAwwAADDDAAQHG//fbbb/8/qJ566qmn/j8bbrjhhhv+PwceeOCBB/4/G2644YYb/j8bbrjhhhv+P1leeeWVV/4/gP75559//j+67rrrrrv+P0QQQQQRRABAa6qppppqAkBffPHFF18EQIEFFlhggQVAjC222GKLBUButdVWW20FQCaddNJJJwVALbTQQgstBEDkiiuuuOICQKyxxhprrAFAbLDBBhtsAED43nvvvff+P99999133/0/sswyyyyz/D90yy233HL7P+KJJ5544vk/Zphhhhlm+D/CBhtssMH2P9FFF1100fU/RRVVVFFF9T+55JJLLrn0P9xzzz333PM/UEMNNdRQ8z8po4wyyijzPxVTTDHFFPM/KaOMMsoo8z8VU0wxxRTzPymjjDLKKPM/KaOMMsoo8z8888wzzzzzPzzzzDPPPPM/3HPPPffc8z8ml1xyySX3P1JNNdVUU/0/l2GGGWaYAUBRQw011FADQJdbbrnllgNAl1tuueWWA0A988wzzzwDQPPJJ5988gFAl19++eWX/z8A/O+///77P0IJJZRQQvk/Jpdccskl9z9yxhlnnHH2P3LGGWeccfY/X3bZZZdd9j9yxhlnnHH2PzrnnHPOOfc/4oknnnji+T/bbLPNNtv8PxtuuOGGG/4/ba655ppr/j9trrnmmmv+PxtuuOGGG/4/oo022mij/T8PO+ywww77PwMIIIAAAvg/ggUWWGCB9T8ttNBCCy30P/LDDz/88PM/8sMPP/zw8z/yww8//PDzPy200EILLfQ/5ZVXXnnl9T9qqaWWWmr5PxZddNFFF/0/dthhhx12AEDzySeffPIBQBxqqKGGGgJA1FFHHXXUAUCiiSaaaKIBQAcggAACCABAFEwwwQQT/D8DCCCAAAL4PxlkkEEGGfQ/bLDBBhts8D8feuihhx7qP7XTTjvttOM/6Z9//vnn3z+43XbbbbfdPxZddNFFF90/Fl100UUX3T9onXXWWWfdPwceeOCBB94/+N5777333j+EEUYYYYThP8YXX3zxxec/gAACCCCA8D8yxRRTTDH1PwUZZJBBBvk/J5xwwgkn/D/LLbfccsv9PxtuuOGGG/4/L7744osv/j8HHnjggQf+P6KNNtpoo/0/oo022mij/T967bXXXnv9PxZddNFFF/0/m2uuueaa+z9WWWWVVVb5P/3222+//fY/bbXVVltt9T/yww8//PDzP+2yyy677PI/scIKK6yw8j+xwgorrLDyP8USSyyxxPI/FVNMMcUU8z/ONNNMM830P0IJJZRQQvk/Fl100UUX/T8if/zxxx//P9NPP/300/8/008//fTT/z/TTz/99NP/P9NPP/300/8/l19++eWX/z9bb7311lv/P1tvvfXWW/8/0D777LPP/j8bbrjhhhv+PyuttNJKK/0/APzvv//++z8jiyyyyCL7P9NKK6200vo/q6qqqqqq+j+DCiqooIL6P4MKKqiggvo/cLrppptu+j+DCiqooIL6P3C66aabbvo/cLrppptu+j+DCiqooIL6P/vqq6+++vo/5I477rjj/j+SSiqppJICQDzttNNOOwVAJ5dccsklB0Czxx577LEHQNE///zzzwdAvO++++67B0DGF1988cUHQLzvvvvuuwdAnnfeeeedB0Bihx122GEHQKSOOuqoowZATz311FNPBUD766+//voDQOSKK6644gJA/PHHH3/8AUA++eSTTz4BQIEAAggggABAJ5hgggkmAECXX3755Zf/PyJ//PHHH/8/gP75559//j8HHnjggQf+P2adddZZZ/0/Fl100UUX/T/vvPPOO+/8P5988sknn/w/UDzxxBNP/D8UTDDBBBP8PwD877///vs/J5xwwgkn/D+LLLLIIov8PzDAAAMMMABA6KGHHnroAUApo4wyyigDQKurrrrqqgNA1EsvvfTSA0Dyww8//PADQHPMMccccwRA5ZVXXnnlBUCOOOKII44IQH3zzTfffAtAG2644YYbDkBll1122WUPQIMPPvjggw9Aeuedd955D0BIH3300UcPQPLNN9988w1ADzvssMMOC0AWWGCBBRYIQB111FFHHQVAAQMMMMAAA0AHGmiggQYCQPPJJ5988gFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQPPJJ5988gFAJZJIIokkAkBvu+22224DQGKNNdZYYwVAN9ZYY401BkAsrrjiiisGQOWVV1555QVA11xzzTXXBEDEEkssscQCQGywwQYbbABAsswyyyyz/D9WWWWVVVb5P++333777fc/iieeeOKJ9z9111133XX3P3XXXXfddfc/nnfeeeed9z+OOOKII474P5daaqmllvo/wwsvvPDC+z8nnHDCCSf8PzvssMMOO/w/O+ywww47/D8nnHDCCSf8P8MLL7zwwvs/VllllVVW+T8hhhhiiCH2P9liiy222PI/wf/++++/7z9A/fTTTz/tP8ccc8wxx+w/xxxzzDHH7D/HHHPMMcfsP2idddZZZ+0/qJ566qmn7j+78MILL7zwP5VVVllllfU/cLrppptu+j+UTjrppJP+P8YYY4wxxgBArLHGGmusAUARQgghhBACQBFCCCGEEAJABxpooIEGAkDooYceeugBQN9555133gFA33nnnXfeAUDUUUcdddQBQN9555133gFA1FFHHXXUAUC/AQcccMABQOihhx566AFA88knn3zyAUDooYceeugBQOihhx566AFA6KGHHnroAUDzySeffPIBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDzySeffPIBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDzySeffPIBQPPJJ5988gFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA88knn3zyAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUDooYceeugBQOihhx566AFA6KGHHnroAUA=\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[808]}},\"selected\":{\"id\":\"5600\"},\"selection_policy\":{\"id\":\"5601\"}},\"id\":\"5543\",\"type\":\"ColumnDataSource\"},{\"attributes\":{\"axis\":{\"id\":\"5521\"},\"ticker\":null},\"id\":\"5524\",\"type\":\"Grid\"},{\"attributes\":{\"axis\":{\"id\":\"5525\"},\"dimension\":1,\"ticker\":null},\"id\":\"5528\",\"type\":\"Grid\"},{\"attributes\":{},\"id\":\"5526\",\"type\":\"BasicTicker\"},{\"attributes\":{\"axis_label\":\"voltage (V)\",\"formatter\":{\"id\":\"5597\"},\"ticker\":{\"id\":\"5526\"}},\"id\":\"5525\",\"type\":\"LinearAxis\"},{\"attributes\":{},\"id\":\"5597\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"5600\",\"type\":\"Selection\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"5535\",\"type\":\"BoxAnnotation\"},{\"attributes\":{\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"5544\",\"type\":\"Line\"},{\"attributes\":{\"source\":{\"id\":\"5543\"}},\"id\":\"5547\",\"type\":\"CDSView\"},{\"attributes\":{},\"id\":\"5519\",\"type\":\"LinearScale\"},{\"attributes\":{\"line_alpha\":0.1,\"line_color\":\"#1f77b4\",\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}},\"id\":\"5545\",\"type\":\"Line\"},{\"attributes\":{},\"id\":\"5517\",\"type\":\"LinearScale\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"5529\"},{\"id\":\"5530\"},{\"id\":\"5531\"},{\"id\":\"5532\"},{\"id\":\"5533\"},{\"id\":\"5534\"}]},\"id\":\"5536\",\"type\":\"Toolbar\"},{\"attributes\":{},\"id\":\"5522\",\"type\":\"BasicTicker\"},{\"attributes\":{\"axis_label\":\"time (s)\",\"formatter\":{\"id\":\"5595\"},\"ticker\":{\"id\":\"5522\"}},\"id\":\"5521\",\"type\":\"LinearAxis\"},{\"attributes\":{\"data_source\":{\"id\":\"5543\"},\"glyph\":{\"id\":\"5544\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"5545\"},\"selection_glyph\":null,\"view\":{\"id\":\"5547\"}},\"id\":\"5546\",\"type\":\"GlyphRenderer\"},{\"attributes\":{},\"id\":\"5515\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"5529\",\"type\":\"PanTool\"},{\"attributes\":{\"text\":\"\"},\"id\":\"5593\",\"type\":\"Title\"}],\"root_ids\":[\"5512\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"518056f2-8d76-47e7-a1c8-1c63877c593f\",\"root_ids\":[\"5512\"],\"roots\":{\"5512\":\"9869bb70-9d25-4a0a-af27-d79022ce7347\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "5512"
}
},
"output_type": "display_data"
}
],
"source": [
"df = pd.read_csv('test_potentiometer_daq.csv')\n",
"\n",
"p = bokeh.plotting.figure(\n",
" x_axis_label='time (s)',\n",
" y_axis_label='voltage (V)',\n",
" frame_height=175,\n",
" frame_width=500,\n",
")\n",
"p.x_range.range_padding = 0\n",
"\n",
"p.line(df['time (ms)'] / 1000, df['voltage (V)'])\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"And again, we should check to make sure our timing is working out ok."
]
},
{
"cell_type": "code",
"execution_count": 34,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"\n",
"\n",
"\n",
"\n",
"\n",
"\n",
" \n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/javascript": [
"(function(root) {\n",
" function embed_document(root) {\n",
" \n",
" var docs_json = {\"079dddf2-c6e3-465e-b388-aaa12e7a13e6\":{\"roots\":{\"references\":[{\"attributes\":{\"below\":[{\"id\":\"5665\"}],\"center\":[{\"id\":\"5668\"},{\"id\":\"5672\"},{\"id\":\"5702\"}],\"left\":[{\"id\":\"5669\"}],\"plot_height\":300,\"plot_width\":400,\"renderers\":[{\"id\":\"5691\"}],\"title\":{\"id\":\"5693\"},\"toolbar\":{\"id\":\"5680\"},\"x_range\":{\"id\":\"5657\"},\"x_scale\":{\"id\":\"5661\"},\"y_range\":{\"id\":\"5659\"},\"y_scale\":{\"id\":\"5663\"}},\"id\":\"5656\",\"subtype\":\"Figure\",\"type\":\"Plot\"},{\"attributes\":{},\"id\":\"5697\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{\"fill_alpha\":{\"value\":0.1},\"fill_color\":{\"value\":\"#1f77b3\"},\"line_alpha\":{\"value\":0.1},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"5690\",\"type\":\"Circle\"},{\"attributes\":{\"fill_color\":{\"value\":\"#1f77b3\"},\"line_color\":{\"value\":\"#1f77b3\"},\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"__ECDF\"}},\"id\":\"5689\",\"type\":\"Circle\"},{\"attributes\":{\"axis\":{\"id\":\"5669\"},\"dimension\":1,\"ticker\":null},\"id\":\"5672\",\"type\":\"Grid\"},{\"attributes\":{},\"id\":\"5674\",\"type\":\"WheelZoomTool\"},{\"attributes\":{\"axis_label\":\"ECDF\",\"formatter\":{\"id\":\"5697\"},\"ticker\":{\"id\":\"5670\"}},\"id\":\"5669\",\"type\":\"LinearAxis\"},{\"attributes\":{},\"id\":\"5700\",\"type\":\"Selection\"},{\"attributes\":{},\"id\":\"5673\",\"type\":\"PanTool\"},{\"attributes\":{},\"id\":\"5701\",\"type\":\"UnionRenderers\"},{\"attributes\":{\"data_source\":{\"id\":\"5687\"},\"glyph\":{\"id\":\"5689\"},\"hover_glyph\":null,\"muted_glyph\":null,\"nonselection_glyph\":{\"id\":\"5690\"},\"selection_glyph\":null,\"view\":{\"id\":\"5692\"}},\"id\":\"5691\",\"type\":\"GlyphRenderer\"},{\"attributes\":{\"axis_label\":\"time between acquisitions (ms)\",\"formatter\":{\"id\":\"5695\"},\"ticker\":{\"id\":\"5666\"}},\"id\":\"5665\",\"type\":\"LinearAxis\"},{\"attributes\":{},\"id\":\"5676\",\"type\":\"SaveTool\"},{\"attributes\":{\"source\":{\"id\":\"5687\"}},\"id\":\"5692\",\"type\":\"CDSView\"},{\"attributes\":{\"axis\":{\"id\":\"5665\"},\"ticker\":null},\"id\":\"5668\",\"type\":\"Grid\"},{\"attributes\":{\"bottom_units\":\"screen\",\"fill_alpha\":0.5,\"fill_color\":\"lightgrey\",\"left_units\":\"screen\",\"level\":\"overlay\",\"line_alpha\":1.0,\"line_color\":\"black\",\"line_dash\":[4,4],\"line_width\":2,\"right_units\":\"screen\",\"top_units\":\"screen\"},\"id\":\"5679\",\"type\":\"BoxAnnotation\"},{\"attributes\":{},\"id\":\"5657\",\"type\":\"DataRange1d\"},{\"attributes\":{},\"id\":\"5678\",\"type\":\"HelpTool\"},{\"attributes\":{\"data\":{\"__ECDF\":{\"__ndarray__\":\"DToPsKOk3z9Diw8ZZ01UP5lJKBfxuN8/Q4sPGWdNZD/kUJelGnRuPyRZQX4+zd8/Q4sPGWdNdD+vaFrli+HfPxRuU9/AYHk/OnhzTNn13z/kUJelGnR+P+NDxlkTBeA/25ntNbrDgT+oy1INOg/gP0OLDxlnTYQ/blPfwGAZ4D+rfDH8E9eGPzTba3SHI+A/FG5T38BgiT/5Yvgnri3gP3xfdcJt6os/v+qE29Q34D/kUJelGnSOP4VyEY/7QeA/JqFcxON+kD9K+p1CIkzgP9uZ7TW6w5E/EIIq9khW4D+Pkn6nkAiTP0OLDxlnTZQ/1Qm3qW9g4D/3g6CKPZKVP5uRQ12WauA/q3wx/BPXlj/g+6oTblPvP191wm3qG5g/YRnQEL104D8UblPfwGCZPyahXMTjfuA/yGbkUJelmj/sKOl3CongP3xfdcJt6ps/srB1KzGT4D8wWAY0RC+dP3c4At9XneA/5FCXpRp0nj89wI6SfqfgP5lJKBfxuJ8/A0gbRqWx4D8moVzE436gP8jPp/nLu+A/gB0l/U4hoT+OVzSt8sXgP9uZ7TW6w6E/U9/AYBnQ4D81FrZuJWaiP4+SfqeQCKM/GWdNFEDa4D/pDkfg+6qjP9/u2cdm5OA/Q4sPGWdNpD+kdmZ7je7gP50H2FHS76Q/av7yLrT44D/3g6CKPZKlPzCGf+LaAuE/UQBpw6g0pj/1DQyWAQ3hP6t8MfwT16Y/u5WYSSgX4T8F+fk0f3mnP4AdJf1OIeE/X3XCbeobqD9GpbGwdSvhP7rxiqZVvqg/DC0+ZJw14T8UblPfwGCpP9G0yhfDP+E/buobGCwDqj+XPFfL6UnhP8hm5FCXpao/IuOsiQJIqz9dxON+EFThP3xfdcJt6qs/IkxwMjde4T/W2z372IysP+jT/OVdaOE/MFgGNEQvrT+uW4mZhHLhP4rUzmyv0a0/c+MVTat84T/kUJelGnSuPzlrogDShuE//vIutPiQ4T/EertnH5vhPz7NX96FFq8/igJIG0al4T+ZSSgX8bivP0+K1M5sr+E/+WL4J64tsD8VEmGCk7nhPyahXMTjfrA/25ntNbrD4T9T38BgGdCwP6AheungzeE/gB0l/U4hsT+uW4mZhHKxP2apBp0H2OE/25ntNbrDsT8rMZNQLuLhPwjYUdLvFLI/8bgfBFXs4T81FrZuJWayP7dArLd79uE/YlQaC1u3sj98yDhrogDiP4+SfqeQCLM/QlDFHskK4j+80OJDxlmzPwjYUdLvFOI/6Q5H4Puqsz/NX96FFh/iPxZNq3wx/LM/k+dqOT0p4j9Diw8ZZ020P1lv9+xjM+I/cMlztZyetD8e94Ogij3iP50H2FHS77Q/5H4QVLFH4j/KRTzuB0G1P/eDoIo9krU/qQadB9hR4j8kwgQnc+O1P2+OKbv+W+I/NRa2biVm4j/6nUIiTHDiP1EAacOoNLY/wCXP1XJ64j9+Ps1f3oW2P4atW4mZhOI/q3wx/BPXtj9LNeg8wI7iP9i6lZhJKLc/Eb108OaY4j8F+fk0f3m3P9ZEAaQNo+I/Mjde0bTKtz+czI1XNK3iP191wm3qG7g/YlQaC1u34j+NsyYKIG24Pyfcpr6BweI/uvGKplW+uD/tYzNyqMviP+cv70KLD7k/s+u/Jc/V4j8UblPfwGC5P0Gst3v2sbk/eHNM2fXf4j9u6hsYLAO6Pz772Iwc6uI/myiAtGFUuj8Dg2VAQ/TiP8hm5FCXpbo/yQry82n+4j/1pEjtzPa6P4+SfqeQCOM/IuOsiQJIuz9UGgtbtxLjP08hESY4mbs/GqKXDt4c4z98X3XCbeq7P+ApJMIEJ+M/qZ3ZXqM7vD+lsbB1KzHjP9bbPfvYjLw/azk9KVI74z8xwcnceEXjP/ZIVpCfT+M/Axqilw7evD+80OJDxlnjPzBYBjREL70/gVhv9+xj4z9dlmrQeYC9P4rUzmyv0b0/R+D7qhNu4z+3EjMJ5SK+Pw1oiF46eOM/5FCXpRp0vj/S7xQSYYLjPxGP+0FQxb4/mHehxYeM4z8+zV/ehRa/P17/LXmuluM/bAvEertnvz8jh7os1aDjP5lJKBfxuL8/6Q5H4Puq4z/jQ8ZZEwXAP66W05MiteM/+WL4J64twD90HmBHSb/jPxCCKvZIVsA/Oqbs+m/J4z8moVzE437AP/8tea6W0+M/PcCOkn6nwD/FtQVivd3jP1PfwGAZ0MA/av7yLrT4wD+LPZIV5OfjP4AdJf1OIcE/UMUeyQry4z+XPFfL6UnBPxZNq3wx/OM/rluJmYRywT/c1DcwWAbkP8R6u2cfm8E/poM3x5Rd7z/bme01usPBP6FcxON+EOQ/8bgfBFXswT9n5FCXpRrkPwjYUdLvFMI/LGzdSswk5D8e94Ogij3CP/Lzaf7yLuQ/NRa2biVmwj+4e/axGTnkP0s16DzAjsI/fQODZUBD5D9iVBoLW7fCP0OLDxlnTeQ/eHNM2fXfwj+Pkn6nkAjDPwkTnMyNV+Q/pbGwdSsxwz/OmiiAtGHkP7zQ4kPGWcM/lCK1M9tr5D/S7xQSYYLDP1mqQecBduQ/6Q5H4Puqwz8fMs6aKIDkP/8tea6W08M/5blaTk+K5D8WTat8MfzDP6pB5wF2lOQ/LGzdSswkxD9wyXO1nJ7kP0OLDxlnTcQ/NlEAacOo5D9ZqkHnAXbEP/vYjBzqsuQ/cMlztZyexD/BYBnQEL3kP4fopYM3x8Q/h+ilgzfH5D+dB9hR0u/EP7QmCiBtGMU/bAvEertn7z/KRTzuB0HFP0xwMjde0eQ/4WRuvKJpxT8S+L7qhNvkP/eDoIo9ksU/139Lnqvl5D8Oo9JY2LrFP50H2FHS7+Q/JMIEJ3PjxT9jj2QF+fnkPzvhNvUNDMY/KBfxuB8E5T9RAGnDqDTGP+6efWxGDuU/aB+bkUNdxj+0JgogbRjlP34+zV/ehcY/ea6W05Mi5T+VXf8tea7GPz82I4e6LOU/q3wx/BPXxj8Evq864TblP8KbY8qu/8Y/ykU87gdB5T/YupWYSSjHP+/Zx2bkUMc/kM3IoS5L5T8F+fk0f3nHP1VVVVVVVeU/HBgsAxqixz8b3eEIfF/lPzI3XtG0ysc/4WRuvKJp5T+m7PpvyXPlP2x0hyPwfeU/SVaQn0/zxz8x/BPXFojlP191wm3qG8g/94Ogij2S5T92lPQ7hUTIP70LLT5knOU/jbMmCiBtyD+Ck7nxiqblP6PSWNi6lcg/SBtGpbGw5T+68YqmVb7IPw6j0ljYuuU/0BC9dPDmyD/TKl8M/8TlP5my678lz+U/Xzp4c0zZ5T/nL+9Ciw/JP/1OIREmOMk/JMIEJ3Pj5T8UblPfwGDJP+pJkdqZ7eU/Ko2FrVuJyT+v0R2OwPflP0Gst3v2sck/dVmqQecB5j9Xy+lJkdrJPzvhNvUNDOY/buobGCwDyj8AacOoNBbmP4QJTubGK8o/MZNQLuJx7z+bKIC0YVTKP8bwT1xbIOY/sUeygvx8yj+MeNwPgirmP8hm5FCXpco/UQBpw6g05j/ehRYfMs7KPxeI9XbPPuY/9aRI7cz2yj/cD4Iq9kjmPwvEertnH8s/opcO3hxT5j8i46yJAkjLPzgC31edcMs/aB+bkUNd5j8tpydFamfmP/MutPiQceY/TyERJjiZyz+5tkCst3vmP2ZAQ/TSwcs/fj7NX96F5j98X3XCberLP0TGWRMFkOY/k36nkAgTzD8KTubGK5rmP6md2V6jO8w/z9VyelKk5j/AvAstPmTMP5Vd/y15ruY/1ts9+9iMzD/3Gt3hCHzvP+36b8lztcw/WuWL4Z+45j8DGqKXDt7MPyBtGJXGwuY/GjnUZakGzT/m9KRI7czmPzBYBjREL80/q3wx/BPX5j9HdzgC31fNP12WatB5gM0/cQS+rzrh5j90tZyeFKnNPzeMSmNh6+Y/itTObK/RzT/8E9cWiPXmP8KbY8qu/+Y/hyPwfdUJ5z+h8wA7SvrNP02rfDH8E+c/txIzCeUizj8TMwnlIh7nP84xZdd/S84/2LqVmEko5z/kUJelGnTOP55CIkxwMuc/+2/Jc7Wczj9kyq7/ljznPxGP+0FQxc4/KVI7s71G5z8ori0Q6+3OP+/Zx2bkUOc/tWFUGgtb5z966eDNMWXnPz7NX96FFs8/QHFtgVhv5z9V7JGsID/PP2wLxHq7Z88/Bfn5NH955z+CKvZIVpDPP8uAhuilg+c/mUkoF/G4zz+RCBOczI3nP69oWuWL4c8/VpCfT/OX5z/jQ8ZZEwXQPxwYLAMaouc/4p+4tkCs5z+nJ0VqZ7bnP25T38BgGdA/ba/RHY7A5z/5Yvgnri3QPzI3XtG0yuc/hXIRj/tB0D/4vuqE29TnPxCCKvZIVtA/vkZ3OALf5z+bkUNdlmrQP4POA+wo6ec/JqFcxON+0D9JVpCfT/PnP7KwdSsxk9A/D94cU3b95z/UZakGnQfoPz3AjpJ+p9A/mu01usMR6D/Iz6f5y7vQP191wm3qG+g/U9/AYBnQ0D8l/U4hESboP9/u2cdm5NA/64Tb1Dcw6D9q/vIutPjQP7AMaIheOug/9Q0MlgEN0T92lPQ7hUToP4AdJf1OIdE/PByB76tO6D8MLT5knDXRP7yiaZUvhu8/lzxXy+lJ0T8BpA2j0ljoPyJMcDI3XtE/xyuaVvli6D+uW4mZhHLRP42zJgogbeg/OWuiANKG0T9SO7O9RnfoP8R6u2cfm9E/GMM/cW2B6D9PitTObK/RP9uZ7TW6w9E/3UrMJJSL6D9mqQadB9jRP6PSWNi6leg/aVrli+Gf6D8u4nE/CKroP/G4HwRV7NE/9Gn+8i606D98yDhrogDSP7rxiqZVvug/CNhR0u8U0j9/eRdafMjoP5Pnajk9KdI/RQGkDaPS6D8e94Ogij3SPwqJMMHJ3Og/qQadB9hR0j/QEL108OboPzUWtm4lZtI/lphJKBfx6D9bINbbPfvoPyGoYo9kBek/wCXP1XJ60j/nL+9Ciw/pP0s16DzAjtI/rLd79rEZ6T/WRAGkDaPSP2JUGgtbt9I/cj8Iqtgj6T/tYzNyqMvSPzjHlF3/Lek/eHNM2fXf0j/9TiERJjjpPwODZUBD9NI/w9atxExC6T+Pkn6nkAjTP4Iq9khWkO8/GqKXDt4c0z+IXjp4c0zpP6WxsHUrMdM/TubGK5pW6T8xwcnceEXTPxRuU9/AYOk/vNDiQ8ZZ0z/Z9d+S52rpP0fg+6oTbtM/n31sRg516T/S7xQSYYLTP2UF+fk0f+k/Xv8tea6W0z8qjYWtW4npP+kOR+D7qtM/SLKC/Hya7z90HmBHSb/TP/8tea6W09M/8BQSYYKT6T+LPZIV5OfTP7WcnhSpnek/Fk2rfDH80z97JCvIz6fpP6FcxON+ENQ/Qay3e/ax6T8sbN1KzCTUPwY0RC8dvOk/uHv2sRk51D/Mu9DiQ8bpP0OLDxlnTdQ/kkNdlmrQ6T9Xy+lJkdrpPx1Tdv235Ok/zpoogLRh1D/i2gKx3u7pP1mqQecBdtQ/qGKPZAX56T/luVpOT4rUP27qGxgsA+o/cMlztZye1D8zcqjLUg3qP/vYjBzqstQ/+fk0f3kX6j+H6KWDN8fUPxL4vuqE29Q/v4HBMqAh6j+dB9hR0u/UPw06D7CjpO8/KBfxuB8E1T+ECU7mxivqP7QmCiBtGNU/SpHame016j8/NiOHuizVPxAZZ00UQOo/ykU87gdB1T/VoPMAO0rqP1VVVVVVVdU/myiAtGFU6j/hZG68omnVP2CwDGiIXuo/bHSHI/B91T8mOJkbr2jqP+y/Jc/Vcuo/sUeygvx86j/3g6CKPZLVP3fPPjYjh+o/gpO58Yqm1T89V8vpSZHqPw6j0ljYutU/At9XnXCb6j+Zsuu/Jc/VPyTCBCdz49U/yGbkUJel6j+v0R2OwPfVP43ucAS+r+o/O+E29Q0M1j9Tdv235LnqP8bwT1xbINY/08GbY8qu7z9RAGnDqDTWPxn+iWsLxOo/3A+CKvZI1j/ehRYfMs7qP2gfm5FDXdY/pA2j0ljY6j/zLrT4kHHWP2qVL4Z/4uo/fj7NX96F1j8vHbw5puzqPwpO5sYrmtY/9aRI7cz26j+VXf8tea7WP7ss1aDzAOs/IG0YlcbC1j+ZSSgX8bjvP6t8MfwT19Y/gLRhVBoL6z83jEpjYevWP8KbY8qu/9Y/RjzuB0EV6z9Nq3wx/BPXPwvEertnH+s/2LqVmEko1z/RSwdvjinrP2TKrv+WPNc/l9OTIrUz6z/v2cdm5FDXP1xbINbbPes/eungzTFl1z8i46yJAkjrPwX5+TR/edc/6Go5PSlS6z+RCBOczI3XP17RtMoXw+8/HBgsAxqi1z+t8sXwT1zrP6cnRWpnttc/c3pSpHZm6z8yN17RtMrXPzgC31edcOs/vkZ3OALf1z/+iWsLxHrrP0lWkJ9P89c/xBH4vuqE6z/UZakGnQfYP191wm3qG9g/iZmEchGP6z/rhNvUNzDYP08hESY4mes/Famd2V6j6z/aMCqNha3rP3aU9DuFRNg/oLi2QKy36z8BpA2j0ljYP2ZAQ/TSwes/jbMmCiBt2D8ryM+n+cvrPxjDP3Ftgdg/8U9cWyDW6z+j0ljYupXYP7bX6A5H4Os/LuJxPwiq2D98X3XCberrP7rxiqZVvtg/QucBdpT06z8Hb44pu/7rP832Gt3hCOw/RQGkDaPS2D+TfqeQCBPsP9AQvXTw5tg/WAY0RC8d7D9bINbbPfvYP+cv70KLD9k/Ho7A91Un7D9yPwiq2CPZP+MVTat8Mew//U4hESY42T+pndleozvsP4heOnhzTNk/byVmEspF7D8UblPfwGDZPyRZQX4+ze8/n31sRg512T80rfLF8E/sPyqNha1bidk/+jR/eRda7D+1nJ4UqZ3ZP8C8Cy0+ZOw/Qay3e/ax2T+FRJjgZG7sP8y70OJDxtk/S8wklIt47D9Xy+lJkdrZPxBUsUeyguw/4toCsd7u2T/W2z372IzsP5xjyq7/luw/YetWYiah7D9u6hsYLAPaP/n5NH95F9o/J3PjFU2r7D+ECU7mxivaP+36b8lztew/EBlnTRRA2j+ygvx8mr/sP5sogLRhVNo/eAqJMMHJ7D8mOJkbr2jaPz6SFeTn0+w/sUeygvx82j8DGqKXDt7sPz1Xy+lJkdo/6eDNMWXX7z/IZuRQl6XaP8mhLks16Ow/U3b9t+S52j+OKbv+W/LsP96FFh8yzto/VLFHsoL87D9qlS+Gf+LaPxo51GWpBu0/9aRI7cz22j/fwGAZ0BDtP4C0YVQaC9s/pUjtzPYa7T8LxHq7Zx/bP5fTkyK1M9s/a9B5gB0l7T8wWAY0RC/tP/bfkudqOe0/IuOsiQJI2z+7Zx+bkUPtP63yxfBPXNs/ge+rTrhN7T84At9XnXDbP0d3OALfV+0/xBH4vuqE2z8M/8S1BWLtP08hESY4mds/0oZRaSxs7T/aMCqNha3bP5gO3hxTdu0/ZkBD9NLB2z9dlmrQeYDtPyMe94Ogiu0/6aWDN8eU7T/xT1xbINbbP64tEOvtnu0/fF91wm3q2z90tZyeFKntPwdvjim7/ts/OT0pUjuz7T+TfqeQCBPcPx6OwPdVJ9w//8S1BWK97T+pndleozvcP8VMQrmIx+0/NK3yxfBP3D+K1M5sr9HtP8C8Cy0+ZNw/r2ha5Yvh7z9LzCSUi3jcP1BcWyDW2+0/1ts9+9iM3D8W5OfT/OXtP2HrVmImodw/22t0hyPw7T/t+m/Jc7XcP6HzADtK+u0/eAqJMMHJ3D9me43ucATuPwMaopcO3tw/LAMaopcO7j+OKbv+W/LcP/KKplW+GO4/GjnUZakG3T918OaYsuvvP6VI7cz2Gt0/txIzCeUi7j8wWAY0RC/dP7tnH5uRQ90/fZq/vAst7j9HdzgC31fdP0MiTHAyN+4/0oZRaSxs3T8IqtgjWUHuP12WatB5gN0/zjFl139L7j/ppYM3x5TdP5S58YqmVe4/dLWcnhSp3T86eHNM2fXvP//EtQVivd0/WUF+Ps1f7j+K1M5sr9HdPx/JCvLzae4/FuTn0/zl3T/kUJelGnTuP6HzADtK+t0/qtgjWUF+7j8sAxqilw7eP3BgsAxoiO4/txIzCeUi3j816DzAjpLuP0MiTHAyN94/+2/Jc7Wc7j/OMWXXf0veP8H3VSfcpu4/hn/i2gKx7j9ZQX4+zV/eP0wHb44pu+4/5FCXpRp03j8Rj/tBUMXuP3BgsAxoiN4/1xaI9XbP7j/7b8lztZzeP52eFKmd2e4/hn/i2gKx3j9iJqFcxOPuPxGP+0FQxd4/KK4tEOvt7j+dnhSpndneP+41usMR+O4/s71GdzgC7z95RdMqXwzvPyiuLRDr7d4/Ps1f3oUW7z+zvUZ3OALfPwRV7JGsIO8/Ps1f3oUW3z/K3HhF0yrvP8rceEXTKt8/j2QF+fk07z9V7JGsID/fP+D7qhNuU98/VeyRrCA/7z9sC8R6u2ffPxt0HmBHSe8/9xrd4Qh83z8AAAAAAADwP4Iq9khWkN8/\",\"dtype\":\"float64\",\"order\":\"little\",\"shape\":[807]},\"__dummy_cat\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"__label\":[\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \",\" \"],\"index\":[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,441,442,443,444,445,446,447,448,449,450,451,452,453,454,455,456,457,458,459,460,461,462,463,464,465,466,467,468,469,470,471,472,473,474,475,476,477,478,479,480,481,482,483,484,485,486,487,488,489,490,491,492,493,494,495,496,497,498,499,500,501,502,503,504,505,506,507,508,509,510,511,512,513,514,515,516,517,518,519,520,521,522,523,524,525,526,527,528,529,530,531,532,533,534,535,536,537,538,539,540,541,542,543,544,545,546,547,548,549,550,551,552,553,554,555,556,557,558,559,560,561,562,563,564,565,566,567,568,569,570,571,572,573,574,575,576,577,578,579,580,581,582,583,584,585,586,587,588,589,590,591,592,593,594,595,596,597,598,599,600,601,602,603,604,605,606,607,608,609,610,611,612,613,614,615,616,617,618,619,620,621,622,623,624,625,626,627,628,629,630,631,632,633,634,635,636,637,638,639,640,641,642,643,644,645,646,647,648,649,650,651,652,653,654,655,656,657,658,659,660,661,662,663,664,665,666,667,668,669,670,671,672,673,674,675,676,677,678,679,680,681,682,683,684,685,686,687,688,689,690,691,692,693,694,695,696,697,698,699,700,701,702,703,704,705,706,707,708,709,710,711,712,713,714,715,716,717,718,719,720,721,722,723,724,725,726,727,728,729,730,731,732,733,734,735,736,737,738,739,740,741,742,743,744,745,746,747,748,749,750,751,752,753,754,755,756,757,758,759,760,761,762,763,764,765,766,767,768,769,770,771,772,773,774,775,776,777,778,779,780,781,782,783,784,785,786,787,788,789,790,791,792,793,794,795,796,797,798,799,800,801,802,803,804,805,806],\"x\":[21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,20,21,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,20,21,20,21,20,21,20,21,20,21,20,22,20,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,20,21,20,21,20,21,20,21,20,21,20,21,20,21,21,21,20,21,20,21,20,21,20,21,20,20,21,20,21,20,22,20]},\"selected\":{\"id\":\"5700\"},\"selection_policy\":{\"id\":\"5701\"}},\"id\":\"5687\",\"type\":\"ColumnDataSource\"},{\"attributes\":{},\"id\":\"5666\",\"type\":\"BasicTicker\"},{\"attributes\":{},\"id\":\"5663\",\"type\":\"LinearScale\"},{\"attributes\":{},\"id\":\"5677\",\"type\":\"ResetTool\"},{\"attributes\":{\"items\":[{\"id\":\"5703\"}],\"visible\":false},\"id\":\"5702\",\"type\":\"Legend\"},{\"attributes\":{\"label\":{\"value\":\" \"},\"renderers\":[{\"id\":\"5691\"}]},\"id\":\"5703\",\"type\":\"LegendItem\"},{\"attributes\":{\"overlay\":{\"id\":\"5679\"}},\"id\":\"5675\",\"type\":\"BoxZoomTool\"},{\"attributes\":{},\"id\":\"5695\",\"type\":\"BasicTickFormatter\"},{\"attributes\":{},\"id\":\"5661\",\"type\":\"LinearScale\"},{\"attributes\":{\"text\":\"\"},\"id\":\"5693\",\"type\":\"Title\"},{\"attributes\":{},\"id\":\"5659\",\"type\":\"DataRange1d\"},{\"attributes\":{\"active_drag\":\"auto\",\"active_inspect\":\"auto\",\"active_multi\":null,\"active_scroll\":\"auto\",\"active_tap\":\"auto\",\"tools\":[{\"id\":\"5673\"},{\"id\":\"5674\"},{\"id\":\"5675\"},{\"id\":\"5676\"},{\"id\":\"5677\"},{\"id\":\"5678\"}]},\"id\":\"5680\",\"type\":\"Toolbar\"},{\"attributes\":{},\"id\":\"5670\",\"type\":\"BasicTicker\"}],\"root_ids\":[\"5656\"]},\"title\":\"Bokeh Application\",\"version\":\"2.1.1\"}};\n",
" var render_items = [{\"docid\":\"079dddf2-c6e3-465e-b388-aaa12e7a13e6\",\"root_ids\":[\"5656\"],\"roots\":{\"5656\":\"b82a665a-fcca-4cee-aa51-6b9c4a307e0c\"}}];\n",
" root.Bokeh.embed.embed_items_notebook(docs_json, render_items);\n",
"\n",
" }\n",
" if (root.Bokeh !== undefined) {\n",
" embed_document(root);\n",
" } else {\n",
" var attempts = 0;\n",
" var timer = setInterval(function(root) {\n",
" if (root.Bokeh !== undefined) {\n",
" clearInterval(timer);\n",
" embed_document(root);\n",
" } else {\n",
" attempts++;\n",
" if (attempts > 100) {\n",
" clearInterval(timer);\n",
" console.log(\"Bokeh: ERROR: Unable to run BokehJS code because BokehJS library is missing\");\n",
" }\n",
" }\n",
" }, 10, root)\n",
" }\n",
"})(window);"
],
"application/vnd.bokehjs_exec.v0+json": ""
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"id": "5656"
}
},
"output_type": "display_data"
}
],
"source": [
"p = bokeh_catplot.ecdf(\n",
" np.diff(df['time (ms)'].values),\n",
" x_axis_label='time between acquisitions (ms)',\n",
")\n",
"\n",
"bokeh.io.show(p)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### A performant controllable graphical live app\n",
"\n",
"The performance of the graphics leaves a bit to be desired. The updates are too slow. This is because Bokeh has to re-render an entire plot each time the periodic callback is executed. Preferably, we would only update the *data* on the plot. It turns out that Bokeh is highly optimized for this.\n",
"\n",
"To do this, though, we must drop down into the lower level graphics of Bokeh and build a **Bokeh app**. We will use Bokeh alone to generate the toggles, buttons, and callbacks, and will *stream* the data into the Bokeh plot.\n",
"\n",
"As an example of how a Bokeh app can use a periodic callback for streaming, I build one below to dynamically plot a random walk. The walk will proceed with a dot doing the walk and the trail behind it represented as a line. To build a Bokeh app, we need to write a function the controls the app. The function for the random walker is shown below with an explanation following immediately."
]
},
{
"cell_type": "code",
"execution_count": 35,
"metadata": {},
"outputs": [],
"source": [
"def random_walk(doc):\n",
" \"\"\"Bokeh app for a dynamic random walk of 1000 steps.\"\"\"\n",
" rg = np.random.default_rng(3252)\n",
"\n",
" p = bokeh.plotting.figure(\n",
" frame_width=200,\n",
" frame_height=200,\n",
" x_range=[-20, 20],\n",
" y_range=[-20, 20],\n",
" )\n",
"\n",
" # Use ColumnDataSources for data for populating glyphs\n",
" source_line = bokeh.models.ColumnDataSource({\"x\": [0], \"y\": [0]})\n",
" source_dot = bokeh.models.ColumnDataSource({\"x\": [0], \"y\": [0]})\n",
" line = p.line(source=source_line, x=\"x\", y=\"y\")\n",
" dot = p.circle(source=source_dot, x=\"x\", y=\"y\", color=\"tomato\", size=7)\n",
"\n",
" @bokeh.driving.linear()\n",
" def update(step):\n",
" if step > 1000:\n",
" doc.remove_periodic_callback(pc)\n",
" else:\n",
" theta = rg.uniform(0, 2 * np.pi)\n",
" new_position = {\n",
" \"x\": [source_dot.data[\"x\"][0] + np.cos(theta)],\n",
" \"y\": [source_dot.data[\"y\"][0] + np.sin(theta)],\n",
" }\n",
" source_line.stream(new_position)\n",
" source_dot.data = new_position\n",
"\n",
" doc.add_root(p)\n",
"\n",
" # Add a periodic callback to be run every 20 milliseconds\n",
" pc = doc.add_periodic_callback(update, 20)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The argument of the function (traditionally called `doc`) is accessed to add any plots (or other Bokeh) to app and to add the callbacks. We first set up the figure and set up the data sources for the dot and for the line. Next, we set up the data sources using Bokeh's `ColumnDataSource`. So far in the bootcamp, we have use Pandas data frames as the source for plots. Under the hood, Bokeh automatically converts those to its `ColumnDataSource` data type. This data type may be dynamically updated in a Bokeh app, which is exactly what we want. After the data sources are set up, we set up an update function (we call it `update()` here, but it could have any name). This is what will be called each time the periodic callback triggers. In this case, we decorate the function with `@bokeh.driving.linear()`. This results in the argument of `update`, `step`, being advanced by one every time the function is called. This way we can keep track of how many steps were taken. In the update function, if we have exceeded the number of desired steps, we cancel the periodic callbacks. Otherwise, we compute the next step of the random walk by computing a random angle for the step. We update the position of the walker by adding the step to it. Finally, we update the data sources for the dot and line. For the line, we use the `stream()` method. This results in Bokeh only appending new data to the data source instead of pushing through the whole data set for the plot each time. For the dot, since it is only plotted as a single position, we update the source data to be the dot position.\n",
"\n",
"To run our app, we use `bokeh.io.show()`. We should also include the URL of the notebook (specified above in the input cell; you can see the URL by looking at the top of your browser)."
]
},
{
"cell_type": "code",
"execution_count": 36,
"metadata": {},
"outputs": [
{
"data": {
"application/vnd.bokehjs_exec.v0+json": "",
"text/html": [
"\n",
""
]
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"server_id": "d212e4606f2b4f018585275581ff5957"
}
},
"output_type": "display_data"
}
],
"source": [
"bokeh.io.show(random_walk, notebook_url=notebook_url)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"When you run this app, you will see that Bokeh has no problem updating a plot every 20 ms using the `stream()` method of a `ColumnDataSource`. We will use this as we build out our app.\n",
"\n",
"Instead of building the app directly, we will write a function that returns an app. This lets us conveniently specify parameters for the app. It takes care of opening and closing the connection with the device, writing to disk, etc."
]
},
{
"cell_type": "code",
"execution_count": 37,
"metadata": {},
"outputs": [],
"source": [
"def potentiometer_app(\n",
" port,\n",
" outfile,\n",
" delay=20,\n",
" plot_delay=90,\n",
" rollover=400,\n",
" force_overwrite=False,\n",
"):\n",
" \"\"\"Make a Bokeh app for potentiometer.\n",
" \n",
" Parameters\n",
" ----------\n",
" port : str\n",
" Location of port for serial connection to Arduino.\n",
" outfile : str\n",
" Path to the file to which data will be written.\n",
" delay: int, default 20\n",
" Delay between data points in milliseconds.\n",
" plot_delay : int, default 100\n",
" Delay between updates of the plot in milliseconds.\n",
" rollover: int, default 400\n",
" Maximum number of data points to show on plot at a time.\n",
" force_overwrite: bool, default False\n",
" If True, overwrite `outfile` if the file already exists.\n",
" \n",
" Returns\n",
" -------\n",
" app : function\n",
" A function that defines a Bokeh app. To start the app,\n",
" run `bokeh.io.show(app)`.\n",
" \"\"\"\n",
" if os.path.isfile(outfile) and not force_overwrite:\n",
" raise RuntimeError(f\"{outfile} exists, cowardly not overwriting.\")\n",
"\n",
" def app(doc):\n",
" arduino = open_arduino(port)\n",
"\n",
" # Specify delay\n",
" arduino.write(bytes([READ_DAQ_DELAY]) + (str(delay) + \"x\").encode())\n",
"\n",
" # Initialize data arrays\n",
" time_ms = []\n",
" voltage = []\n",
"\n",
" # Initialize the read buffer\n",
" read_buffer = [b\"\"]\n",
"\n",
" # Toggles\n",
" acquire_toggle = bokeh.models.Toggle(\n",
" label=\"ACQUIRE\", button_type=\"success\", width=100,\n",
" )\n",
"\n",
" stop_button = bokeh.models.Button(\n",
" label=\"STOP\", button_type=\"danger\", width=100,\n",
" )\n",
"\n",
" # Status report\n",
" status_text = bokeh.models.Div(\n",
" text=\"Status: Awaiting data acquisition.\", width=200\n",
" )\n",
"\n",
" # Callbacks\n",
" def shutdown(new):\n",
" \"\"\"Stop procedures\"\"\"\n",
" # Stop the periodic callback\n",
" doc.remove_periodic_callback(pc)\n",
"\n",
" # Disable toggles\n",
" acquire_toggle.active = False\n",
" stop_button.disabled = True\n",
" acquire_toggle.disabled = True\n",
"\n",
" # Close the connection to Arduino\n",
" try:\n",
" arduino.reset_input_buffer()\n",
" arduino.close()\n",
" except:\n",
" pass\n",
"\n",
" # Write the resulting data out to disk\n",
" df = pd.DataFrame(\n",
" data={\n",
" \"time (ms)\": np.concatenate(time_ms),\n",
" \"voltage (V)\": np.concatenate(voltage),\n",
" }\n",
" )\n",
" df.to_csv(outfile, index=False)\n",
"\n",
" # Update status\n",
" status_text.text = (\n",
" \"Status: Arduino connection closed; \"\n",
" + f\"app terminated. {len(df)} data points are \"\n",
" + f\"stored in {outfile}.\"\n",
" )\n",
"\n",
" def stream_control(attr, old, new):\n",
" \"\"\"Turn on the data stream\"\"\"\n",
" if new:\n",
" status_text.text = \"Status: Acquiring data.\"\n",
" arduino.write(bytes([STREAM]))\n",
" else:\n",
" status_text.text = \"Status: Awaiting data acquisition.\"\n",
" arduino.write(bytes([ON_REQUEST]))\n",
"\n",
" # Link callbacks\n",
" acquire_toggle.on_change(\"active\", stream_control)\n",
" stop_button.on_click(shutdown)\n",
"\n",
" # Make plot\n",
" p = bokeh.plotting.figure(\n",
" frame_width=500,\n",
" frame_height=175,\n",
" x_axis_label=\"time (s)\",\n",
" y_axis_label=\"voltage (V)\",\n",
" y_range=[-0.2, 5.2],\n",
" )\n",
" p.x_range.range_padding = 0\n",
" source = bokeh.models.ColumnDataSource({\"t\": [], \"V\": []})\n",
" r = p.line(source=source, x=\"t\", y=\"V\")\n",
"\n",
" # Turn on the stream\n",
" arduino.write(bytes([STREAM]))\n",
"\n",
" @bokeh.driving.linear()\n",
" def update(step):\n",
" if step == 0:\n",
" arduino.reset_input_buffer()\n",
" read_buffer[0] = b\"\"\n",
" elif acquire_toggle.active:\n",
" # Wait for data to arrive\n",
" while arduino.in_waiting < 0:\n",
" pass\n",
"\n",
" # Read in the data\n",
" read = read_all(\n",
" arduino, chunk_size=100, read_buffer=read_buffer[0]\n",
" )\n",
" \n",
" # Parse and add data set\n",
" t, V, read_buffer[0] = parse_read(read)\n",
" time_ms.append(t)\n",
" voltage.append(V)\n",
"\n",
" # Update plot\n",
" source.stream(\n",
" {\"t\": np.array(t) / 1000, \"V\": V,}, rollover,\n",
" )\n",
"\n",
" doc.add_root(\n",
" bokeh.layouts.row(\n",
" p,\n",
" bokeh.layouts.Spacer(width=15),\n",
" bokeh.layouts.column(acquire_toggle, stop_button, status_text),\n",
" )\n",
" )\n",
"\n",
" # Add a periodic callback to be run every `plot_delay` milliseconds\n",
" pc = doc.add_periodic_callback(update, plot_delay)\n",
"\n",
" return app"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"This app has several bits of syntax you haven't seen before. Essentially, we're building a layout and linking up callbacks using Bokeh directly instead of Panel. Based on what you already know from the bootcamp and what you've already seen in this lesson, the code above should be self-explanatory. A couple key points of note:\n",
"\n",
"1. Instead of setting up a watcher like we do with Panel, we use an the `on_change()` method of a toggle widget. The callback function for on-change behavior must have call signature `callback(attr, old, new)`, where `attr` is an attribute of the widget, `old` is the pre-change value of that attribute, and `new` is the post-change value of the attribute.\n",
"2. There is now plain text widget for Bokeh. Instead, we use a `Div` object to make a div, into which we can insert text that will be interpreted as HTML.\n",
"3. We have to add the layout to the `doc` using the `add_root()` method. Similarly, a periodic callback has to be added to the `doc`.\n",
"\n",
"One other point of note is that I choose a default `plot_delay` of 90 ms. I find that ten updates per second is fine for the human eye to perceive; there is no reason to go faster, though we could.\n",
"\n",
"Now that we've built it, let's see it in action!"
]
},
{
"cell_type": "code",
"execution_count": 38,
"metadata": {},
"outputs": [
{
"data": {
"application/vnd.bokehjs_exec.v0+json": "",
"text/html": [
"\n",
""
]
},
"metadata": {
"application/vnd.bokehjs_exec.v0+json": {
"server_id": "6cf94b3f9b71466c943f35d0a04467e4"
}
},
"output_type": "display_data"
}
],
"source": [
"bokeh.io.show(\n",
" potentiometer_app(port, \"test_potentiometer_daq.csv\", force_overwrite=True),\n",
" notebook_url=\"localhost:8888\",\n",
")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Conclusions\n",
"\n",
"By using Bokeh's and Panel's built-in asynchrony, we can collect streams of data from Arduino. If we want hight responsive plot updating, we need to dig a bit into the lower-level plotting library, in this case Bokeh. For many devices, though, data acquisition is not that fast, and updates every second or so are plenty fast, and you can build the app entirely with Panel's high-level functionality.\n",
"\n",
"The apps we built here function in a notebook. You can read [here](https://docs.bokeh.org/en/latest/docs/user_guide/server.html) about how to serve the app up on a static website. This would be a good exercise for you in reading documentation to build your own stand-alone browser-based app for controlling an external device."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Computing environment"
]
},
{
"cell_type": "code",
"execution_count": 39,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"CPython 3.7.7\n",
"IPython 7.16.1\n",
"\n",
"numpy 1.18.5\n",
"pandas 0.24.2\n",
"serial 3.4\n",
"bokeh 2.1.1\n",
"panel 0.9.7\n",
"bokeh_catplot 0.1.8\n",
"jupyterlab 2.1.5\n"
]
}
],
"source": [
"%load_ext watermark\n",
"%watermark -v -p numpy,pandas,serial,bokeh,panel,bokeh_catplot,jupyterlab"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.7"
}
},
"nbformat": 4,
"nbformat_minor": 4
}