# vi: ts=4 sw=4
'''AreaDetector Devices

`areaDetector`_ detector abstractions

.. _areaDetector: https://areadetector.github.io/master/index.html
'''
import warnings

from .base import (ADBase, ADComponent as C)
from . import cam


__all__ = ['DetectorBase',
           'AreaDetector',
           'AdscDetector',
           'Andor3Detector',
           'AndorDetector',
           'BrukerDetector',
           'DexelaDetector',
           'EmergentVisionDetector',
           'EigerDetector',
           'FirewireLinDetector',
           'FirewireWinDetector',
           'GreatEyesDetector',
           'LightFieldDetector',
           'Mar345Detector',
           'MarCCDDetector',
           'PSLDetector',
           'PerkinElmerDetector',
           'PICamDetector',
           'PilatusDetector',
           'PixiradDetector',
           'PointGreyDetector',
           'ProsilicaDetector',
           'PvcamDetector',
           'RoperDetector',
           'SimDetector',
           'URLDetector',
           'UVCDetector',
           'Xspress3Detector'
           ]


class DetectorBase(ADBase):
    """
    The base class for the hardware-specific classes that follow.

    Note that Plugin also inherits from ADBase.
    This adds some AD-specific methods that are not shared by the plugins.
    """

    _default_configuration_attrs = (ADBase._default_configuration_attrs +
                                    ('cam', ))

    def generate_datum(self, key, timestamp, datum_kwargs=None):
        """
        Notify plugins of acquisition being complete.

        When a new acquisition is started, this method is called with a
        key which is a label like 'light', 'dark', or 'gain8'.

        It in turn calls ``generate_datum`` on all of the plugins that have
        that method.

        File plugins are identified by searching for a
        :meth:`~ophyd.areadetector.filestore_mixins.FileStoreBase.generate_datum`
        method that must have the signature ::

           def generate_datum(key: str, timestamp: float, datum_kwargs: dict):
              ...

        Parameters
        ----------
        key : str
            The label for the datum that should be generated

        timestamp : float
            The time of the trigger

        datum_kwargs : Dict[str, Any], optional
            Any datum kwargs that should go to all children.
        """
        if datum_kwargs is None:
            datum_kwargs = {}
        file_plugins = [s for s in self._signals.values() if
                        hasattr(s, 'generate_datum')]
        for p in file_plugins:
            if p.enable.get():
                p.generate_datum(key, timestamp, datum_kwargs)

    def dispatch(self, key, timestamp):
        warnings.warn(
            ".dispatch is deprecated, use .generate_datum instead",
            stacklevel=2
        )

        return self.generate_datum(key, timestamp, {})

    dispatch.__doc__ = generate_datum.__doc__

    def make_data_key(self):
        source = 'PV:{}'.format(self.prefix)
        # This shape is expected to match arr.shape for the array.
        shape = (self.cam.num_images.get(),
                 self.cam.array_size.array_size_y.get(),
                 self.cam.array_size.array_size_x.get())
        return dict(shape=shape, source=source, dtype='array',
                    external='FILESTORE:')

    def collect_asset_docs(self):
        file_plugins = [s for s in self._signals.values() if
                        hasattr(s, 'collect_asset_docs')]
        for p in file_plugins:
            yield from p.collect_asset_docs()


class AreaDetector(DetectorBase):
    cam = C(cam.AreaDetectorCam, 'cam1:')


class SimDetector(DetectorBase):
    _html_docs = ['simDetectorDoc.html']
    cam = C(cam.SimDetectorCam, 'cam1:')


class AdscDetector(DetectorBase):
    _html_docs = ['adscDoc.html']
    cam = C(cam.AdscDetectorCam, 'cam1:')


class AndorDetector(DetectorBase):
    _html_docs = ['andorDoc.html']
    cam = C(cam.AndorDetectorCam, 'cam1:')


class Andor3Detector(DetectorBase):
    _html_docs = ['andor3Doc.html']
    cam = C(cam.Andor3DetectorCam, 'cam1:')


class BrukerDetector(DetectorBase):
    _html_docs = ['BrukerDoc.html']
    cam = C(cam.BrukerDetectorCam, 'cam1:')


class DexelaDetector(DetectorBase):
    _html_docs = ['DexelaDoc.html']
    cam = C(cam.DexelaDetectorCam, 'cam1:')


class EmergentVisionDetector(DetectorBase):
    _html_docs = ['EVTDoc.html']
    cam = C(cam.EmergentVisionDetectorCam, 'cam1:')


class EigerDetector(DetectorBase):
    _html_docs = ['EigerDoc.html']
    cam = C(cam.EigerDetectorCam, 'cam1:')


class FirewireLinDetector(DetectorBase):
    _html_docs = ['FirewireWinDoc.html']
    cam = C(cam.FirewireLinDetectorCam, 'cam1:')


class FirewireWinDetector(DetectorBase):
    _html_docs = ['FirewireWinDoc.html']
    cam = C(cam.FirewireWinDetectorCam, 'cam1:')


class GreatEyesDetector(DetectorBase):
    _html_docs = []  # the documentation is not public
    cam = C(cam.GreatEyesDetectorCam, 'cam1:')


class LightFieldDetector(DetectorBase):
    _html_docs = ['LightFieldDoc.html']
    cam = C(cam.LightFieldDetectorCam, 'cam1:')


class Mar345Detector(DetectorBase):
    _html_docs = ['Mar345Doc.html']
    cam = C(cam.Mar345DetectorCam, 'cam1:')


class MarCCDDetector(DetectorBase):
    _html_docs = ['MarCCDDoc.html']
    cam = C(cam.MarCCDDetectorCam, 'cam1:')


class PerkinElmerDetector(DetectorBase):
    _html_docs = ['PerkinElmerDoc.html']
    cam = C(cam.PerkinElmerDetectorCam, 'cam1:')


class PSLDetector(DetectorBase):
    _html_docs = ['PSLDoc.html']
    cam = C(cam.PSLDetectorCam, 'cam1:')


class PICamDetector(DetectorBase):
    _html_docs = ['PICamDoc.html']
    cam = C(cam.PICamDetectorCam, 'cam1:')


class PilatusDetector(DetectorBase):
    _html_docs = ['pilatusDoc.html']
    cam = C(cam.PilatusDetectorCam, 'cam1:')


class PixiradDetector(DetectorBase):
    _html_docs = ['PixiradDoc.html']
    cam = C(cam.PixiradDetectorCam, 'cam1:')


class PointGreyDetector(DetectorBase):
    _html_docs = ['PointGreyDoc.html']
    cam = C(cam.PointGreyDetectorCam, 'cam1:')


class ProsilicaDetector(DetectorBase):
    _html_docs = ['prosilicaDoc.html']
    cam = C(cam.ProsilicaDetectorCam, 'cam1:')


class PvcamDetector(DetectorBase):
    _html_docs = ['pvcamDoc.html']
    cam = C(cam.PvcamDetectorCam, 'cam1:')


class RoperDetector(DetectorBase):
    _html_docs = ['RoperDoc.html']
    cam = C(cam.RoperDetectorCam, 'cam1:')


class URLDetector(DetectorBase):
    _html_docs = ['URLDoc.html']
    cam = C(cam.URLDetectorCam, 'cam1:')


class UVCDetector(DetectorBase):
    _html_docs = ['UVCDoc.html']
    cam = C(cam.UVCDetectorCam, 'cam1:')


class Xspress3Detector(DetectorBase):
    _html_docs = ['Xspress3Doc.html']
    cam = C(cam.Xspress3DetectorCam, 'det1:')

[((93, 8, 96, 9), 'warnings.warn', 'warnings.warn', (), '', False, 'import warnings\n')]