# Path: molyso/mm/tracking_output.py
# def s_to_h(s):
#     """
#     converts seconds to hours
#     :param s: seconds
#     :return: hours
#     """
#     return s / (60.0 * 60.0)
# 
# Path: molyso/generic/etc.py
# class QuickTableDumper(object):
# 
#     """
# 
#     :param recipient:
#     """
#     delimiter = '\t'
#     line_end = '\n'
# 
#     precision = 8
# 
#     def __init__(self, recipient=None):
#         if recipient is None:
#             recipient = sys.stdout
# 
#         self.recipient = recipient
#         self.headers = []
# 
#     def write_list(self, the_list):
#         """
# 
#         :param the_list:
#         """
#         self.recipient.write(self.delimiter.join(map(self.stringify, the_list)) + self.line_end)
# 
#     def add(self, row):
#         """
# 
#         :param row:
#         """
#         if len(self.headers) == 0:
#             self.headers = list(sorted(row.keys()))
#             self.write_list(self.headers)
# 
#         self.write_list(row[k] for k in self.headers)
# 
#     def stringify(self, obj):
#         """
# 
#         :param obj:
#         :return:
#         """
#         if type(obj) in (float, np.float32, np.float64) and self.precision:
#             return str(round(obj, self.precision))
#         else:
#             return str(obj)
# 
# Path: molyso/mm/fluorescence.py
# class FluorescentChannel(Channel):
#     """
#     A subclass to handle fluorescences.
# 
#     :param image:
#     :param left:
#     :param right:
#     :param top:
#     :param bottom:
#     """
#     __slots__ = 'fluorescences_channel_image'
#     cells_type = FluorescentCells
# 
#     def __init__(self, image, left, right, top, bottom):
#         super(FluorescentChannel, self).__init__(image, left, right, top, bottom)
# 
#         fluorescences_count = len(image.image_fluorescences)
# 
#         self.fluorescences_channel_image = [None] * fluorescences_count
# 
#         for f in range(fluorescences_count):
#             if image.image_fluorescences[f] is None:
#                 continue
# 
#             self.fluorescences_channel_image[f] = self.crop_out_of_image(image.image_fluorescences[f])


import numpy as np
import time
import json
import jsonpickle
import jsonpickle.ext.numpy as jsonpickle_numpy
        import matplotlib.pyplot as plt
                import code
from .tracking_output import s_to_h
from ..generic.etc import QuickTableDumper
from .fluorescence import FluorescentChannel

                timepoints = pixels_to_timepoints(x)

                t_deltas = timepoints[1:] - timepoints[:-1]
                indices_to_keep = np.r_[[True], t_deltas != 0]

                x, u_y, l_y = x[indices_to_keep], u_y[indices_to_keep], l_y[indices_to_keep]

                timepoints = pixels_to_timepoints(x)
                times = timepoints_to_time(timepoints)

                height_deltas = u_y - l_y

                height_deltas *= calibration_px_to_mu  # important

                height_development = np.c_[s_to_h(times), height_deltas]
                height_development = height_development[1:, :] - height_development[:-1, :]

                changes = height_development.copy()
                changes = changes[:, 1] / changes[:, 0]

                try:
                    average_elongation = np.average(changes, weights=height_development[:, 0])
                except ZeroDivisionError:
                    average_elongation = float('NaN')

                p_results[polyline_num] = {
                    'growth_start': s_to_h(times[0]),
                    'growth_end':  s_to_h(times[-1]),
                    'division_age': s_to_h(times[-1] - times[0]),

# Path: molyso/mm/tracking_output.py
# def s_to_h(s):
#     """
#     converts seconds to hours
#     :param s: seconds
#     :return: hours
#     """
#     return s / (60.0 * 60.0)
# 
# Path: molyso/generic/etc.py
# class QuickTableDumper(object):
# 
#     """
# 
#     :param recipient:
#     """
#     delimiter = '\t'
#     line_end = '\n'
# 
#     precision = 8
# 
#     def __init__(self, recipient=None):
#         if recipient is None:
#             recipient = sys.stdout
# 
#         self.recipient = recipient
#         self.headers = []
# 
#     def write_list(self, the_list):
#         """
# 
#         :param the_list:
#         """
#         self.recipient.write(self.delimiter.join(map(self.stringify, the_list)) + self.line_end)
# 
#     def add(self, row):
#         """
# 
#         :param row:
#         """
#         if len(self.headers) == 0:
#             self.headers = list(sorted(row.keys()))
#             self.write_list(self.headers)
# 
#         self.write_list(row[k] for k in self.headers)
# 
#     def stringify(self, obj):
#         """
# 
#         :param obj:
#         :return:
#         """
#         if type(obj) in (float, np.float32, np.float64) and self.precision:
#             return str(round(obj, self.precision))
#         else:
#             return str(obj)
# 
# Path: molyso/mm/fluorescence.py
# class FluorescentChannel(Channel):
#     """
#     A subclass to handle fluorescences.
# 
#     :param image:
#     :param left:
#     :param right:
#     :param top:
#     :param bottom:
#     """
#     __slots__ = 'fluorescences_channel_image'
#     cells_type = FluorescentCells
# 
#     def __init__(self, image, left, right, top, bottom):
#         super(FluorescentChannel, self).__init__(image, left, right, top, bottom)
# 
#         fluorescences_count = len(image.image_fluorescences)
# 
#         self.fluorescences_channel_image = [None] * fluorescences_count
# 
#         for f in range(fluorescences_count):
#             if image.image_fluorescences[f] is None:
#                 continue
# 
#             self.fluorescences_channel_image[f] = self.crop_out_of_image(image.image_fluorescences[f])


# Path: molyso/mm/highlevel_interactive_advanced_ground_truth.py
import numpy as np
import time
import json
import jsonpickle
import jsonpickle.ext.numpy as jsonpickle_numpy
        import matplotlib.pyplot as plt
                import code
from .tracking_output import s_to_h
from ..generic.etc import QuickTableDumper
from .fluorescence import FluorescentChannel


                timepoints = pixels_to_timepoints(x)

                t_deltas = timepoints[1:] - timepoints[:-1]
                indices_to_keep = np.r_[[True], t_deltas != 0]

                x, u_y, l_y = x[indices_to_keep], u_y[indices_to_keep], l_y[indices_to_keep]

                timepoints = pixels_to_timepoints(x)
                times = timepoints_to_time(timepoints)

                height_deltas = u_y - l_y

                height_deltas *= calibration_px_to_mu  # important

                height_development = np.c_[s_to_h(times), height_deltas]
                height_development = height_development[1:, :] - height_development[:-1, :]

                changes = height_development.copy()
                changes = changes[:, 1] / changes[:, 0]

                try:
                    average_elongation = np.average(changes, weights=height_development[:, 0])
                except ZeroDivisionError:
                    average_elongation = float('NaN')

                p_results[polyline_num] = {
                    'growth_start': s_to_h(times[0]),
                    'growth_end':  s_to_h(times[-1]),
                    'division_age': s_to_h(times[-1] - times[0]),

                    'growth_rate': np.log(2) / s_to_h(times[-1] - times[0]),