boris-behav-obs 8.12__py3-none-any.whl → 9.7.6__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of boris-behav-obs might be problematic. Click here for more details.

Files changed (128) hide show
  1. boris/__init__.py +1 -1
  2. boris/__main__.py +1 -1
  3. boris/about.py +28 -39
  4. boris/add_modifier.py +122 -109
  5. boris/add_modifier_ui.py +239 -135
  6. boris/advanced_event_filtering.py +81 -45
  7. boris/analysis_plugins/__init__.py +0 -0
  8. boris/analysis_plugins/_latency.py +59 -0
  9. boris/analysis_plugins/irr_cohen_kappa.py +109 -0
  10. boris/analysis_plugins/irr_cohen_kappa_with_modifiers.py +112 -0
  11. boris/analysis_plugins/irr_weighted_cohen_kappa.py +157 -0
  12. boris/analysis_plugins/irr_weighted_cohen_kappa_with_modifiers.py +162 -0
  13. boris/analysis_plugins/list_of_dataframe_columns.py +22 -0
  14. boris/analysis_plugins/number_of_occurences.py +22 -0
  15. boris/analysis_plugins/number_of_occurences_by_independent_variable.py +54 -0
  16. boris/analysis_plugins/time_budget.py +61 -0
  17. boris/behav_coding_map_creator.py +228 -229
  18. boris/behavior_binary_table.py +33 -50
  19. boris/behaviors_coding_map.py +17 -18
  20. boris/boris_cli.py +6 -25
  21. boris/cmd_arguments.py +12 -1
  22. boris/coding_pad.py +42 -49
  23. boris/config.py +141 -65
  24. boris/config_file.py +58 -67
  25. boris/connections.py +107 -61
  26. boris/converters.py +13 -37
  27. boris/converters_ui.py +187 -110
  28. boris/cooccurence.py +250 -0
  29. boris/core.py +2373 -1786
  30. boris/core_qrc.py +15895 -10743
  31. boris/core_ui.py +943 -798
  32. boris/db_functions.py +17 -42
  33. boris/dev.py +109 -8
  34. boris/dialog.py +482 -236
  35. boris/duration_widget.py +9 -14
  36. boris/edit_event.py +61 -31
  37. boris/edit_event_ui.py +208 -97
  38. boris/event_operations.py +408 -293
  39. boris/events_cursor.py +25 -17
  40. boris/events_snapshots.py +36 -82
  41. boris/exclusion_matrix.py +4 -9
  42. boris/export_events.py +184 -223
  43. boris/export_observation.py +74 -100
  44. boris/external_processes.py +123 -98
  45. boris/geometric_measurement.py +644 -290
  46. boris/gui_utilities.py +91 -14
  47. boris/image_overlay.py +4 -4
  48. boris/import_observations.py +190 -98
  49. boris/ipc_mpv.py +325 -0
  50. boris/irr.py +20 -57
  51. boris/latency.py +31 -24
  52. boris/measurement_widget.py +14 -18
  53. boris/media_file.py +17 -19
  54. boris/menu_options.py +17 -6
  55. boris/modifier_coding_map_creator.py +1013 -0
  56. boris/modifiers_coding_map.py +7 -9
  57. boris/mpv.py +1 -0
  58. boris/mpv2.py +732 -705
  59. boris/observation.py +533 -221
  60. boris/observation_operations.py +1025 -390
  61. boris/observation_ui.py +572 -362
  62. boris/observations_list.py +71 -53
  63. boris/otx_parser.py +74 -68
  64. boris/param_panel.py +31 -16
  65. boris/param_panel_ui.py +254 -138
  66. boris/player_dock_widget.py +90 -60
  67. boris/plot_data_module.py +25 -33
  68. boris/plot_events.py +127 -90
  69. boris/plot_events_rt.py +17 -31
  70. boris/plot_spectrogram_rt.py +95 -30
  71. boris/plot_waveform_rt.py +32 -21
  72. boris/plugins.py +431 -0
  73. boris/portion/__init__.py +18 -8
  74. boris/portion/const.py +35 -18
  75. boris/portion/dict.py +5 -5
  76. boris/portion/func.py +2 -2
  77. boris/portion/interval.py +21 -41
  78. boris/portion/io.py +41 -32
  79. boris/preferences.py +306 -83
  80. boris/preferences_ui.py +684 -227
  81. boris/project.py +448 -293
  82. boris/project_functions.py +671 -238
  83. boris/project_import_export.py +213 -222
  84. boris/project_ui.py +674 -438
  85. boris/qrc_boris.py +6 -3
  86. boris/qrc_boris5.py +6 -3
  87. boris/select_modifiers.py +74 -48
  88. boris/select_observations.py +20 -198
  89. boris/select_subj_behav.py +67 -39
  90. boris/state_events.py +52 -35
  91. boris/subjects_pad.py +6 -9
  92. boris/synthetic_time_budget.py +45 -28
  93. boris/time_budget_functions.py +171 -171
  94. boris/time_budget_widget.py +84 -114
  95. boris/transitions.py +41 -47
  96. boris/utilities.py +627 -236
  97. boris/version.py +3 -3
  98. boris/video_equalizer.py +16 -14
  99. boris/video_equalizer_ui.py +199 -130
  100. boris/video_operations.py +95 -29
  101. boris/view_df.py +104 -0
  102. boris/view_df_ui.py +75 -0
  103. boris/write_event.py +538 -0
  104. boris_behav_obs-9.7.6.dist-info/METADATA +139 -0
  105. boris_behav_obs-9.7.6.dist-info/RECORD +109 -0
  106. {boris_behav_obs-8.12.dist-info → boris_behav_obs-9.7.6.dist-info}/WHEEL +1 -1
  107. boris_behav_obs-9.7.6.dist-info/entry_points.txt +2 -0
  108. boris/README.TXT +0 -22
  109. boris/add_modifier.ui +0 -323
  110. boris/converters.ui +0 -289
  111. boris/core.qrc +0 -36
  112. boris/core.ui +0 -1556
  113. boris/edit_event.ui +0 -233
  114. boris/icons/logo_eye.ico +0 -0
  115. boris/map_creator.py +0 -850
  116. boris/observation.ui +0 -814
  117. boris/param_panel.ui +0 -379
  118. boris/preferences.ui +0 -537
  119. boris/project.ui +0 -1069
  120. boris/project_server.py +0 -236
  121. boris/vlc.py +0 -10343
  122. boris/vlc_local.py +0 -90
  123. boris_behav_obs-8.12.dist-info/LICENSE.TXT +0 -674
  124. boris_behav_obs-8.12.dist-info/METADATA +0 -128
  125. boris_behav_obs-8.12.dist-info/RECORD +0 -108
  126. boris_behav_obs-8.12.dist-info/entry_points.txt +0 -3
  127. {boris → boris_behav_obs-9.7.6.dist-info/licenses}/LICENSE.TXT +0 -0
  128. {boris_behav_obs-8.12.dist-info → boris_behav_obs-9.7.6.dist-info}/top_level.txt +0 -0
boris/latency.py CHANGED
@@ -1,7 +1,7 @@
1
1
  """
2
2
  BORIS
3
3
  Behavioral Observation Research Interactive Software
4
- Copyright 2012-2023 Olivier Friard
4
+ Copyright 2012-2025 Olivier Friard
5
5
 
6
6
  This program is free software; you can redistribute it and/or modify
7
7
  it under the terms of the GNU General Public License as published by
@@ -18,9 +18,7 @@ Copyright 2012-2023 Olivier Friard
18
18
  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
19
  MA 02110-1301, USA.
20
20
 
21
- """
22
21
 
23
- """
24
22
  Module for analyzing the latency of behaviors after another behavior(s) (marker)
25
23
 
26
24
  """
@@ -31,7 +29,7 @@ from . import dialog
31
29
  from . import select_observations
32
30
  from . import project_functions, observation_operations
33
31
 
34
- from PyQt5.QtWidgets import QMessageBox
32
+ from PySide6.QtWidgets import QMessageBox
35
33
 
36
34
 
37
35
  def get_latency(self):
@@ -43,10 +41,9 @@ def get_latency(self):
43
41
  None,
44
42
  cfg.programName,
45
43
  (
46
- f"This function is experimental. Please test it and report any bug at <br>"
44
+ "This function is experimental. Please test it and report any bug at <br>"
47
45
  '<a href="https://github.com/olivierfriard/BORIS/issues">'
48
46
  "https://github.com/olivierfriard/BORIS/issues</a><br>"
49
- "or by email (See the About page on the BORIS web site.<br><br>"
50
47
  "Thank you for your collaboration!"
51
48
  ),
52
49
  QMessageBox.Ok | QMessageBox.Default,
@@ -83,10 +80,10 @@ def get_latency(self):
83
80
  )
84
81
  return
85
82
 
86
- parameters = select_subj_behav.choose_obs_subj_behav_category(
83
+ parameters: dict = select_subj_behav.choose_obs_subj_behav_category(
87
84
  self,
88
85
  selected_observations,
89
- flagShowExcludeBehaviorsWoEvents=False,
86
+ show_exclude_non_coded_behaviors=False,
90
87
  window_title="Select the marker behaviors (stimulus)",
91
88
  n_observations=len(selected_observations),
92
89
  )
@@ -102,10 +99,10 @@ def get_latency(self):
102
99
  marker_subjects = parameters[cfg.SELECTED_SUBJECTS]
103
100
  include_marker_modifiers = parameters[cfg.INCLUDE_MODIFIERS]
104
101
 
105
- # print(f"{marker_behaviors=} {marker_subjects=} {include_marker_modifiers=}")
102
+ print(f"{marker_behaviors=} {marker_subjects=} {include_marker_modifiers=}")
106
103
 
107
- parameters = select_subj_behav.choose_obs_subj_behav_category(
108
- self, selected_observations, flagShowExcludeBehaviorsWoEvents=False, window_title="Select the latency behaviors"
104
+ parameters: dict = select_subj_behav.choose_obs_subj_behav_category(
105
+ self, selected_observations, show_exclude_non_coded_behaviors=False, window_title="Select the latency behaviors"
109
106
  )
110
107
  if not parameters[cfg.SELECTED_SUBJECTS] or not parameters[cfg.SELECTED_BEHAVIORS]:
111
108
  return
@@ -113,11 +110,11 @@ def get_latency(self):
113
110
  latency_subjects = parameters[cfg.SELECTED_SUBJECTS]
114
111
  include_latency_modifiers = parameters[cfg.INCLUDE_MODIFIERS]
115
112
 
116
- # print(f"{latency_behaviors=} {latency_subjects=} {include_latency_modifiers=}")
113
+ print(f"{latency_behaviors=} {latency_subjects=} {include_latency_modifiers=}")
117
114
 
118
- results = {}
115
+ results: dict = {}
119
116
  for obs_id in selected_observations:
120
- # print(f"{obs_id=}")
117
+ print(f"{obs_id=}")
121
118
 
122
119
  events_with_status = project_functions.events_start_stop(
123
120
  self.pj[cfg.ETHOGRAM],
@@ -125,7 +122,17 @@ def get_latency(self):
125
122
  self.pj[cfg.OBSERVATIONS][obs_id][cfg.TYPE],
126
123
  )
127
124
 
125
+ print(f"{events_with_status=}")
126
+
128
127
  for idx, event in enumerate(events_with_status):
128
+ print(f"{event=}")
129
+
130
+ print(f"{event[cfg.EVENT_STATUS_FIELD_IDX]=}")
131
+
132
+ print(f"{event[cfg.EVENT_BEHAVIOR_FIELD_IDX]=}")
133
+
134
+ print(f"{event[cfg.EVENT_SUBJECT_FIELD_IDX]=}")
135
+
129
136
  if all(
130
137
  (
131
138
  event[cfg.EVENT_STATUS_FIELD_IDX] in (cfg.START, cfg.POINT),
@@ -138,11 +145,13 @@ def get_latency(self):
138
145
  ),
139
146
  )
140
147
  ):
141
-
142
148
  if include_marker_modifiers:
143
149
  marker = event[cfg.EVENT_TIME_FIELD_IDX : cfg.EVENT_MODIFIER_FIELD_IDX + 1]
144
150
  else:
145
151
  marker = event[cfg.EVENT_TIME_FIELD_IDX : cfg.EVENT_BEHAVIOR_FIELD_IDX + 1]
152
+
153
+ print(f"{marker=}")
154
+
146
155
  if marker not in results:
147
156
  results[marker] = {}
148
157
 
@@ -164,20 +173,19 @@ def get_latency(self):
164
173
  ),
165
174
  )
166
175
  ):
167
-
168
- # print(event, event2)
176
+ print(event, event2)
169
177
  if include_latency_modifiers:
170
178
  latency = event2[cfg.EVENT_SUBJECT_FIELD_IDX : cfg.EVENT_MODIFIER_FIELD_IDX + 1]
171
179
  else:
172
180
  latency = event2[cfg.EVENT_SUBJECT_FIELD_IDX : cfg.EVENT_BEHAVIOR_FIELD_IDX + 1]
173
181
 
174
182
  # print(f"{marker=}")
175
- # print(f"{latency=}")
176
- if not latency in results[marker]:
183
+ print(f"{latency=}")
184
+ if latency not in results[marker]:
177
185
  results[marker][latency] = []
178
- results[marker][latency].append(
179
- event2[cfg.EVENT_TIME_FIELD_IDX] - event[cfg.EVENT_TIME_FIELD_IDX]
180
- )
186
+ results[marker][latency].append(event2[cfg.EVENT_TIME_FIELD_IDX] - event[cfg.EVENT_TIME_FIELD_IDX])
187
+
188
+ print(f"{results[marker][latency]=}")
181
189
 
182
190
  # check if new marker
183
191
  if all(
@@ -208,7 +216,6 @@ def get_latency(self):
208
216
  out = ""
209
217
 
210
218
  for marker in sorted(results.keys()):
211
-
212
219
  subject = cfg.NO_FOCAL_SUBJECT if marker[cfg.EVENT_SUBJECT_FIELD_IDX] == "" else marker[1]
213
220
  if include_marker_modifiers:
214
221
  out += f"Marker: <b>{marker[cfg.EVENT_BEHAVIOR_FIELD_IDX]}</b> at {marker[cfg.EVENT_TIME_FIELD_IDX]} s (subject: {subject} - modifiers: {marker[cfg.EVENT_MODIFIER_FIELD_IDX]})<br><br>"
@@ -223,7 +230,7 @@ def get_latency(self):
223
230
 
224
231
  out += "first occurrence: "
225
232
  out += f"{sorted(results[marker][behav])[0]} s<br>"
226
- out += f"all occurrences: "
233
+ out += "all occurrences: "
227
234
 
228
235
  out += ", ".join([f"{x} s" for x in sorted(results[marker][behav])])
229
236
  out += "<br><br>"
@@ -1,8 +1,7 @@
1
- #!/usr/bin/env python3
2
1
  """
3
2
  BORIS
4
3
  Behavioral Observation Research Interactive Software
5
- Copyright 2012-2023 Olivier Friard
4
+ Copyright 2012-2025 Olivier Friard
6
5
 
7
6
  This file is part of BORIS.
8
7
 
@@ -23,10 +22,10 @@ This file is part of BORIS.
23
22
 
24
23
  import logging
25
24
 
26
- from PyQt5.QtCore import pyqtSignal
25
+ from PySide6.QtCore import Signal
27
26
 
28
- # from PyQt5.QtGui import *
29
- from PyQt5.QtWidgets import (
27
+ # from PySide6.QtGui import *
28
+ from PySide6.QtWidgets import (
30
29
  QApplication,
31
30
  QWidget,
32
31
  QRadioButton,
@@ -40,14 +39,14 @@ from PyQt5.QtWidgets import (
40
39
  QFileDialog,
41
40
  QMessageBox,
42
41
  )
43
- from boris import dialog
44
- from boris.config import YES, NO, CANCEL, programName
42
+ from . import dialog
43
+ from . import config as cfg
45
44
 
46
45
 
47
46
  class wgMeasurement(QWidget):
48
47
  """ """
49
48
 
50
- closeSignal, clearSignal = pyqtSignal(), pyqtSignal()
49
+ closeSignal, clearSignal = Signal(), Signal()
51
50
  flagSaved = True
52
51
  draw_mem = []
53
52
 
@@ -112,7 +111,7 @@ class wgMeasurement(QWidget):
112
111
  self.pbSave = QPushButton("Save results", clicked=self.pbSave_clicked)
113
112
  hbox3.addWidget(self.pbSave)
114
113
 
115
- self.pbClose = QPushButton("Close", clicked=self.pbClose_clicked)
114
+ self.pbClose = QPushButton(cfg.CLOSE, clicked=self.pbClose_clicked)
116
115
  hbox3.addWidget(self.pbClose)
117
116
 
118
117
  vbox.addLayout(hbox3)
@@ -128,13 +127,13 @@ class wgMeasurement(QWidget):
128
127
  def pbClose_clicked(self):
129
128
  if not self.flagSaved:
130
129
  response = dialog.MessageDialog(
131
- programName,
130
+ cfg.programName,
132
131
  "The current results are not saved. Do you want to save results before closing?",
133
- [YES, NO, CANCEL],
132
+ [cfg.YES, cfg.NO, cfg.CANCEL],
134
133
  )
135
- if response == YES:
134
+ if response == cfg.YES:
136
135
  self.pbSave_clicked()
137
- if response == CANCEL:
136
+ if response == cfg.CANCEL:
138
137
  return
139
138
  self.closeSignal.emit()
140
139
 
@@ -143,19 +142,16 @@ class wgMeasurement(QWidget):
143
142
  save results
144
143
  """
145
144
  if self.pte.toPlainText():
146
- fileName, _ = QFileDialog().getSaveFileName(
147
- self, "Save measurement results", "", "Text files (*.txt);;All files (*)"
148
- )
145
+ fileName, _ = QFileDialog().getSaveFileName(self, "Save measurement results", "", "Text files (*.txt);;All files (*)")
149
146
  if fileName:
150
147
  with open(fileName, "w") as f:
151
148
  f.write(self.pte.toPlainText())
152
149
  self.flagSaved = True
153
150
  else:
154
- QMessageBox.information(self, programName, "There are no results to save")
151
+ QMessageBox.information(self, cfg.programName, "There are no results to save")
155
152
 
156
153
 
157
154
  if __name__ == "__main__":
158
-
159
155
  import sys
160
156
 
161
157
  app = QApplication(sys.argv)
boris/media_file.py CHANGED
@@ -1,7 +1,7 @@
1
1
  """
2
2
  BORIS
3
3
  Behavioral Observation Research Interactive Software
4
- Copyright 2012-2023 Olivier Friard
4
+ Copyright 2012-2025 Olivier Friard
5
5
 
6
6
  This file is part of BORIS.
7
7
 
@@ -20,13 +20,13 @@ This file is part of BORIS.
20
20
 
21
21
  """
22
22
 
23
- import logging
23
+ from PySide6.QtWidgets import QFileDialog
24
24
 
25
25
  from . import config as cfg
26
26
  from . import utilities as util
27
27
  from . import dialog
28
28
  from . import project_functions
29
- from PyQt5.QtWidgets import QFileDialog
29
+ from . import utilities as util
30
30
 
31
31
 
32
32
  def get_info(self) -> None:
@@ -34,22 +34,23 @@ def get_info(self) -> None:
34
34
  show info about media file (current media file if an observation is opened)
35
35
  """
36
36
 
37
- def media_analysis_str(ffmpeg_bin, media_full_path):
38
-
37
+ def media_analysis_str(ffmpeg_bin: str, media_full_path: str) -> str:
39
38
  r = util.accurate_media_analysis(ffmpeg_bin, media_full_path)
40
39
 
41
40
  if "error" in r:
42
41
  ffmpeg_output = f"File path: {media_full_path}<br><br>{r['error']}<br><br>"
43
42
  else:
44
- ffmpeg_output = f"<br><b>{r['analysis_program'] } analysis</b><br>"
43
+ ffmpeg_output = f"<br><b>{r['analysis_program']} analysis</b><br>"
45
44
 
46
45
  ffmpeg_output += (
47
46
  f"File path: <b>{media_full_path}</b><br><br>"
48
47
  f"Duration: {r['duration']} seconds ({util.convertTime(self.timeFormat, r['duration'])})<br>"
49
- f"Resolution: {r['resolution']}<br>"
48
+ f"FPS: {r['fps']}<br>"
49
+ f"Resolution: {r['resolution']} pixels<br>"
50
+ f"Format long name: {r.get('format_long_name', cfg.NA)}<br>"
51
+ f"Creation time: {r.get('creation_time', cfg.NA)}<br>"
50
52
  f"Number of frames: {r['frames_number']}<br>"
51
53
  f"Bitrate: {util.smart_size_format(r['bitrate'])} <br>"
52
- f"FPS: {r['fps']}<br>"
53
54
  f"Has video: {r['has_video']}<br>"
54
55
  f"Has audio: {r['has_audio']}<br>"
55
56
  f"File size: {util.smart_size_format(r.get('file size', cfg.NA))}<br>"
@@ -60,7 +61,6 @@ def get_info(self) -> None:
60
61
  return ffmpeg_output
61
62
 
62
63
  if self.observationId and self.playerType == cfg.MEDIA:
63
-
64
64
  tot_output: str = ""
65
65
 
66
66
  for i, dw in enumerate(self.dw_player):
@@ -72,6 +72,12 @@ def get_info(self) -> None:
72
72
 
73
73
  mpv_output = (
74
74
  "<b>MPV information</b><br>"
75
+ f"Duration: {dw.player.duration} seconds ({util.seconds2time(dw.player.duration)})<br>"
76
+ # "Position: {} %<br>"
77
+ f"FPS: {dw.player.container_fps}<br>"
78
+ # "Rate: {}<br>"
79
+ f"Resolution: {dw.player.width}x{dw.player.height} pixels<br>"
80
+ # "Scale: {}<br>"
75
81
  f"Video format: {dw.player.video_format}<br>"
76
82
  # "State: {}<br>"
77
83
  # "Media Resource Location: {}<br>"
@@ -79,12 +85,6 @@ def get_info(self) -> None:
79
85
  # "Track: {}/{}<br>"
80
86
  f"Number of media in media list: {dw.player.playlist_count}<br>"
81
87
  f"Current time position: {dw.player.time_pos}<br>"
82
- f"duration: {dw.player.duration}<br>"
83
- # "Position: {} %<br>"
84
- f"FPS: {dw.player.container_fps}<br>"
85
- # "Rate: {}<br>"
86
- f"Video size: {dw.player.width}x{dw.player.height}<br>"
87
- # "Scale: {}<br>"
88
88
  f"Aspect ratio: {round(dw.player.width / dw.player.height, 3)}<br>"
89
89
  # "is seekable? {}<br>"
90
90
  # "has_vout? {}<br>"
@@ -101,9 +101,7 @@ def get_info(self) -> None:
101
101
  tot_output += mpv_output + ffmpeg_output + "<br><hr>"
102
102
 
103
103
  else: # no open observation
104
-
105
- fn = QFileDialog().getOpenFileNames(self, "Select a media file", "", "Media files (*)")
106
- file_paths = fn[0] if type(fn) is tuple else fn
104
+ file_paths, _ = QFileDialog().getOpenFileNames(self, "Select a media file", "", "Media files (*)")
107
105
  if not file_paths:
108
106
  return
109
107
 
@@ -112,6 +110,6 @@ def get_info(self) -> None:
112
110
  tot_output += media_analysis_str(self.ffmpeg_bin, file_path)
113
111
 
114
112
  self.results = dialog.Results_dialog()
115
- self.results.setWindowTitle(cfg.programName + " - Media file information")
113
+ self.results.setWindowTitle(f"{cfg.programName} - Media file information")
116
114
  self.results.ptText.appendHtml(tot_output)
117
115
  self.results.show()
boris/menu_options.py CHANGED
@@ -1,7 +1,7 @@
1
1
  """
2
2
  BORIS
3
3
  Behavioral Observation Research Interactive Software
4
- Copyright 2012-2023 Olivier Friard
4
+ Copyright 2012-2025 Olivier Friard
5
5
 
6
6
  This program is free software; you can redistribute it and/or modify
7
7
  it under the terms of the GNU General Public License as published by
@@ -19,9 +19,9 @@ Copyright 2012-2023 Olivier Friard
19
19
  MA 02110-1301, USA.
20
20
  """
21
21
 
22
-
23
22
  import logging
24
23
  from . import config as cfg
24
+ from PySide6.QtCore import QSize
25
25
 
26
26
 
27
27
  def update_windows_title(self):
@@ -57,6 +57,13 @@ def update_menu(self):
57
57
 
58
58
  update_windows_title(self)
59
59
 
60
+ self.toolBar.setIconSize(
61
+ QSize(
62
+ self.config_param.get(cfg.TOOLBAR_ICON_SIZE, cfg.DEFAULT_TOOLBAR_ICON_SIZE_VALUE),
63
+ self.config_param.get(cfg.TOOLBAR_ICON_SIZE, cfg.DEFAULT_TOOLBAR_ICON_SIZE_VALUE),
64
+ )
65
+ )
66
+
60
67
  # enabled if project loaded
61
68
  for action in (
62
69
  self.actionEdit_project,
@@ -65,9 +72,9 @@ def update_menu(self):
65
72
  self.actionExport_project,
66
73
  self.actionCheck_project,
67
74
  self.actionClose_project,
68
- self.actionSend_project,
69
75
  self.actionNew_observation,
70
76
  self.actionRemove_path_from_media_files,
77
+ self.action_create_observations,
71
78
  self.action_obs_list,
72
79
  self.actionExport_observations_list,
73
80
  self.actionExplore_project,
@@ -136,7 +143,10 @@ def update_menu(self):
136
143
  self.actionJumpForward,
137
144
  self.actionJumpBackward,
138
145
  self.actionJumpTo,
146
+ self.action_change_time_offset_of_players,
147
+ self.action_deinterlace,
139
148
  self.actionZoom_level,
149
+ self.actionRotate_current_video,
140
150
  self.actionDisplay_subtitles,
141
151
  self.actionPlay,
142
152
  self.actionReset,
@@ -156,12 +166,12 @@ def update_menu(self):
156
166
  self.menuImage_overlay_on_video_2,
157
167
  self.actionAdd_image_overlay_on_video,
158
168
  self.actionRemove_image_overlay,
169
+ self.actionAdd_frame_indexes,
159
170
  ):
160
-
161
171
  action.setEnabled(self.playerType == cfg.MEDIA)
162
172
 
163
173
  # geometric measurements
164
- self.action_geometric_measurements.setEnabled(observation_is_active and self.geometric_measurements_mode == False)
174
+ self.action_geometric_measurements.setEnabled(observation_is_active and self.geometric_measurements_mode is False)
165
175
  self.actionCoding_pad.setEnabled(observation_is_active)
166
176
  self.actionSubjects_pad.setEnabled(observation_is_active)
167
177
  self.actionBehaviors_coding_map.setEnabled(observation_is_active)
@@ -187,6 +197,7 @@ def update_menu(self):
187
197
  self.action_behavior_binary_table,
188
198
  self.action_advanced_event_filtering,
189
199
  self.action_latency,
200
+ self.action_cooccurence,
190
201
  self.menuPlot_events,
191
202
  self.menuInter_rater_reliability,
192
203
  self.menuSimilarities,
@@ -196,7 +207,7 @@ def update_menu(self):
196
207
  w.setEnabled(project_contains_obs)
197
208
 
198
209
  # statusbar labels
199
- for w in [self.lbTimeOffset, self.lbSpeed, self.lb_obs_time_interval]:
210
+ for w in (self.lbTimeOffset, self.lb_obs_time_interval):
200
211
  w.setVisible(self.playerType == cfg.MEDIA)
201
212
 
202
213
  logging.debug("function: menu_options finished")