Commit 72488293 authored by bliss administrator's avatar bliss administrator

First commit with everything

parent fff3304c
Pipeline #3787 failed with stages
stages:
- test
- deploy
test:
stage: test
before_script:
- source activate tango2.7
- conda install --yes git
- git clone https://gitlab.esrf.fr/ID10/id10.git
- conda install --yes --channel http://bcu-ci.esrf.fr/stable --file bliss/requirements-conda.txt
- conda install --yes --channel http://bcu-ci.esrf.fr/stable --file bliss/requirements-test-conda.txt
- pip install bliss/
script: python setup.py test
artifacts:
paths:
- tests/htmlcov/
expire_in: 7 days
pages:
stage: deploy
dependencies:
- test
script:
- mv tests/htmlcov public/
artifacts:
paths:
- public
expire_in: 2 months
only:
- master
GNU GENERAL PUBLIC LICENSE
Version 3, 29 June 2007
ID10 software & configuration
Copyright (C) 2018 BCU Team
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
Also add information on how to contact you by electronic and paper mail.
You should also get your employer (if you work as a programmer) or school,
if any, to sign a "copyright disclaimer" for the program, if necessary.
For more information on this, and how to apply and follow the GNU GPL, see
<http://www.gnu.org/licenses/>.
The GNU General Public License does not permit incorporating your program
into proprietary programs. If your program is a subroutine library, you
may consider it more useful to permit linking proprietary applications with
the library. If this is what you want to do, use the GNU Lesser General
Public License instead of this License. But first, please read
<http://www.gnu.org/philosophy/why-not-lgpl.html>.
include LICENSE
include README.rst
recursive-include tests *
recursive-exclude * __pycache__
recursive-exclude * *.py[co]
recursive-include docs *.rst conf.py Makefile make.bat *.jpg *.png *.gif
============
ID10 project
============
[![build status](https://gitlab.esrf.fr/ID10/id10/badges/master/build.svg)](http://ID10.gitlab-pages.esrf.fr/ID10)
[![coverage report](https://gitlab.esrf.fr/ID10/id10/badges/master/coverage.svg)](http://ID10.gitlab-pages.esrf.fr/id10/htmlcov)
ID10 software & configuration
Latest documentation from master can be found [here](http://ID10.gitlab-pages.esrf.fr/id10)
/id10.rst
/id10.*.rst
/modules.rst
# Minimal makefile for Sphinx documentation
#
# You can set these variables from the command line.
SPHINXOPTS =
SPHINXBUILD = python -msphinx
SPHINXPROJ = id10
SOURCEDIR = .
BUILDDIR = _build
# Put it first so that "make" without argument is like "make help".
help:
@$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
.PHONY: help Makefile
# Catch-all target: route all unknown targets to Sphinx using the new
# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS).
%: Makefile
@$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# id10 documentation build configuration file, created by
# sphinx-quickstart on Fri Jun 9 13:47:02 2017.
#
# This file is execfile()d with the current directory set to its
# containing dir.
#
# Note that not all possible configuration values are present in this
# autogenerated file.
#
# All configuration values have a default; values that are commented out
# serve to show the default.
# If extensions (or modules to document with autodoc) are in another
# directory, add these directories to sys.path here. If the directory is
# relative to the documentation root, use os.path.abspath to make it
# absolute, like shown here.
#
import os
import sys
sys.path.insert(0, os.path.abspath('..'))
import id10
# -- General configuration ---------------------------------------------
# If your documentation needs a minimal Sphinx version, state it here.
#
# needs_sphinx = '1.0'
# Add any Sphinx extension module names here, as strings. They can be
# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom ones.
extensions = ['sphinx.ext.autodoc', 'sphinx.ext.viewcode']
# Add any paths that contain templates here, relative to this directory.
templates_path = ['_templates']
# The suffix(es) of source filenames.
# You can specify multiple suffix as a list of string:
#
# source_suffix = ['.rst', '.md']
source_suffix = '.rst'
# The master toctree document.
master_doc = 'index'
# General information about the project.
project = u'ID10 project'
copyright = u"2018, BCU Team"
author = u"BCU Team"
# The version info for the project you're documenting, acts as replacement
# for |version| and |release|, also used in various other places throughout
# the built documents.
#
# The short X.Y version.
version = id10.__version__
# The full version, including alpha/beta/rc tags.
release = id10.__version__
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
#
# This is also used if you do content translation via gettext catalogs.
# Usually you set "language" from the command line for these cases.
language = None
# List of patterns, relative to source directory, that match files and
# directories to ignore when looking for source files.
# This patterns also effect to html_static_path and html_extra_path
exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store']
# The name of the Pygments (syntax highlighting) style to use.
pygments_style = 'sphinx'
# If true, `todo` and `todoList` produce output, else they produce nothing.
todo_include_todos = False
# -- Options for HTML output -------------------------------------------
# The theme to use for HTML and HTML Help pages. See the documentation for
# a list of builtin themes.
#
html_theme = 'alabaster'
# Theme options are theme-specific and customize the look and feel of a
# theme further. For a list of options available for each theme, see the
# documentation.
#
# html_theme_options = {}
# Add any paths that contain custom static files (such as style sheets) here,
# relative to this directory. They are copied after the builtin static files,
# so a file named "default.css" will overwrite the builtin "default.css".
html_static_path = ['_static']
# -- Options for HTMLHelp output ---------------------------------------
# Output file base name for HTML help builder.
htmlhelp_basename = 'id10doc'
# -- Options for LaTeX output ------------------------------------------
latex_elements = {
# The paper size ('letterpaper' or 'a4paper').
#
# 'papersize': 'letterpaper',
# The font size ('10pt', '11pt' or '12pt').
#
# 'pointsize': '10pt',
# Additional stuff for the LaTeX preamble.
#
# 'preamble': '',
# Latex figure (float) alignment
#
# 'figure_align': 'htbp',
}
# Grouping the document tree into LaTeX files. List of tuples
# (source start file, target name, title, author, documentclass
# [howto, manual, or own class]).
latex_documents = [
(master_doc, 'id10.tex',
u'ID10 project Documentation',
u'BCU Team', 'manual'),
]
# -- Options for manual page output ------------------------------------
# One entry per manual page. List of tuples
# (source start file, name, description, authors, manual section).
man_pages = [
(master_doc, 'id10',
u'ID10 project Documentation',
[author], 1)
]
# -- Options for Texinfo output ----------------------------------------
# Grouping the document tree into Texinfo files. List of tuples
# (source start file, target name, title, author,
# dir menu entry, description, category)
texinfo_documents = [
(master_doc, 'id10',
u'ID10 project Documentation',
author,
'id10',
'One line description of project.',
'Miscellaneous'),
]
Welcome to ID10 project's documentation!
======================================
.. toctree::
:maxdepth: 2
:caption: Contents:
readme
usage
modules
Indices and tables
==================
* :ref:`genindex`
* :ref:`modindex`
* :ref:`search`
.. include:: ../README.rst
=====
Usage
=====
To use ID10 project in a project::
import id10
# -*- coding: utf-8 -*-
#
# This file is part of the bliss project
#
# Copyright (c) 2016 Beamline Control Unit, ESRF
# Distributed under the GNU LGPLv3. See LICENSE for more info.
"""
Class to move 'together' delta motor and as a consequence the
motors ypipe and ydet are moved for the sufficient amount to
follow delta rotation, so that detector ALWAYS POINTS TO THE SAMPLE.
_____
| _____
| _____
| | _____
ydet | _____
| ypipe / _____
| | delta _____
___|_________|________\______________ Sample <-------- BEAM
|<--- pipe supp. to sample -->|
|<---- detector support to sample ----->|
Real motor roles:
* *delta*: rotation of ....
* *ypipe*: translation of 'pipe' support along y (horizontal) axis.
* *ydet*: translation of detector support along y (horizontal) axis.
Calc. motor roles:
* *delcoup*: angle equal to delta
Configuration parameters:
* *samptopipe*: sample-to-pipe support distance [mm]
* *samptodet*: sample-to-detector support distance [mm]
Example configuration::
Controller:
class: deltacoup
name: deltacoup
description: EH2 pipe and detector lateral translation to follow delta
samptopipe: 3000.
samptodet: 5200.
axes:
- name: $delta
tags: real rotation
- name: $ypipe
tags: real translation
- name: $ydet
tags: real translation
- name: delcoup
description: angle equal to delta
tags:delcoup
low_limit: 0.0
high_limit: 30.0
user_tag:
- EH2.DELCOUP
"""
from bliss.config import settings
from bliss.controllers.motor import CalcController
import math
class deltacoup(CalcController):
def __init__(self, *args, **kwargs):
#CalcController.__init__(self, *args, **kwargs)
super(deltacoup, self).__init__(*args, **kwargs)
hash_name = 'id10.deltacoup'
ctrl_name = self.config.get('name', default=None)
if ctrl_name:
hash_name += '.%s' % ctrl_name
self._samptopipe = settings.SimpleSetting(hash_name + '.samptopipe')
self._samptodet = settings.SimpleSetting(hash_name + '.samptodet')
self._coupling = settings.SimpleSetting(hash_name + '.coupling', default_value=True)
@property
def samptopipe(self):
return self._samptopipe.get()
@samptopipe.setter
def samptopipe(self, value):
self._samptopipe.set(value)
@property
def samptodet(self):
return self._samptodet.get()
@samptodet.setter
def samptodet(self, value):
self._samptodet.set(value)
@property
def coupling(self):
return self._coupling.get()
@coupling.setter
def coupling(self, value):
self._coupling.set(value)
def calc_from_real(self, positions_dict):
'''
Returns calculated/virtual motor "delcoup" position from real one
("delta").
Remark: Normally will NEVER derive calculated/virtual motor,
but will rather move it and as a consequence the 3
real motors ("delta", "ypipe" and "ydet") will be moved.
Units:
Calculated/virtual rotation motor "delcoup" = in degrees.
'''
# delcoup position value = delta position value when "coupled"
delcoup_position = positions_dict["delta"]
return dict(delcoup=delcoup_position)
def calc_to_real(self, positions_dict):
'''
Returns real motors positions of motors "delta", "ypipe" and
"ydet" (as a dictionary) given virtual one ("delcoup") and
sample to ypipe and sample to detector distances.
Units:
delta_position = in degrees
delcoup_position = in degrees
ypipe_position = in mm
ydet_position = in mm
'''
if self.coupling == True:
delcoup_position = positions_dict["delcoup"]
delta_position = delcoup_position
ypipe_position = -self.samptopipe * math.tan((delcoup_position-20.)/180. * math.pi)
ydet_position = -self.samptodet * math.tan((delcoup_position-20)/180. * math.pi)
return dict(delta=delta_position,ypipe=ypipe_position,ydet=ydet_position)
else:
return {}
def __repr__(self):
ctrl_name = self.config.get('name', default=None)
name = 'DELTACOUP' + ('' if ctrl_name is None else ' ' + ctrl_name)
return "{name}:\n" \
" .samptopipe = {0.samptopipe} mm\n" \
" .samptodet = {0.samptodet} mm\n" \
" .coupling = {0.coupling}".format(self, name=name)
......@@ -56,7 +56,7 @@ controller:
class: gammacoup
name: gammacoup
description: EH2 detector translation and rotation
samptor3: 50.
samptor3: 700.
axes:
- name: $r3
tags: real rotation
......@@ -72,28 +72,43 @@ controller:
"""
from bliss.config import settings
from bliss.controllers.motor import CalcController
import math
class gammacoup(CalcController):
def __init__(self, *args, **kwargs):
CalcController.__init__(self, *args, **kwargs)
self.z3_offset = z3.position()
self.gam_offset = gam.position()
# Sample-r3 distance
self.samptor3 = self.config.get("samptor3", float)
self.coupling = True
def re_initialize(self, samptor3_dist=0):
self.z3_offset = z3.position()
self.gam_offset = gam.position()
if samptor3_dist == 0:
samptor3 = raw_input("Enter sample to R3 distance[mm] ")
# By default set coupling between (r3,z3) and (gam) ON
def couponoff(flag=True):
self.coupling = flag
#CalcController.__init__(self, *args, **kwargs)
super(gammacoup, self).__init__(*args, **kwargs)
hash_name = 'id10.gammacoup'
ctrl_name = self.config.get('name', default=None)
if ctrl_name:
hash_name += '.%s' % ctrl_name
self._samptor3 = settings.SimpleSetting(hash_name + '.samptor3')
self._coupling = settings.SimpleSetting(hash_name + '.coupling', default_value=True)
@property
def samptor3(self):
return self._samptor3.get()
@samptor3.setter
def samptor3(self, value):
self._samptor3.set(value)
@property
def coupling(self):
return self._coupling.get()
@coupling.setter
def coupling(self, value):
self._coupling.set(value)
def calc_from_real(self, positions_dict):
'''
......@@ -108,9 +123,7 @@ class gammacoup(CalcController):
'''
# gam position value = r3 position value when "coupled"
#gam_position = r3.position()
gam_position = gam.position()
gam_position = positions_dict["r3"]
return dict(gam=gam_position)
......@@ -118,22 +131,27 @@ class gammacoup(CalcController):
def calc_to_real(self, positions_dict):
'''
Returns real motors positions of motors "r3" and "z3" (as a
dictionary) given virtual one ("gam").
dictionary) given virtual one ("gam") and sample to r3 distance.
Units:
samptor3 = in mm
z3_offset = in mm
z3_position = in mm
gam_offset = in degrees
gam_position = in degrees
r3_position = in degrees
samptor3 = in mm
z3_position = mm
'''
if self.coupling == True:
gam_position = gam.position()
gam_position = positions_dict["gam"]
r3_position = gam_position
z3_position = self.samptor3 * math.tan((gam_position-self.gam_offset)/180.* math.pi) + self.z3_offset
z3_position = self.samptor3 * math.tan(gam_position/180.* math.pi)
return dict(r3=r3_position,z3=z3_position)
else:
r3_position = r3.position()
z3_position = z3.position()
return {}
return dict(r3=r3_position,z3=z3_position)
def __repr__(self):
ctrl_name = self.config.get('name', default=None)
name = 'GAMMACOUP' + ('' if ctrl_name is None else ' ' + ctrl_name)
return "{name}:\n" \
" .samptor3 = {0.samptor3} mm\n" \
" .coupling = {0.coupling}".format(self, name=name)
......@@ -18,26 +18,21 @@ example for single VERTICAL slits:
-
controller:
class: mockup
axes:
- name: rvg
- name: rvo
-
controller:
class: slits
class: invslits
package: id10.controllers.motors.invslits
slit_type: vertical
axes:
-
name: $rvgap
name: $sgvg
tags: real vgap
-
name: $rvoff
name: $sgvo
tags: real voffset
-
name: cup
name: sgu
tags: up
-
name: cdown
name: sgd
tags: down
"""
......@@ -46,7 +41,7 @@ example for single VERTICAL slits:
default value : both
"""
class InvSlits(CalcController):
class Invslits(CalcController):
def __init__(self, *args, **kwargs):
CalcController.__init__(self, *args, **kwargs)
......
......@@ -28,7 +28,9 @@ Real motor roles:
Calc. motor roles:
* *q45*: "diagonal" move (move of scattering vector)
Configuration parameters:
Configuration parameters (originally put in q45coup.yml file,
but later commented since these parameters can vary and are
now rather ser in redis DB):
* *samptodet*: sample-to-detector distance [mm]
* *lam*: X-ray wavelength [angstroem]
......@@ -37,25 +39,31 @@ Example configuration::
controller:
class: q45coup
package: id10.controllers.motors.q45coup
name: q45coup
description: EH2 detector simultaneous translation in Y and Z
samptodet: .....
lam: .....
#samptodet: 5200
#lam: 1.531
axes:
- name: $ydet
tags: real translation along Y-axis
tags: real ydet
- name: $zdet
tags: real translation along Z-axis
tags: real zdet
- name: q45
description: scattering vector at 45 degrees
tags: q45
#low_limit: 0.0
#high_limit: 90.0
#high_limit: 1.45