%23%20%2F%2F%2F%20script%0A%23%20requires-python%20%3D%20%22%3E%3D3.11%22%0A%23%20dependencies%20%3D%20%5B%22marimo%3E%3D0.23.9%22%2C%20%22numpy%3E%3D2.0%22%2C%20%22matplotlib%3E%3D3.9%22%2C%20%22pandas%3E%3D2.2%22%2C%20%22scipy%3E%3D1.14%22%2C%20%22seaborn%3E%3D0.13%22%2C%20%22urllib3%3E%3D2.2%22%2C%20%22detecta%3E%3D0.0.5%22%5D%0A%23%20%2F%2F%2F%0A%0Aimport%20marimo%0A%0A__generated_with%20%3D%20%220.25.2%22%0Aapp%20%3D%20marimo.App()%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%20Read%20Cortex%20Motion%20Analysis%20Corporation%20.trc%20and%20.forces%20files%20(example)%0A%0A%20%20%20%20%3E%20Marcos%20Duarte%2C%20Renato%20Naville%20Watanabe%3Cbr%3E%0A%20%20%20%20%3E%20%5BLaboratory%20of%20Biomechanics%20and%20Motor%20Control%5D(https%3A%2F%2Fbmclab.pesquisa.ufabc.edu.br%2F)%3Cbr%3E%0A%20%20%20%20%3E%20Federal%20University%20of%20ABC%2C%20Brazil%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20How%20to%20use%20this%20guide%0A%0A%20%20%20%20Marker%20trajectories%20and%20force%20plates%20share%20a%20trial%20but%20have%20different%20sample%20rates.%20How%20can%20we%20compare%20them%20on%20one%20time%20axis%3F%0A%0A%20%20%20%20We%20will%20read%20two%20public%20walking%20trials%2C%20inspect%20sampling%20rates%2C%20and%20resample%20marker%20trajectories%20before%20plotting%20heel%20position%20and%20force.%0A%0A%20%20%20%20Predict%20the%20result%20before%20running%20each%20example.%20Try%20the%20**Exercises**%20before%20opening%20their%20worked%20solutions.%20Finish%20with%20the%20**Checkpoint%20questions**%20and%20**Problems**%3B%20the%20latter%20provide%20final%20answers%20only.%0A%0A%20%20%20%20Open%20this%20file%20locally%20in%20marimo%2C%20on%20%5Bmarimo.app%5D(https%3A%2F%2Fmarimo.app%2F)%2C%20or%20in%20%5Bmolab%5D(https%3A%2F%2Fmolab.marimo.io%2Fnotebooks).%20The%20repository%20files%20%60walk1.trc%2F.forces%60%20and%20%60walk2.trc%2F.forces%60%20replace%20the%20old%20private%20day%2Fnight%20filenames.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_()%3A%0A%20%20%20%20try%3A%0A%20%20%20%20%20%20%20%20from%20notebook_resources%20import%20repo_file%0A%20%20%20%20except%20ModuleNotFoundError%20as%20_error%3A%0A%20%20%20%20%20%20%20%20if%20_error.name%20!%3D%20%22notebook_resources%22%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20raise%0A%20%20%20%20%20%20%20%20raise%20ModuleNotFoundError(%0A%20%20%20%20%20%20%20%20%20%20%20%20%22This%20notebook%20needs%20notebook_resources.py.%20Download%20it%20from%3A%5Cn%22%0A%20%20%20%20%20%20%20%20%20%20%20%20%22https%3A%2F%2Fraw.githubusercontent.com%2FBMClab%2FBMC%2Fmaster%2Ffunctions%2Fnotebook_resources.py%5Cn%22%0A%20%20%20%20%20%20%20%20%20%20%20%20%22Save%20it%20in%20the%20same%20folder%20as%20this%20notebook%2C%20then%20rerun%20this%20cell.%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20name%3D%22notebook_resources%22%2C%0A%20%20%20%20%20%20%20%20)%20from%20None%0A%20%20%20%20return%20(repo_file%2C)%0A%0A%0A%40app.cell%0Adef%20_(repo_file)%3A%0A%20%20%20%20import%20numpy%20as%20np%0A%20%20%20%20import%20pandas%20as%20pd%0A%20%20%20%20%23%20'%25matplotlib%20inline'%20command%20supported%20automatically%20in%20marimo%0A%20%20%20%20import%20matplotlib%20as%20mpl%0A%20%20%20%20import%20matplotlib.pyplot%20as%20plt%0A%20%20%20%20import%20seaborn%20as%20sns%0A%20%20%20%20sns.set_style('whitegrid')%0A%20%20%20%20sns.set_context('notebook'%2C%20font_scale%3D1.2%2C%20rc%3D%7B%22lines.linewidth%22%3A%202%7D)%0A%20%20%20%20from%20scipy%20import%20signal%0A%20%20%20%20import%20sys%2C%20os%0A%20%20%20%20_functions%20%3D%20%5Brepo_file(f'functions%2F%7B_m%7D.py')%20for%20_m%20in%20('io_cortexmac'%2C%20'critic_damp'%2C%20'linear_envelope')%5D%0A%20%20%20%20sys.path.insert(0%2C%20str(_functions%5B0%5D.parent))%20%20%23%20add%20to%20pythonpath%0A%20%20%20%20import%20io_cortexmac%20as%20io%20%20%23%20from%20https%3A%2F%2Fgithub.com%2FBMClab%2FBMC%2Ftree%2Fmaster%2Ffunctions%0A%0A%20%20%20%20return%20io%2C%20np%2C%20pd%2C%20plt%2C%20signal%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Python%20setup%0A%0A%20%20%20%20The%20repository%20reader%20keeps%20marker%20and%20force%20channels%20in%20separate%20tables.%20NumPy%20and%20SciPy%20handle%20the%20numerical%20resampling%3B%20pandas%20preserves%20labels.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Use%20function%20%60io_cortexmac.py%60%20from%20BMClab's%20repo%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(repo_file)%3A%0A%20%20%20%20path2%20%3D%20repo_file(%22data%2Fwalk1.trc%22).parent%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(io%2C%20repo_file)%3A%0A%20%20%20%20_fname%20%3D%20str(repo_file(%22data%2Fwalk1.trc%22))%0A%20%20%20%20(_h_trc%2C%20trc)%20%3D%20io.read_trc(_fname%2C%20fname2%3D''%2C%20units%3D'm'%2C%20dropna%3DFalse%2C%20na%3D0.0%2C%20df_multi%3DFalse)%0A%20%20%20%20trc.set_index('Time'%2C%20drop%3DTrue%2C%20inplace%3DTrue)%0A%20%20%20%20trc.drop('Frame%23'%2C%20axis%3D1%2C%20inplace%3DTrue)%0A%20%20%20%20return%20(trc%2C)%0A%0A%0A%40app.cell%0Adef%20_(io%2C%20repo_file)%3A%0A%20%20%20%20_fname%20%3D%20str(repo_file(%22data%2Fwalk1.forces%22))%0A%20%20%20%20(_h_grf%2C%20grf)%20%3D%20io.read_forces(_fname%2C%20time%3DTrue%2C%20forcepla%3D%5B%5D%2C%20mm2m%3DTrue%2C%20show_msg%3DTrue)%0A%20%20%20%20return%20(grf%2C)%0A%0A%0A%40app.cell%0Adef%20_(trc)%3A%0A%20%20%20%20trc%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(grf)%3A%0A%20%20%20%20grf%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%23%20trc%20and%20forces%20data%20have%20different%20sampling%20rates%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(np%2C%20trc)%3A%0A%20%20%20%20freq_trc%20%3D%201%2Fnp.mean(np.diff(trc.index))%0A%20%20%20%20freq_trc%0A%20%20%20%20return%20(freq_trc%2C)%0A%0A%0A%40app.cell%0Adef%20_(grf%2C%20np)%3A%0A%20%20%20%20freq_grf%20%3D%201%2Fnp.mean(np.diff(grf.index))%0A%20%20%20%20freq_grf%0A%20%20%20%20return%20(freq_grf%2C)%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20**Exercise%201.**%20If%20marker%20data%20are%20sampled%20at%20150%20Hz%20and%20force%20data%20at%20450%20Hz%2C%20what%20is%20the%20upsampling%20ratio%3F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%2F%2F%2F%20details%20%7C%20Solution%20to%20Exercise%201%0A%0A%20%20%20%20The%20ratio%20is%20%24450%2F150%3D3%24.%20Each%20marker%20sampling%20bin%20corresponds%20to%20three%20force%20sampling%20bins.%20This%20interpolates%20marker%20values%3B%20it%20adds%20no%20measured%20kinematic%20detail.%0A%20%20%20%20%2F%2F%2F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%23%23%20Resample%20trc%20to%20the%20force%20sampling%20rate%20(150%20Hz%20to%20450%20Hz)%0A%0A%20%20%20%20Linear%20boundary%20extension%20avoids%20forcing%20the%20last%20marker%20coordinate%20toward%20zero.%0A%20%20%20%20Boundary%20values%20remain%20estimates%3A%20inspect%20the%20ends%2C%20and%20retain%20the%20original%20timestamps%0A%20%20%20%20when%20deciding%20which%20part%20of%20the%20resampled%20signal%20to%20analyse.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(freq_grf%2C%20freq_trc%2C%20np%2C%20pd%2C%20signal%2C%20trc)%3A%0A%20%20%20%20_nrows%20%3D%20int(trc.shape%5B0%5D%20*%20np.round(freq_grf%20%2F%20freq_trc))%0A%20%20%20%20_ncols%20%3D%20trc.shape%5B1%5D%0A%20%20%20%20_data%20%3D%20np.nan%20*%20np.zeros((_nrows%2C%201%20%2B%20_ncols)%2C%20dtype%3D'float64')%0A%20%20%20%20_data%5B%3A%2C%200%5D%20%3D%20np.linspace(start%3D0%2C%20stop%3D_nrows%20%2F%20freq_grf%2C%20num%3D_nrows%2C%20endpoint%3DFalse)%0A%20%20%20%20for%20_i%20in%20range(_ncols)%3A%0A%20%20%20%20%20%20%20%20_data%5B%3A%2C%20_i%20%2B%201%5D%20%3D%20signal.resample_poly(trc.iloc%5B%3A%2C%20_i%5D%2C%20int(round(freq_grf))%2C%20int(round(freq_trc))%2C%20window%3D'blackman'%2C%20padtype%3D'line')%0A%20%20%20%20trc_1%20%3D%20pd.DataFrame(data%3D_data%5B%3A%2C%201%3A%5D%2C%20index%3D_data%5B%3A%2C%200%5D%2C%20columns%3Dtrc.columns)%0A%20%20%20%20trc_1.index.name%20%3D%20trc_1.index.name%0A%20%20%20%20return%20(trc_1%2C)%0A%0A%0A%40app.cell%0Adef%20_(trc_1)%3A%0A%20%20%20%20trc_1%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Plot%20of%20some%20data%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(trc_1)%3A%0A%20%20%20%20trc_1.columns%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(grf)%3A%0A%20%20%20%20grf.columns%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(grf%2C%20plt%2C%20trc_1)%3A%0A%20%20%20%20(_fig%2C%20_axs)%20%3D%20plt.subplots(2%2C%201%2C%20sharex%3DTrue%2C%20squeeze%3DTrue%2C%20figsize%3D(10%2C%205))%0A%20%20%20%20trc_1.plot(y%3D%5B'R.Heely'%2C%20'L.Heely'%5D%2C%20ax%3D_axs%5B0%5D%2C%20title%3D'Walking%20trial%201')%0A%20%20%20%20grf.plot(y%3D%5B'FY5'%2C%20'FY6'%5D%2C%20ax%3D_axs%5B1%5D%2C%20colormap%3D'viridis')%0A%20%20%20%20_axs%5B0%5D.set_ylabel('Position%20%5Bm%5D')%0A%20%20%20%20_axs%5B1%5D.set_ylabel('Force%20%5BN%5D')%0A%20%20%20%20plt.show()%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20Use%20the%20synchronized%20heel%20and%20force%20traces%20to%20assess%20foot%20contacts.%20A%20force-plate%20number%20alone%20does%20not%20identify%20left%20versus%20right%20foot.%20Confirm%20the%20assignment%20against%20the%20marker%20positions%20and%20acquisition%20layout%20for%20each%20trial.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20**Exercise%202.**%20Does%20matching%20the%20two%20sampling%20rates%20prove%20that%20the%20devices%20were%20synchronized%3F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%2F%2F%2F%20details%20%7C%20Solution%20to%20Exercise%202%0A%0A%20%20%20%20No.%20Matching%20rates%20gives%20compatible%20spacing%2C%20but%20an%20offset%20or%20clock%20drift%20can%20remain.%20The%20paired%20files%20must%20share%20a%20known%20acquisition%20time%20origin%3B%20verify%20that%20assumption%20before%20assigning%20force%20to%20a%20foot.%0A%20%20%20%20%2F%2F%2F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Compare%20a%20second%20trial%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(io%2C%20np%2C%20pd%2C%20plt%2C%20repo_file%2C%20signal)%3A%0A%20%20%20%20_fname%20%3D%20str(repo_file(%22data%2Fwalk2.trc%22))%0A%20%20%20%20(_h_trc%2C%20trc_2)%20%3D%20io.read_trc(_fname%2C%20fname2%3D''%2C%20units%3D'm'%2C%20dropna%3DFalse%2C%20na%3D0.0%2C%20df_multi%3DFalse)%0A%20%20%20%20trc_2.set_index('Time'%2C%20drop%3DTrue%2C%20inplace%3DTrue)%0A%20%20%20%20trc_2.drop('Frame%23'%2C%20axis%3D1%2C%20inplace%3DTrue)%0A%20%20%20%20_fname%20%3D%20str(repo_file(%22data%2Fwalk2.forces%22))%0A%20%20%20%20(_h_grf%2C%20grf_1)%20%3D%20io.read_forces(_fname%2C%20time%3DTrue%2C%20forcepla%3D%5B%5D%2C%20mm2m%3DTrue%2C%20show_msg%3DTrue)%0A%20%20%20%20freq_trc_1%20%3D%201%20%2F%20np.mean(np.diff(trc_2.index))%0A%20%20%20%20freq_grf_1%20%3D%201%20%2F%20np.mean(np.diff(grf_1.index))%0A%20%20%20%20_nrows%20%3D%20int(trc_2.shape%5B0%5D%20*%20np.round(freq_grf_1%20%2F%20freq_trc_1))%0A%20%20%20%20_ncols%20%3D%20trc_2.shape%5B1%5D%0A%20%20%20%20_data%20%3D%20np.nan%20*%20np.zeros((_nrows%2C%201%20%2B%20_ncols)%2C%20dtype%3D'float64')%0A%20%20%20%20_data%5B%3A%2C%200%5D%20%3D%20np.linspace(start%3D0%2C%20stop%3D_nrows%20%2F%20freq_grf_1%2C%20num%3D_nrows%2C%20endpoint%3DFalse)%0A%20%20%20%20for%20_i%20in%20range(_ncols)%3A%0A%20%20%20%20%20%20%20%20_data%5B%3A%2C%20_i%20%2B%201%5D%20%3D%20signal.resample_poly(trc_2.iloc%5B%3A%2C%20_i%5D%2C%20int(round(freq_grf_1))%2C%20int(round(freq_trc_1))%2C%20window%3D'blackman'%2C%20padtype%3D'line')%0A%20%20%20%20trc_2%20%3D%20pd.DataFrame(data%3D_data%5B%3A%2C%201%3A%5D%2C%20index%3D_data%5B%3A%2C%200%5D%2C%20columns%3Dtrc_2.columns)%0A%20%20%20%20trc_2.index.name%20%3D%20trc_2.index.name%0A%20%20%20%20(_fig%2C%20_axs)%20%3D%20plt.subplots(2%2C%201%2C%20sharex%3DTrue%2C%20squeeze%3DTrue%2C%20figsize%3D(10%2C%205))%0A%20%20%20%20trc_2.plot(y%3D%5B'R.Heely'%2C%20'L.Heely'%5D%2C%20ax%3D_axs%5B0%5D%2C%20title%3D'Walking%20trial%202')%0A%20%20%20%20grf_1.plot(y%3D%5B'FY5'%2C%20'FY6'%5D%2C%20ax%3D_axs%5B1%5D%2C%20colormap%3D'viridis')%0A%20%20%20%20_axs%5B0%5D.set_ylabel('Position%20%5Bm%5D')%0A%20%20%20%20_axs%5B1%5D.set_ylabel('Force%20%5BN%5D')%0A%20%20%20%20plt.show()%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20This%20means%20that%20the%20subject%20stepped%20on%20force%20plate%20**%236**%20with%20her%2Fhis%20**right**%20foot%20and%20then%20stepped%20on%20force%20plate%20**%235**%20with%20her%2Fhis%20**left**%20foot.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20marimo%20as%20mo%0A%0A%20%20%20%20return%20(mo%2C)%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Checkpoint%20questions%0A%0A%20%20%20%201.%20Does%20resampling%20create%20new%20marker%20observations%3F%0A%0A%20%20%20%202.%20Why%20plot%20both%20signals%20against%20time%20rather%20than%20row%20number%3F%0A%0A%20%20%20%203.%20Can%20force-plate%20labels%20alone%20identify%20the%20contacting%20foot%3F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%2F%2F%2F%20details%20%7C%20Checkpoint%20answers%0A%0A%20%20%20%201.%20No.%0A%20%20%20%202.%20Original%20rows%20correspond%20to%20different%20sampling%20intervals.%0A%20%20%20%203.%20No.%0A%20%20%20%20%2F%2F%2F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Problems%0A%0A%20%20%20%20Try%20these%20independently%3B%20open%20a%20panel%20only%20to%20check%20your%20final%20answer.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20**Problem%201.**%20There%20are%20364%20marker%20frames%20at%20150%20Hz.%20How%20many%20output%20rows%20result%20at%20450%20Hz%3F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%2F%2F%2F%20details%20%7C%20Answer%20to%20Problem%201%0A%0A%20%20%20%201%2C092.%0A%20%20%20%20%2F%2F%2F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20**Problem%202.**%20What%20time%20interval%20separates%20force%20samples%20at%20450%20Hz%3F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%2F%2F%2F%20details%20%7C%20Answer%20to%20Problem%202%0A%0A%20%20%20%20%241%2F450%24%20s%2C%20approximately%202.22%20ms.%0A%20%20%20%20%2F%2F%2F%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20Go%20deeper%0A%0A%20%20%20%20Inspect%20alignment%20at%20several%20contacts%2C%20and%20compare%20original%20versus%20resampled%20marker%20values%20away%20from%20filter%20boundaries.%0A%0A%20%20%20%20%23%23%23%20Video%20lectures%20on%20the%20Internet%0A%0A%20%20%20%20%5BOpenSim%20video%20tutorials%5D(https%3A%2F%2Fwww.youtube.com%2F%40OpenSimVideos)%20provide%20gait-analysis%20context.%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20_(mo)%3A%0A%20%20%20%20mo.md(r%22%22%22%0A%20%20%20%20%23%23%20References%0A%0A%20%20%20%20-%20%5BSciPy%20polyphase%20resampling%5D(https%3A%2F%2Fdocs.scipy.org%2Fdoc%2Fscipy%2Freference%2Fgenerated%2Fscipy.signal.resample_poly.html).%0A%0A%20%20%20%20-%20%5BMotion%20Analysis%5D(https%3A%2F%2Fwww.motionanalysis.com%2F).%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0Aif%20__name__%20%3D%3D%20%22__main__%22%3A%0A%20%20%20%20app.run()%0A
1dbce155103eb3ed2acdbac69d08f0f7