The main process of hierarchical clustering list below can be found in ./fft_main_sep_twoMiceInteract.py
- Get data from tracking result with function
retrieve_poses_Mice
- Clean the data with functions
clean_differentLength_clips
,remove_longMiceDist_clips
,left_right
,correctLimbs
- Preprocess the data with function
align_poses_self
- Get feature from the data with funcion
compute_features_sep_twoMice_Independent
- Conduct hierarchical clustering with function
cluster
- Visualize and save the result
- Generate input files for clustering UI
See the installation for the tracking part.
Set the Behavioral Clustering folder as the current directory.
cd BehavioralClustering
Change the following settings in ./setting.py
. Changes for individual behavior and social behavior are explained separately here.
- Adjust the weights for Individual behavioral features
# cluster_arg: parameter of features and threshold for clustering
self.cluster_arg = [
{
'thred':30, # threshold for defining cluster in the dendrogram
'name':'all_twoMice', ## name: for display
'evaluation_metric':'Adjusted Rand index',
'features_arg':[\
# {'feat_key':'newFeatureName','weight':4,'norm':'zscore_all'},
{'feat_key':'left_ear','weight':1,'norm':'zscore_all'},
{'feat_key':'right_ear','weight':1,'norm':'zscore_all'},
{'feat_key':'left_ear_phi','weight':1,'norm':'zscore_all'},
{'feat_key':'right_ear_phi','weight':1,'norm':'zscore_all'},
{'feat_key':'body_length','weight':1,'norm':'zscore_all'},
{'feat_key':'head_length','weight':1,'norm':'zscore_all'},
{'feat_key':'head_body_angles','weight':1,'norm':'zscore_all'},
{'feat_key':'displace_rho','weight':1,'norm':'zscore_all'},
{'feat_key':'displace_phi_c','weight':1,'norm':'zscore_all'},
{'feat_key':'displace_phi_s','weight':1,'norm':'zscore_all'},
{'feat_key':'nose_fft_amp','weight':1,'norm':'zscore_all'},
{'feat_key':'nose_fft_ang','weight':1,'norm':'zscore_all'},
{'feat_key':'contourPCA_fft_amp','weight':1,'norm':'zscore_all'},
{'feat_key':'contourPCA_fft_ang','weight':1,'norm':'zscore_all'},
{'feat_key':'body_change_ang','weight':1,'norm':'zscore_all'},
{'feat_key':'left_ear_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'right_ear_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'left_ear_phi_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'right_ear_phi_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'body_length_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'head_length_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'head_body_angles_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'displace_rho_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'displace_phi_c_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'displace_phi_s_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'nose_fft_amp_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'nose_fft_ang_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'contourPCA_fft_amp_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'contourPCA_fft_ang_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'body_change_ang_TO','weight':0,'norm':'zscore_all'},
{'feat_key':'TM_nose_RM_tail_displace_phi','weight':0,'norm':'zscore_all'},
{'feat_key':'TM_nose_RM_tail_displace_rho','weight':0,'norm':'zscore_all'},
{'feat_key':'RM_nose_TM_tail_displace_phi','weight':0,'norm':'zscore_all'},
{'feat_key':'RM_nose_TM_tail_displace_rho','weight':0,'norm':'zscore_all'},
{'feat_key':'nose_nose_displace_rho','weight':0,'norm':'zscore_all'},
{'feat_key':'nose_nose_displace_phi','weight':0,'norm':'zscore_all'},
{'feat_key':'two_body_ang','weight':0,'norm':'zscore_all'},
{'feat_key':'two_head_ang','weight':0,'norm':'zscore_all'},
],
},
]
- Change the threshold for distance between two mice to a very large number
self.distance_threshold = 10000 #
- Specify the directory to save the generated videos
self.gen_video_folder = # where the generated videos will be saved
- Specify the directory to save the metadata which will be used for inspecting the clustering results
self.result_folder = # where the metadata will be saved
- Specify the suffix for generated videos
self.video_name_suffix = # suffix for generated videos
-
Adjust the weights for Social behavioral features
self.cluster_arg = [ { 'thred':30, # threshold for defining cluster in the dendrogram 'name':'all_twoMice',## name: for display 'evaluation_metric':'Adjusted Rand index', 'features_arg':[\ # {'feat_key':'newFeatureName','weight':4,'norm':'zscore_all'}, {'feat_key':'left_ear','weight':1,'norm':'zscore_all'}, {'feat_key':'right_ear','weight':1,'norm':'zscore_all'}, {'feat_key':'left_ear_phi','weight':1,'norm':'zscore_all'}, {'feat_key':'right_ear_phi','weight':1,'norm':'zscore_all'}, {'feat_key':'body_length','weight':1,'norm':'zscore_all'}, {'feat_key':'head_length','weight':1,'norm':'zscore_all'}, {'feat_key':'head_body_angles','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_rho','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_phi_c','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_phi_s','weight':1,'norm':'zscore_all'}, {'feat_key':'nose_fft_amp','weight':1,'norm':'zscore_all'}, {'feat_key':'nose_fft_ang','weight':1,'norm':'zscore_all'}, {'feat_key':'contourPCA_fft_amp','weight':1,'norm':'zscore_all'}, {'feat_key':'contourPCA_fft_ang','weight':1,'norm':'zscore_all'}, {'feat_key':'body_change_ang','weight':1,'norm':'zscore_all'}, {'feat_key':'left_ear_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'right_ear_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'left_ear_phi_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'right_ear_phi_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'body_length_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'head_length_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'head_body_angles_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_rho_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_phi_c_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'displace_phi_s_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'nose_fft_amp_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'nose_fft_ang_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'contourPCA_fft_amp_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'contourPCA_fft_ang_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'body_change_ang_TO','weight':1,'norm':'zscore_all'}, {'feat_key':'TM_nose_RM_tail_displace_phi','weight':4,'norm':'zscore_all'}, {'feat_key':'TM_nose_RM_tail_displace_rho','weight':4,'norm':'zscore_all'}, {'feat_key':'RM_nose_TM_tail_displace_phi','weight':4,'norm':'zscore_all'}, {'feat_key':'RM_nose_TM_tail_displace_rho','weight':4,'norm':'zscore_all'}, {'feat_key':'nose_nose_displace_rho','weight':4,'norm':'zscore_all'}, {'feat_key':'nose_nose_displace_phi','weight':4,'norm':'zscore_all'}, {'feat_key':'two_body_ang','weight':4,'norm':'zscore_all'}, {'feat_key':'two_head_ang','weight':4,'norm':'zscore_all'}, ], }, ]
-
Change the threshold for distance between two mice to include only mice that are within 1.8 body length
self.distance_threshold = 1.8
- Specify the directory to save the generated videos
self.gen_video_folder = # where the generated videos will be saved
- Specify the directory to save the metadata which will be used for inspecting the clustering results
self.result_folder = # where the metadata will be saved
- Specify the suffix for generated videos
self.video_name_suffix = # suffix for generated videos
Run the following command in the current folder
bash run_all.sh
Run the following command in the current folder
python fft_main_sep_twoMiceInteract.py
There are two steps to add feature for clustering:
- Define the new feature ./fft_utils.py as the following template (you can find this template in ./fft_utils.py ;
## you can process data to get the feature
## the pose data are in five variables: pose_clips, pose_clips_align, poseTheOther_clips, poseTheOther_clips_alignSelf, poseTheOther_clips_alignToOther
## each of the variables is a numpy array whose shape is (number_of_clip, number_of_frames_in_one_clip, number_of_key_point, 3)
## pose_clips contains the raw key points data of the target mouse
## pose_clips_align contains key point data that is aligned to the target mouse in the middle frame
## poseTheOther_clips contains the raw key points data of the mouse that is closest to the target mouse
## poseTheOther_clips_alignSelf contains the key points data of the closest mousethat that is aligned to itself in the middle frame
## poseTheOther_clips_alignToOther contains the key points data of the closest mousethat that is aligned to the target mouse in the middle frame
newFeature = np.ones(pose_clips.shape[1]) # the feature of one clip should be a numpy array whose shape is the frame number of the clip
if 'newFeatureName' in feature_clips_dict:
feature_clips_dict['newFeatureName'].append(newFeature)
else:
feature_clips_dict['newFeatureName'] = [newFeature]
- define the weight and normalization of the new feature in ./utils_file/setting.py :
self.cluster_arg = [
{
'thred':30,
'name':'all_twoMice',
'evaluation_metric':'Adjusted Rand index',
'features_arg':[\
{'feat_key':'newFeatureName','weight':4,'norm':'zscore_all'}, # add the setting of the new feature here
{'feat_key':'body_length','weight':1,'norm':'zscore_all'},
{'feat_key':'head_length','weight':1,'norm':'zscore_all'},
{'feat_key':'head_body_angles','weight':1,'norm':'zscore_all'},
{'feat_key':'displace_rho','weight':1,'norm':'zscore_all'},
{'feat_key':'displace_phi_c','weight':1,'norm':'zscore_all'},
],
},
]
Run the following command in the current folder
python fft_main_sep_twoMiceInteract.py
Detailed instructions are included in the jupyter notebook
-
Dendrogram
-
Timeline
-
UMAP
-
Mutual information plots
-
Similarity matrix between clusters
Detailed instructions are included in the jupyter notebook
-
Individual cluster skeletons
-
Social behaviror cluster skeletons