This commit is contained in:
2022-09-01 13:29:57 +02:00
parent 1d818568f5
commit a54e580664
3 changed files with 121 additions and 49 deletions

View File

@@ -32,13 +32,13 @@ class MyJsonEncoder(json.JSONEncoder):
class AppCfg(QSettings):
GBL_FLD_SCR_SHOT="global/folder_screenshot"
GEO_OPT_CTR='geometry/opt_ctr'
GEO_PIX2POS='geometry/pix2pos'
GEO_BEAM_SZ="geometry/beam_size"
GEO_BEAM_POS="geometry/beam_pos"
GEO_CAM_PARAM="geometry/cam_param"
WINDOW_GEOMETRY="window/geometry"
WINDOW_SPLITTER="window/splitter"
@@ -147,19 +147,26 @@ class AppCfg(QSettings):
def setValue(self, key: str, val): #overload to debug
# only simple lists, str, int, float can not be serialized nicely
t=type(val)
if key in (AppCfg.GEO_PIX2POS):
if key in (AppCfg.GEO_PIX2POS,):
val=json.dumps(val, cls=MyJsonEncoder)
elif key in (AppCfg.GEO_CAM_PARAM,):
val=json.dumps(val, cls=MyJsonEncoder)
val=val.replace('"',"'")
elif key in (AppCfg.GEO_OPT_CTR,AppCfg.GEO_BEAM_SZ,AppCfg.GEO_BEAM_POS,):
val=val.tolist()
if type(val)==np.ndarray:
val=val.tolist()
elif type(val)==tuple:
val=list(val)
return super(AppCfg, self).setValue(key,val)
def value(self,key,*vargs,**kwargs): #overload to debug
val=super(AppCfg, self).value(key,*vargs,**kwargs)
if key in (AppCfg.GEO_PIX2POS):
if key in (AppCfg.GEO_PIX2POS,):
val=json.loads(val)#, object_hook=MyJsonDecoder)
val=(np.array(val[0]),np.array(val[1]))
if key in (AppCfg.GEO_CAM_PARAM,):
val=val.replace("'",'"')
val=json.loads(val) # , object_hook=MyJsonDecoder)
elif key in (AppCfg.GEO_BEAM_SZ,AppCfg.GEO_BEAM_POS,):
val=np.array(tuple(map(float, val)))/1000
elif key in (AppCfg.GEO_OPT_CTR):

View File

@@ -169,6 +169,54 @@ class epics_cam(object):
pv_w=self.getPv('WIDTH');pv_h=self.getPv('HEIGHT')
self._sz=(int(pv_w.value), int(pv_h.value))
def get_param(self):
param=dict()
pv_gain=self.getPv('AMPGAIN')
pv_exp=self.getPv('EXPOSURE')
pv_bx=self.getPv('BINX');pv_by=self.getPv('BINY')
pv_rxs=self.getPv('REGIONX_START');pv_rxe=self.getPv('REGIONX_END')
pv_rys=self.getPv('REGIONY_START');pv_rye=self.getPv('REGIONY_END')
pv_mono8=self.getPv('FORCEMONO8')
param['gain']=pv_gain.get()
param['exposure']=pv_exp.get()
param['binning']=(pv_bx.get(),pv_by.get())
xs=pv_rxs.get();xe=pv_rxe.get()
ys=pv_rys.get();ye=pv_rye.get()
param['roi']=(xs,ys,xe-xs,ye-ys)
param['mono8']=pv_mono8.get()
return param
def set_param(self,**kwargs):
param=[]
for k,v in kwargs:
if k=='gain':
pv_gain=self.getPv('AMPGAIN')
param.append((pv_gain,v))
elif k=='exposure':
pv_exp=self.getPv('EXPOSURE')
param.append((pv_exp,v))
elif k=='binning':
pv_bx=self.getPv('BINX');pv_by=self.getPv('BINY')
param.append((pv_bx,v[0]))
param.append((pv_by,v[1]))
elif k=='roi':
pv_rxs=self.getPv('REGIONX_START');pv_rxe=self.getPv('REGIONX_END')
pv_rys=self.getPv('REGIONY_START');pv_rye=self.getPv('REGIONY_END')
pv_rxs.put(v[0], wait=False)
pv_rxe.put(v[0]+v[2], wait=False)
pv_rys.put(v[1], wait=False)
pv_rye.put(v[1]+v[3], wait=False)
param.append((pv_rxs,v[0]))
param.append((pv_rxe,v[0]+v[2]))
param.append((pv_rys,v[1]))
param.append((pv_rye,v[1]+v[3]))
elif k=='mono8':
pv_mono8=self.getPv('FORCEMONO8')
param.append((pv_mono8,vv))
self.update_params(param)
def set_exposure(self,exp):
try:
pv_exp=self.getPv('EXPOSURE')

View File

@@ -86,7 +86,7 @@ import qtawesome
import qutilities
from PyQt5 import QtCore, QtGui
from PyQt5.QtCore import Qt, pyqtSlot, QSize, QRegExp, pyqtSignal, QObject, QThread
from PyQt5.QtGui import QKeySequence, QPixmap, QRegExpValidator
from PyQt5.QtGui import QKeySequence, QPixmap, QRegExpValidator, QFont
from PyQt5.QtWidgets import (
QAction, QApplication, QDoubleSpinBox, QFileDialog, QFormLayout, QGridLayout, QGroupBox, QHBoxLayout, QLabel, QLineEdit,
QMessageBox, QPlainTextEdit, QProgressBar, QProgressDialog, QPushButton, QShortcut, QSizePolicy, QSpinBox,
@@ -302,9 +302,10 @@ class WndSwissMx(QMainWindow, Ui_MainWindow):
self._message_critical_fault = QLabel(None)
self._message_critical_fault.setAccessibleName("device_fault")
self.statusbar.insertWidget(0, self._message_critical_fault)
self._lb_coords = QLabel(None)
self._lb_coords.setText("coords")
self.statusbar.addPermanentWidget(self._lb_coords)
self._lb_coords=lbl=QLabel(None)
#f=QFont('monospace', 10)
#lbl.setFont(f)
self.statusbar.addPermanentWidget(lbl)
self._fel_status = QLabel(None)
self._fel_status.setAccessibleName("fel_status_statusbar")
@@ -645,7 +646,25 @@ class WndSwissMx(QMainWindow, Ui_MainWindow):
self.cb_new_frame_sim()
except AttributeError:
self.sigNewCamImg.connect(self.cb_update_img)
app._camera.run(self.cb_new_frame_pv)
cam=app._camera
cfg=app._cfg
param=cam.get_param()
try:
paramSv=cfg.value(AppCfg.GEO_CAM_PARAM)
except AttributeError as e:
cfg.setValue(AppCfg.GEO_CAM_PARAM, param)
else:
for k,v in param.items():
if v!=paramSv[k]:
if type(v)==tuple:
if v==tuple(paramSv[k]):
continue
#cam.set_param(paramSv)
#cfg.setValue(AppCfg.GEO_CAM_PARAM, param)
#break
_log.debug(f'diff:{k},{v} != {paramSv[k]}')
cam.run(self.cb_new_frame_pv)
def cb_new_frame_pv(self, **kwargs):
#thrd=threading.current_thread()
@@ -932,47 +951,40 @@ class WndSwissMx(QMainWindow, Ui_MainWindow):
def cb_mouse_move(self, pos):
app = QApplication.instance()
self._mouse_pos = pos
geo = app._geometry
#pos = pixel position on the widget
task = self.active_task()
xy = self._goImg.mapFromScene(pos)
z = app._zoom.get_val()
#_log.debug('mouse_pos:{} scene_pos:{} zoom:{}'.format(pos,xy,z))
#TODO: implement mouse handling
# if self._ppm_toolbox._force_ppm > 0:
# ppm = self._ppm_toolbox._force_ppm
# else:
try:
ppm = self.ppm_fitter(z)
except:
ppm = 1E3
x, y = xy.x(), xy.y()
try:
bx, by = self.get_beam_mark_on_camera_xy()
except:
bx, by = 500, 500
dx = (x - bx) / ppm
dy = -(y - by) / ppm
try:
fx = self.tweakers["fast_x"].motor.get_position()
fy = self.tweakers["fast_y"].motor.get_position()
fx += dx
fy += dy
except:
fx=fy=0
self._lb_coords.setText(
"\u23FA{:>}:{:>6.0f} {:<.0f}"
"\u23FA{:>}:{:>6.0f} {:<.0f}"
"\u23FA{:>}:{:<.0f}"
"\u23FA{:>}:{:>6.1f} {:<.1f} \u00B5"
"\u23FA{:>}:{:>7.3f} {:<.3f} mm".format(
"Beam at", bx, by,
"Pixel coord ", x, y,
"PPM", ppm,
"Distance to beam", 1000 * dx, 1000 * dy,
"Stage", fx, fy,
)
)
#bm=self._goBeamMarker
#pos=event.scenePos()
pImg=pg.Point(self._goImg.mapFromScene(pos))
pTrk=pg.Point(self._goTracked.mapFromScene(pos))
fx=self.tweakers["fast_x"].get_val()
fy=self.tweakers["fast_y"].get_val()
pTrk=pTrk-(fx,fy)
#s=f'pImg{pImg} pTrk{pTrk} bm._pos_eu{bm._pos_eu}'
s=\
f'img pix ({pImg[0]:>0.1f} {pImg[1]:>0.1f})px \u23A2 ' \
f'dist to beam ({pTrk[0]:>0.6g} {pTrk[1]:>0.6g}mm) '
_log.debug(s)
self._lb_coords.setText(s)
#self._lb_coords.setText(
# "\u23FA{:>}:{:>6.0f} {:<.0f}"
# "\u23FA{:>}:{:>6.0f} {:<.0f}"
# "\u23FA{:>}:{:<.0f}"
# "\u23FA{:>}:{:>6.1f} {:<.1f} \u00B5"
# "\u23FA{:>}:{:>7.3f} {:<.3f} mm".format(
# "Beam at", bx, by,
# "Pixel coord ", x, y,
# "PPM", ppm,
# "Distance to beam", 1000 * dx, 1000 * dy,
# "Stage", fx, fy,
# )
#)
def cb_mouse_click(self, event):
#_log.debug("{}".format(event))
@@ -983,7 +995,8 @@ class WndSwissMx(QMainWindow, Ui_MainWindow):
#_log.debug(f"vb pos {self.vb.mapFromScene(p)}") #pixel position on the scene (including black frame)
#for o in self.vb.childGroup.childItems():
# _log.debug(f"{type(o)} pos {o.mapFromScene(p)}") #pixel position on the scene (including black frame)
_log.debug(f"currentItem:{event.currentItem}")
#_log.debug(f"currentItem:{event.currentItem}")
task = self.active_task()
if task==TASK_SETUP_GEOMETRY_CALIB:
self.mouse_click_event_geometry_calib(event)
@@ -1270,7 +1283,11 @@ class WndSwissMx(QMainWindow, Ui_MainWindow):
import PIL.Image
#img=PIL.Image.fromarray(cam.pic.astype(np.uint8))
try:
pic=cam.pic
pic=cam._pic
mx=pic.max()
if pic.max()>255:
scl=2**int(round(np.log2(mx)-8))
pic=np.array(pic/scl,dtype=np.uint8)
except AttributeError:
sim=app._camera._sim
pic=cam._sim['imgSeq'][sim['imgIdx']]