| Home | Trees | Indices | Help |
|
|---|
|
|
1 """GNUmed provider inbox handling widgets.
2 """
3 #================================================================
4 __version__ = "$Revision: 1.48 $"
5 __author__ = "Karsten Hilbert <Karsten.Hilbert@gmx.net>"
6
7 import sys, logging
8
9
10 import wx
11
12
13 if __name__ == '__main__':
14 sys.path.insert(0, '../../')
15 from Gnumed.pycommon import gmI18N
16 from Gnumed.pycommon import gmExceptions
17 from Gnumed.pycommon import gmPG2
18 from Gnumed.pycommon import gmCfg
19 from Gnumed.pycommon import gmTools
20 from Gnumed.pycommon import gmDispatcher
21 from Gnumed.pycommon import gmMatchProvider
22
23 from Gnumed.business import gmPerson
24 from Gnumed.business import gmSurgery
25 from Gnumed.business import gmProviderInbox
26
27 from Gnumed.wxpython import gmGuiHelpers
28 from Gnumed.wxpython import gmListWidgets
29 from Gnumed.wxpython import gmPlugin
30 from Gnumed.wxpython import gmRegetMixin
31 from Gnumed.wxpython import gmPhraseWheel
32 from Gnumed.wxpython import gmEditArea
33 from Gnumed.wxpython import gmAuthWidgets
34 from Gnumed.wxpython import gmPatSearchWidgets
35 from Gnumed.wxpython import gmVaccWidgets
36 from Gnumed.wxpython import gmCfgWidgets
37
38
39 _log = logging.getLogger('gm.ui')
40 _log.info(__version__)
41
42 _indicator = {
43 -1: '',
44 0: '',
45 1: '*!!*'
46 }
47 #============================================================
48 from Gnumed.wxGladeWidgets import wxgTextExpansionEditAreaPnl
49
50 -class cTextExpansionEditAreaPnl(wxgTextExpansionEditAreaPnl.wxgTextExpansionEditAreaPnl, gmEditArea.cGenericEditAreaMixin):
51
53
54 try:
55 data = kwds['keyword']
56 del kwds['keyword']
57 except KeyError:
58 data = None
59
60 wxgTextExpansionEditAreaPnl.wxgTextExpansionEditAreaPnl.__init__(self, *args, **kwds)
61 gmEditArea.cGenericEditAreaMixin.__init__(self)
62
63 self.mode = 'new'
64 self.data = data
65 if data is not None:
66 self.mode = 'edit'
67
68 #self.__init_ui()
69 self.__register_interests()
70 #--------------------------------------------------------
75 #----------------------------------------------------------------
76 # generic Edit Area mixin API
77 #----------------------------------------------------------------
79 validity = True
80
81 if self._TCTRL_keyword.GetValue().strip() == u'':
82 validity = False
83 self.display_tctrl_as_valid(tctrl = self._TCTRL_keyword, valid = False)
84 gmDispatcher.send(signal = 'statustext', msg = _('Cannot save text expansion without keyword.'), beep = True)
85 else:
86 self.display_tctrl_as_valid(tctrl = self._TCTRL_keyword, valid = True)
87
88 if self._TCTRL_expansion.GetValue().strip() == u'':
89 validity = False
90 self.display_tctrl_as_valid(tctrl = self._TCTRL_expansion, valid = False)
91 gmDispatcher.send(signal = 'statustext', msg = _('Cannot save text expansion without expansion text.'), beep = True)
92 else:
93 self.display_tctrl_as_valid(tctrl = self._TCTRL_expansion, valid = True)
94
95 return validity
96 #----------------------------------------------------------------
98 kwd = self._TCTRL_keyword.GetValue().strip()
99 saved = gmPG2.add_text_expansion (
100 keyword = kwd,
101 expansion = self._TCTRL_expansion.GetValue(),
102 public = self._RBTN_public.GetValue()
103 )
104 if not saved:
105 return False
106
107 self.data = kwd
108 return True
109 #----------------------------------------------------------------
111 kwd = self._TCTRL_keyword.GetValue().strip()
112 gmPG2.edit_text_expansion (
113 keyword = kwd,
114 expansion = self._TCTRL_expansion.GetValue()
115 )
116 self.data = kwd
117 return True
118 #----------------------------------------------------------------
120 self._TCTRL_keyword.SetValue(u'')
121 self._TCTRL_keyword.Enable(True)
122 self._TCTRL_expansion.SetValue(u'')
123 self._TCTRL_expansion.Enable(False)
124 self._RBTN_public.Enable(True)
125 self._RBTN_private.Enable(True)
126 self._RBTN_public.SetValue(1)
127
128 self._TCTRL_keyword.SetFocus()
129 #----------------------------------------------------------------
131 self._TCTRL_keyword.SetValue(u'%s%s' % (self.data, _(u'___copy')))
132 self._TCTRL_keyword.Enable(True)
133 expansion = gmPG2.expand_keyword(keyword = self.data)
134 self._TCTRL_expansion.SetValue(gmTools.coalesce(expansion, u''))
135 self._TCTRL_expansion.Enable(True)
136 self._RBTN_public.Enable(True)
137 self._RBTN_private.Enable(True)
138 self._RBTN_public.SetValue(1)
139
140 self._TCTRL_keyword.SetFocus()
141 #----------------------------------------------------------------
143 self._TCTRL_keyword.SetValue(self.data)
144 self._TCTRL_keyword.Enable(False)
145 expansion = gmPG2.expand_keyword(keyword = self.data)
146 self._TCTRL_expansion.SetValue(gmTools.coalesce(expansion, u''))
147 self._TCTRL_expansion.Enable(True)
148 self._RBTN_public.Enable(False)
149 self._RBTN_private.Enable(False)
150
151 self._TCTRL_expansion.SetFocus()
152 #----------------------------------------------------------------
153 # event handling
154 #----------------------------------------------------------------
157 #----------------------------------------------------------------
159 if self._TCTRL_keyword.GetValue().strip() == u'':
160 self._TCTRL_expansion.Enable(False)
161 else:
162 self._TCTRL_expansion.Enable(True)
163 #============================================================
165
166 if parent is None:
167 parent = wx.GetApp().GetTopWindow()
168
169 #----------------------
170 def delete(keyword=None):
171 gmPG2.delete_text_expansion(keyword = keyword)
172 return True
173 #----------------------
174 def edit(keyword=None):
175 ea = cTextExpansionEditAreaPnl(parent, -1, keyword = keyword)
176 dlg = gmEditArea.cGenericEditAreaDlg2(parent, -1, edit_area = ea)
177 dlg.SetTitle (
178 gmTools.coalesce(keyword, _('Adding text expansion'), _('Editing text expansion "%s"'))
179 )
180 if dlg.ShowModal() == wx.ID_OK:
181 return True
182
183 return False
184 #----------------------
185 def refresh(lctrl=None):
186 kwds = [ [
187 r[0],
188 gmTools.bool2subst(r[1], gmTools.u_checkmark_thick, u''),
189 gmTools.bool2subst(r[2], gmTools.u_checkmark_thick, u''),
190 r[3]
191 ] for r in gmPG2.get_text_expansion_keywords()
192 ]
193 data = [ r[0] for r in gmPG2.get_text_expansion_keywords() ]
194 lctrl.set_string_items(kwds)
195 lctrl.set_data(data)
196 #----------------------
197
198 gmListWidgets.get_choices_from_list (
199 parent = parent,
200 msg = _('\nSelect the keyword you want to edit !\n'),
201 caption = _('Editing keyword-based text expansions ...'),
202 columns = [_('Keyword'), _('Public'), _('Private'), _('Owner')],
203 single_selection = True,
204 edit_callback = edit,
205 new_callback = edit,
206 delete_callback = delete,
207 refresh_callback = refresh
208 )
209 #============================================================
211
212 if parent is None:
213 parent = wx.GetApp().GetTopWindow()
214
215 staff = gmPerson.get_staff_list()
216 choices = [ [
217 s[u'short_alias'],
218 u'%s%s %s' % (
219 gmTools.coalesce(s['title'], u'', u'%s '),
220 s['firstnames'],
221 s['lastnames']
222 ),
223 s['l10n_role'],
224 gmTools.coalesce(s['comment'], u'')
225 ]
226 for s in staff
227 if s['is_active'] is True
228 ]
229 data = [ s['pk_staff'] for s in staff if s['is_active'] is True ]
230
231 gmCfgWidgets.configure_string_from_list_option (
232 parent = parent,
233 message = _(
234 '\n'
235 'Please select the provider to fall back to in case\n'
236 'no primary provider is configured for a patient.\n'
237 ),
238 option = 'patient.fallback_primary_provider',
239 bias = 'user',
240 default_value = None,
241 choices = choices,
242 columns = [_('Alias'), _('Provider'), _('Role'), _('Comment')],
243 data = data,
244 caption = _('Configuring fallback primary provider')
245 )
246 #============================================================
248
250
251 gmPhraseWheel.cPhraseWheel.__init__ (
252 self,
253 *args,
254 **kwargs
255 )
256 self.matcher = gmPerson.cMatchProvider_Provider()
257 self.SetToolTipString(_('Select a healthcare provider.'))
258 self.selection_only = True
259 #============================================================
260 # practice related widgets
261 #============================================================
263
264 if parent is None:
265 parent = wx.GetApp().GetTopWindow()
266
267 conn = gmAuthWidgets.get_dbowner_connection(procedure = _('showing audit trail'))
268 if conn is None:
269 return False
270
271 #-----------------------------------
272 def refresh(lctrl):
273 cmd = u'SELECT * FROM audit.v_audit_trail ORDER BY audit_when_ts'
274 rows, idx = gmPG2.run_ro_queries(link_obj = conn, queries = [{'cmd': cmd}], get_col_idx = False)
275 lctrl.set_string_items (
276 [ [
277 r['event_when'],
278 r['event_by'],
279 u'%s %s %s' % (
280 gmTools.coalesce(r['row_version_before'], gmTools.u_diameter),
281 gmTools.u_right_arrow,
282 gmTools.coalesce(r['row_version_after'], gmTools.u_diameter)
283 ),
284 r['event_table'],
285 r['event'],
286 r['pk_audit']
287 ] for r in rows ]
288 )
289 #-----------------------------------
290 gmListWidgets.get_choices_from_list (
291 parent = parent,
292 msg = u'',
293 caption = _('GNUmed database audit log ...'),
294 columns = [ _('When'), _('Who'), _('Revisions'), _('Table'), _('Event'), '#' ],
295 single_selection = True,
296 refresh_callback = refresh
297 )
298
299 #============================================================
300 # FIXME: this should be moved elsewhere !
301 #------------------------------------------------------------
303
304 if parent is None:
305 parent = wx.GetApp().GetTopWindow()
306
307 #-----------------------------------
308 def delete(workplace):
309
310 curr_workplace = gmSurgery.gmCurrentPractice().active_workplace
311 if workplace == curr_workplace:
312 gmDispatcher.send(signal = 'statustext', msg = _('Cannot delete the active workplace.'), beep = True)
313 return False
314
315 dlg = gmGuiHelpers.c2ButtonQuestionDlg (
316 parent,
317 -1,
318 caption = _('Deleting workplace ...'),
319 question = _('Are you sure you want to delete this workplace ?\n\n "%s"\n') % workplace,
320 show_checkbox = True,
321 checkbox_msg = _('delete configuration, too'),
322 checkbox_tooltip = _(
323 'Check this if you want to delete all configuration items\n'
324 'for this workplace along with the workplace itself.'
325 ),
326 button_defs = [
327 {'label': _('Delete'), 'tooltip': _('Yes, delete this workplace.'), 'default': True},
328 {'label': _('Do NOT delete'), 'tooltip': _('No, do NOT delete this workplace'), 'default': False}
329 ]
330 )
331
332 decision = dlg.ShowModal()
333 if decision != wx.ID_YES:
334 dlg.Destroy()
335 return False
336
337 include_cfg = dlg.checkbox_is_checked()
338 dlg.Destroy()
339
340 dbo_conn = gmAuthWidgets.get_dbowner_connection(procedure = _('delete workplace'))
341 if not dbo_conn:
342 return False
343
344 gmSurgery.delete_workplace(workplace = workplace, conn = dbo_conn, delete_config = include_cfg)
345 return True
346 #-----------------------------------
347 def edit(workplace=None):
348
349 dbcfg = gmCfg.cCfgSQL()
350
351 if workplace is None:
352 dlg = wx.TextEntryDialog (
353 parent = parent,
354 message = _('Enter a descriptive name for the new workplace:'),
355 caption = _('Configuring GNUmed workplaces ...'),
356 defaultValue = u'',
357 style = wx.OK | wx.CENTRE
358 )
359 dlg.ShowModal()
360 workplace = dlg.GetValue().strip()
361 if workplace == u'':
362 gmGuiHelpers.gm_show_error(_('Cannot save a new workplace without a name.'), _('Configuring GNUmed workplaces ...'))
363 return False
364 curr_plugins = []
365 else:
366 curr_plugins = gmTools.coalesce(dbcfg.get2 (
367 option = u'horstspace.notebook.plugin_load_order',
368 workplace = workplace,
369 bias = 'workplace'
370 ), []
371 )
372
373 msg = _(
374 'Pick the plugin(s) to be loaded the next time the client is restarted under the workplace:\n'
375 '\n'
376 ' [%s]\n'
377 ) % workplace
378
379 picker = gmListWidgets.cItemPickerDlg (
380 parent,
381 -1,
382 title = _('Configuring workplace plugins ...'),
383 msg = msg
384 )
385 picker.set_columns(['Available plugins'], ['Active plugins'])
386 available_plugins = gmPlugin.get_installed_plugins(plugin_dir = 'gui')
387 picker.set_choices(available_plugins)
388 picker.set_picks(picks = curr_plugins)
389 btn_pressed = picker.ShowModal()
390 if btn_pressed != wx.ID_OK:
391 picker.Destroy()
392 return False
393
394 new_plugins = picker.get_picks()
395 picker.Destroy()
396 if new_plugins == curr_plugins:
397 return True
398
399 if new_plugins is None:
400 return True
401
402 dbcfg.set (
403 option = u'horstspace.notebook.plugin_load_order',
404 value = new_plugins,
405 workplace = workplace
406 )
407
408 return True
409 #-----------------------------------
410 def edit_old(workplace=None):
411
412 available_plugins = gmPlugin.get_installed_plugins(plugin_dir='gui')
413
414 dbcfg = gmCfg.cCfgSQL()
415
416 if workplace is None:
417 dlg = wx.TextEntryDialog (
418 parent = parent,
419 message = _('Enter a descriptive name for the new workplace:'),
420 caption = _('Configuring GNUmed workplaces ...'),
421 defaultValue = u'',
422 style = wx.OK | wx.CENTRE
423 )
424 dlg.ShowModal()
425 workplace = dlg.GetValue().strip()
426 if workplace == u'':
427 gmGuiHelpers.gm_show_error(_('Cannot save a new workplace without a name.'), _('Configuring GNUmed workplaces ...'))
428 return False
429 curr_plugins = []
430 choices = available_plugins
431 else:
432 curr_plugins = gmTools.coalesce(dbcfg.get2 (
433 option = u'horstspace.notebook.plugin_load_order',
434 workplace = workplace,
435 bias = 'workplace'
436 ), []
437 )
438 choices = curr_plugins[:]
439 for p in available_plugins:
440 if p not in choices:
441 choices.append(p)
442
443 sels = range(len(curr_plugins))
444 new_plugins = gmListWidgets.get_choices_from_list (
445 parent = parent,
446 msg = _(
447 '\n'
448 'Select the plugin(s) to be loaded the next time\n'
449 'the client is restarted under the workplace:\n'
450 '\n'
451 ' [%s]'
452 '\n'
453 ) % workplace,
454 caption = _('Configuring GNUmed workplaces ...'),
455 choices = choices,
456 selections = sels,
457 columns = [_('Plugins')],
458 single_selection = False
459 )
460
461 if new_plugins == curr_plugins:
462 return True
463
464 if new_plugins is None:
465 return True
466
467 dbcfg.set (
468 option = u'horstspace.notebook.plugin_load_order',
469 value = new_plugins,
470 workplace = workplace
471 )
472
473 return True
474 #-----------------------------------
475 def clone(workplace=None):
476 if workplace is None:
477 return False
478
479 new_name = wx.GetTextFromUser (
480 message = _('Enter a name for the new workplace !'),
481 caption = _('Cloning workplace'),
482 default_value = u'%s-2' % workplace,
483 parent = parent
484 ).strip()
485
486 if new_name == u'':
487 return False
488
489 dbcfg = gmCfg.cCfgSQL()
490 opt = u'horstspace.notebook.plugin_load_order'
491
492 plugins = dbcfg.get2 (
493 option = opt,
494 workplace = workplace,
495 bias = 'workplace'
496 )
497
498 dbcfg.set (
499 option = opt,
500 value = plugins,
501 workplace = new_name
502 )
503
504 # FIXME: clone cfg, too
505
506 return True
507 #-----------------------------------
508 def refresh(lctrl):
509 workplaces = gmSurgery.gmCurrentPractice().workplaces
510 curr_workplace = gmSurgery.gmCurrentPractice().active_workplace
511 try:
512 sels = [workplaces.index(curr_workplace)]
513 except ValueError:
514 sels = []
515
516 lctrl.set_string_items(workplaces)
517 lctrl.set_selections(selections = sels)
518 #-----------------------------------
519 gmListWidgets.get_choices_from_list (
520 parent = parent,
521 msg = _(
522 '\nSelect the workplace to configure below.\n'
523 '\n'
524 'The currently active workplace is preselected.\n'
525 ),
526 caption = _('Configuring GNUmed workplaces ...'),
527 columns = [_('Workplace')],
528 single_selection = True,
529 refresh_callback = refresh,
530 edit_callback = edit,
531 new_callback = edit,
532 delete_callback = delete,
533 left_extra_button = (_('Clone'), _('Clone the selected workplace'), clone)
534 )
535 #====================================================================
537
539
540 gmPhraseWheel.cPhraseWheel.__init__(self, *args, **kwargs)
541
542 query = u"""
543 SELECT DISTINCT ON (label)
544 pk_type,
545 (l10n_type || ' (' || l10n_category || ')')
546 AS label
547 FROM
548 dem.v_inbox_item_type
549 WHERE
550 l10n_type %(fragment_condition)s
551 OR
552 type %(fragment_condition)s
553 OR
554 l10n_category %(fragment_condition)s
555 OR
556 category %(fragment_condition)s
557 ORDER BY label
558 LIMIT 50"""
559
560 mp = gmMatchProvider.cMatchProvider_SQL2(queries = query)
561 mp.setThresholds(1, 2, 4)
562 self.matcher = mp
563 self.SetToolTipString(_('Select a message type.'))
564 #----------------------------------------------------------------
566 if self.GetData() is not None:
567 return
568
569 val = self.GetValue().strip()
570 if val == u'':
571 return
572
573 self.SetText (
574 value = val,
575 data = gmProviderInbox.create_inbox_item_type(message_type = val)
576 )
577 #====================================================================
578 from Gnumed.wxGladeWidgets import wxgInboxMessageEAPnl
579
580 -class cInboxMessageEAPnl(wxgInboxMessageEAPnl.wxgInboxMessageEAPnl, gmEditArea.cGenericEditAreaMixin):
581
583
584 try:
585 data = kwargs['message']
586 del kwargs['message']
587 except KeyError:
588 data = None
589
590 wxgInboxMessageEAPnl.wxgInboxMessageEAPnl.__init__(self, *args, **kwargs)
591 gmEditArea.cGenericEditAreaMixin.__init__(self)
592
593 # Code using this mixin should set mode and data
594 # after instantiating the class:
595 self.mode = 'new'
596 self.data = data
597 if data is not None:
598 self.mode = 'edit'
599
600 self.__init_ui()
601 #----------------------------------------------------------------
603 if not gmPerson.gmCurrentPatient().connected:
604 self._CHBOX_active_patient.SetValue(False)
605 self._CHBOX_active_patient.Enable(False)
606 self._PRW_patient.Enable(True)
607 #----------------------------------------------------------------
608 # generic Edit Area mixin API
609 #----------------------------------------------------------------
611 validity = True
612
613 if self._TCTRL_subject.GetValue().strip() == u'':
614 validity = False
615 self.display_ctrl_as_valid(ctrl = self._TCTRL_subject, valid = False)
616 else:
617 self.display_ctrl_as_valid(ctrl = self._TCTRL_subject, valid = True)
618
619 if self._PRW_type.GetValue().strip() == u'':
620 validity = False
621 self._PRW_type.display_as_valid(False)
622 else:
623 self._PRW_type.display_as_valid(True)
624
625 missing_receiver = (
626 (self._CHBOX_send_to_me.IsChecked() is False)
627 and
628 (self._PRW_receiver.GetData() is None)
629 )
630
631 missing_patient = (
632 (self._CHBOX_active_patient.IsChecked() is False)
633 and
634 (self._PRW_patient.person is None)
635 )
636
637 if missing_receiver and missing_patient:
638 validity = False
639 self.display_ctrl_as_valid(ctrl = self._CHBOX_send_to_me, valid = False)
640 self._PRW_receiver.display_as_valid(False)
641 self.display_ctrl_as_valid(ctrl = self._CHBOX_active_patient, valid = False)
642 self.display_ctrl_as_valid(ctrl = self._PRW_patient, valid = False)
643 else:
644 self.display_ctrl_as_valid(ctrl = self._CHBOX_send_to_me, valid = True)
645 self._PRW_receiver.display_as_valid(True)
646 self.display_ctrl_as_valid(ctrl = self._CHBOX_active_patient, valid = True)
647 self.display_ctrl_as_valid(ctrl = self._PRW_patient, valid = True)
648
649 return validity
650 #----------------------------------------------------------------
652
653 pat_id = None
654 if self._CHBOX_active_patient.GetValue() is True:
655 pat_id = gmPerson.gmCurrentPatient().ID
656 else:
657 if self._PRW_patient.person is not None:
658 pat_id = self._PRW_patient.person.ID
659
660 receiver = None
661 if self._CHBOX_send_to_me.IsChecked():
662 receiver = gmPerson.gmCurrentProvider()['pk_staff']
663 else:
664 if self._PRW_receiver.GetData() is not None:
665 receiver = self._PRW_receiver.GetData()
666
667 msg = gmProviderInbox.create_inbox_message (
668 patient = pat_id,
669 staff = receiver,
670 message_type = self._PRW_type.GetData(can_create = True),
671 subject = self._TCTRL_subject.GetValue().strip()
672 )
673
674 msg['data'] = self._TCTRL_message.GetValue().strip()
675
676 if self._RBTN_normal.GetValue() is True:
677 msg['importance'] = 0
678 elif self._RBTN_high.GetValue() is True:
679 msg['importance'] = 1
680 else:
681 msg['importance'] = -1
682
683 msg.save()
684 self.data = msg
685 return True
686 #----------------------------------------------------------------
688
689 self.data['comment'] = self._TCTRL_subject.GetValue().strip()
690 self.data['pk_type'] = self._PRW_type.GetData(can_create = True)
691
692 if self._CHBOX_send_to_me.IsChecked():
693 self.data['pk_staff'] = gmPerson.gmCurrentProvider()['pk_staff']
694 else:
695 self.data['pk_staff'] = self._PRW_receiver.GetData()
696
697 self.data['data'] = self._TCTRL_message.GetValue().strip()
698
699 if self._CHBOX_active_patient.GetValue() is True:
700 self.data['pk_patient'] = gmPerson.gmCurrentPatient().ID
701 else:
702 if self._PRW_patient.person is None:
703 self.data['pk_patient'] = None
704 else:
705 self.data['pk_patient'] = self._PRW_patient.person.ID
706
707 if self._RBTN_normal.GetValue() is True:
708 self.data['importance'] = 0
709 elif self._RBTN_high.GetValue() is True:
710 self.data['importance'] = 1
711 else:
712 self.data['importance'] = -1
713
714 self.data.save()
715 return True
716 #----------------------------------------------------------------
718 self._TCTRL_subject.SetValue(u'')
719 self._PRW_type.SetText(value = u'', data = None)
720 self._CHBOX_send_to_me.SetValue(True)
721 self._PRW_receiver.Enable(False)
722 self._PRW_receiver.SetData(data = gmPerson.gmCurrentProvider()['pk_staff'])
723 self._TCTRL_message.SetValue(u'')
724 self._RBTN_normal.SetValue(True)
725 self._RBTN_high.SetValue(False)
726 self._RBTN_low.SetValue(False)
727
728 self._PRW_patient.person = None
729
730 if gmPerson.gmCurrentPatient().connected:
731 self._CHBOX_active_patient.Enable(True)
732 self._CHBOX_active_patient.SetValue(True)
733 self._PRW_patient.Enable(False)
734 else:
735 self._CHBOX_active_patient.Enable(False)
736 self._CHBOX_active_patient.SetValue(False)
737 self._PRW_patient.Enable(True)
738
739 self._TCTRL_subject.SetFocus()
740 #----------------------------------------------------------------
743 #----------------------------------------------------------------
745
746 self._TCTRL_subject.SetValue(gmTools.coalesce(self.data['comment'], u''))
747 self._PRW_type.SetData(data = self.data['pk_type'])
748
749 curr_prov = gmPerson.gmCurrentProvider()
750 curr_pat = gmPerson.gmCurrentPatient()
751
752 if curr_prov['pk_staff'] == self.data['pk_staff']:
753 self._CHBOX_send_to_me.SetValue(True)
754 self._PRW_receiver.Enable(False)
755 self._PRW_receiver.SetData(data = gmPerson.gmCurrentProvider()['pk_staff'])
756 else:
757 self._CHBOX_send_to_me.SetValue(False)
758 self._PRW_receiver.Enable(True)
759 self._PRW_receiver.SetData(data = self.data['pk_staff'])
760
761 self._TCTRL_message.SetValue(gmTools.coalesce(self.data['data'], u''))
762
763 if curr_pat.connected:
764 self._CHBOX_active_patient.Enable(True)
765 if curr_pat.ID == self.data['pk_patient']:
766 self._CHBOX_active_patient.SetValue(True)
767 self._PRW_patient.Enable(False)
768 self._PRW_patient.person = None
769 else:
770 self._CHBOX_active_patient.SetValue(False)
771 self._PRW_patient.Enable(True)
772 if self.data['pk_patient'] is None:
773 self._PRW_patient.person = None
774 else:
775 self._PRW_patient.person = gmPerson.cIdentity(aPK_obj = self.data['pk_patient'])
776 else:
777 self._CHBOX_active_patient.Enable(False)
778 self._CHBOX_active_patient.SetValue(False)
779 self._PRW_patient.Enable(True)
780 if self.data['pk_patient'] is None:
781 self._PRW_patient.person = None
782 else:
783 self._PRW_patient.person = gmPerson.cIdentity(aPK_obj = self.data['pk_patient'])
784
785 self._RBTN_normal.SetValue(False)
786 self._RBTN_high.SetValue(False)
787 self._RBTN_low.SetValue(False)
788 { -1: self._RBTN_low,
789 0: self._RBTN_normal,
790 1: self._RBTN_high
791 }[self.data['importance']].SetValue(True)
792
793 self._TCTRL_subject.SetFocus()
794 #----------------------------------------------------------------
795 # event handlers
796 #----------------------------------------------------------------
798 if self._CHBOX_active_patient.IsChecked():
799 self._PRW_patient.Enable(False)
800 self._PRW_patient.person = None
801 else:
802 self._PRW_patient.Enable(True)
803 #----------------------------------------------------------------
811 #============================================================
813
814 if parent is None:
815 parent = wx.GetApp().GetTopWindow()
816
817 ea = cInboxMessageEAPnl(parent = parent, id = -1)
818 ea.data = message
819 ea.mode = gmTools.coalesce(message, 'new', 'edit')
820 dlg = gmEditArea.cGenericEditAreaDlg2(parent = parent, id = -1, edit_area = ea, single_entry = single_entry)
821 dlg.SetTitle(gmTools.coalesce(message, _('Adding new inbox message'), _('Editing inbox message')))
822 if dlg.ShowModal() == wx.ID_OK:
823 dlg.Destroy()
824 return True
825 dlg.Destroy()
826 return False
827 #============================================================
828 from Gnumed.wxGladeWidgets import wxgProviderInboxPnl
829
830 -class cProviderInboxPnl(wxgProviderInboxPnl.wxgProviderInboxPnl, gmRegetMixin.cRegetOnPaintMixin):
831
832 _item_handlers = {}
833
834 #--------------------------------------------------------
836
837 wxgProviderInboxPnl.wxgProviderInboxPnl.__init__(self, *args, **kwds)
838 gmRegetMixin.cRegetOnPaintMixin.__init__(self)
839
840 self.provider = gmPerson.gmCurrentProvider()
841 self.filter_mode = 'all'
842 self.__init_ui()
843
844 cProviderInboxPnl._item_handlers['clinical.review docs'] = self._goto_doc_review
845 cProviderInboxPnl._item_handlers['clinical.review results'] = self._goto_measurements_review
846 cProviderInboxPnl._item_handlers['clinical.review lab'] = self._goto_measurements_review
847 cProviderInboxPnl._item_handlers['clinical.review vaccs'] = self._goto_vaccination_review
848
849 self.__register_interests()
850 #--------------------------------------------------------
851 # reget-on-paint API
852 #--------------------------------------------------------
856 #--------------------------------------------------------
857 # internal helpers
858 #--------------------------------------------------------
860 gmDispatcher.connect(signal = u'message_inbox_generic_mod_db', receiver = self._on_message_inbox_mod_db)
861 gmDispatcher.connect(signal = u'message_inbox_mod_db', receiver = self._on_message_inbox_mod_db)
862 # FIXME: listen for results insertion/deletion
863 gmDispatcher.connect(signal = u'reviewed_test_results_mod_db', receiver = self._on_message_inbox_mod_db)
864 gmDispatcher.connect(signal = u'identity_mod_db', receiver = self._on_message_inbox_mod_db)
865 gmDispatcher.connect(signal = u'doc_mod_db', receiver = self._on_message_inbox_mod_db)
866 gmDispatcher.connect(signal = u'doc_obj_review_mod_db', receiver = self._on_message_inbox_mod_db)
867 gmDispatcher.connect(signal = u'post_patient_selection', receiver = self._on_post_patient_selection)
868 #--------------------------------------------------------
870 self._LCTRL_provider_inbox.set_columns([u'', _('Sent'), _('Category'), _('Type'), _('Message')])
871
872 msg = _('\n Inbox of %(title)s %(lname)s.\n') % {
873 'title': gmTools.coalesce (
874 self.provider['title'],
875 gmPerson.map_gender2salutation(self.provider['gender'])
876 ),
877 'lname': self.provider['lastnames']
878 }
879
880 self._LCTRL_provider_inbox.item_tooltip_callback = self._get_msg_tooltip
881
882 self._msg_welcome.SetLabel(msg)
883
884 if gmPerson.gmCurrentPatient().connected:
885 self._RBTN_active_patient.Enable()
886 #--------------------------------------------------------
888 self.__msgs = self.provider.inbox.messages
889
890 if self.filter_mode == 'active':
891 if gmPerson.gmCurrentPatient().connected:
892 curr_pat_id = gmPerson.gmCurrentPatient().ID
893 self.__msgs = [ m for m in self.__msgs if m['pk_patient'] == curr_pat_id ]
894 else:
895 self.__msgs = []
896
897 items = [
898 [
899 _indicator[m['importance']],
900 m['received_when'].strftime('%Y-%m-%d'),
901 m['l10n_category'],
902 m['l10n_type'],
903 m['comment']
904 ] for m in self.__msgs
905 ]
906 self._LCTRL_provider_inbox.set_string_items(items = items)
907 self._LCTRL_provider_inbox.set_data(data = self.__msgs)
908 self._LCTRL_provider_inbox.set_column_widths()
909 self._TXT_inbox_item_comment.SetValue(u'')
910 #--------------------------------------------------------
911 # event handlers
912 #--------------------------------------------------------
916 #--------------------------------------------------------
918 wx.CallAfter(self._schedule_data_reget)
919 gmDispatcher.send(signal = u'request_user_attention', msg = _('Please check your GNUmed Inbox !'))
920 #--------------------------------------------------------
922 msg = self._LCTRL_provider_inbox.get_selected_item_data(only_one = True)
923 if msg is None:
924 return
925
926 handler_key = '%s.%s' % (msg['category'], msg['type'])
927 try:
928 handle_item = cProviderInboxPnl._item_handlers[handler_key]
929 except KeyError:
930 if msg['pk_patient'] is None:
931 gmGuiHelpers.gm_show_warning (
932 _('No double-click action pre-programmed into\n'
933 'GNUmed for message category and type:\n'
934 '\n'
935 ' [%s]\n'
936 ) % handler_key,
937 _('handling provider inbox item')
938 )
939 return False
940 handle_item = self._goto_patient
941
942 if not handle_item(pk_context = msg['pk_context'], pk_patient = msg['pk_patient']):
943 _log.error('item handler returned <False>')
944 _log.error('handler key: [%s]', handler_key)
945 _log.error('message: %s', str(msg))
946 return False
947
948 return True
949 #--------------------------------------------------------
952 #--------------------------------------------------------
954 msg = self._LCTRL_provider_inbox.get_selected_item_data(only_one = True)
955 if msg is None:
956 return
957
958 if msg['data'] is None:
959 tmp = _('Message: %s') % msg['comment']
960 else:
961 tmp = _('Message: %s\nData: %s') % (msg['comment'], msg['data'])
962
963 self._TXT_inbox_item_comment.SetValue(tmp)
964 #--------------------------------------------------------
966 tmp = self._LCTRL_provider_inbox.get_selected_item_data(only_one = True)
967 if tmp is None:
968 return
969 self.__focussed_msg = tmp
970
971 # build menu
972 menu = wx.Menu(title = _('Inbox Message Actions:'))
973
974 if self.__focussed_msg['pk_patient'] is not None:
975 ID = wx.NewId()
976 menu.AppendItem(wx.MenuItem(menu, ID, _('Activate patient')))
977 wx.EVT_MENU(menu, ID, self._on_goto_patient)
978
979 if not self.__focussed_msg['is_virtual']:
980 # - delete message
981 ID = wx.NewId()
982 menu.AppendItem(wx.MenuItem(menu, ID, _('Delete')))
983 wx.EVT_MENU(menu, ID, self._on_delete_focussed_msg)
984 # - edit message
985 ID = wx.NewId()
986 menu.AppendItem(wx.MenuItem(menu, ID, _('Edit')))
987 wx.EVT_MENU(menu, ID, self._on_edit_focussed_msg)
988
989 # if self.__focussed_msg['pk_staff'] is not None:
990 # # - distribute to other providers
991 # ID = wx.NewId()
992 # menu.AppendItem(wx.MenuItem(menu, ID, _('Distribute')))
993 # wx.EVT_MENU(menu, ID, self._on_distribute_focussed_msg)
994
995 # show menu
996 self.PopupMenu(menu, wx.DefaultPosition)
997 menu.Destroy()
998 #--------------------------------------------------------
1003 #--------------------------------------------------------
1008 #--------------------------------------------------------
1011 #--------------------------------------------------------
1013 tt = u'%s: %s%s\n' % (
1014 msg['received_when'].strftime('%A, %Y %B %d, %H:%M').decode(gmI18N.get_encoding()),
1015 gmTools.bool2subst(msg['is_virtual'], _('virtual message'), _('message')),
1016 gmTools.coalesce(msg['pk_inbox_message'], u'', u' #%s ')
1017 )
1018
1019 tt += u'%s: %s\n' % (
1020 msg['l10n_category'],
1021 msg['l10n_type']
1022 )
1023
1024 tt += u'%s %s %s\n' % (
1025 msg['modified_by'],
1026 gmTools.u_right_arrow,
1027 gmTools.coalesce(msg['provider'], _('everyone'))
1028 )
1029
1030 tt += u'\n%s%s%s\n\n' % (
1031 gmTools.u_left_double_angle_quote,
1032 msg['comment'],
1033 gmTools.u_right_double_angle_quote
1034 )
1035
1036 tt += gmTools.coalesce (
1037 msg['pk_patient'],
1038 u'',
1039 u'%s\n\n' % _('Patient #%s')
1040 )
1041
1042 if msg['data'] is not None:
1043 tt += msg['data'][:150]
1044 if len(msg['data']) > 150:
1045 tt += gmTools.u_ellipsis
1046
1047 return tt
1048 #--------------------------------------------------------
1049 # item handlers
1050 #--------------------------------------------------------
1053 #--------------------------------------------------------
1055 if self.__focussed_msg['is_virtual']:
1056 gmDispatcher.send(signal = 'statustext', msg = _('You must deal with the reason for this message to remove it from your inbox.'), beep = True)
1057 return False
1058
1059 if not self.provider.inbox.delete_message(self.__focussed_msg['pk_inbox_message']):
1060 gmDispatcher.send(signal='statustext', msg=_('Problem removing message from Inbox.'))
1061 return False
1062 return True
1063 #--------------------------------------------------------
1065 if self.__focussed_msg['is_virtual']:
1066 gmDispatcher.send(signal = 'statustext', msg = _('This message cannot be edited because it is virtual.'))
1067 return False
1068 edit_inbox_message(parent = self, message = self.__focussed_msg, single_entry = True)
1069 return True
1070 #--------------------------------------------------------
1072 if self.__focussed_msg['pk_staff'] is None:
1073 gmDispatcher.send(signal = 'statustext', msg = _('This message is already visible to all providers.'))
1074 return False
1075 print "now distributing"
1076 return True
1077 #--------------------------------------------------------
1079
1080 wx.BeginBusyCursor()
1081
1082 msg = _('There is a message about patient [%s].\n\n'
1083 'However, I cannot find that\n'
1084 'patient in the GNUmed database.'
1085 ) % pk_patient
1086
1087 try:
1088 pat = gmPerson.cIdentity(aPK_obj = pk_patient)
1089 except gmExceptions.ConstructorError:
1090 wx.EndBusyCursor()
1091 _log.exception('patient [%s] not found', pk_patient)
1092 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1093 return False
1094 except:
1095 wx.EndBusyCursor()
1096 raise
1097
1098 success = gmPatSearchWidgets.set_active_patient(patient = pat)
1099
1100 wx.EndBusyCursor()
1101
1102 if not success:
1103 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1104 return False
1105
1106 return True
1107 #--------------------------------------------------------
1109
1110 msg = _('Supposedly there are unreviewed documents\n'
1111 'for patient [%s]. However, I cannot find\n'
1112 'that patient in the GNUmed database.'
1113 ) % pk_patient
1114
1115 wx.BeginBusyCursor()
1116
1117 try:
1118 pat = gmPerson.cIdentity(aPK_obj = pk_patient)
1119 except gmExceptions.ConstructorError:
1120 wx.EndBusyCursor()
1121 _log.exception('patient [%s] not found', pk_patient)
1122 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1123 return False
1124
1125 success = gmPatSearchWidgets.set_active_patient(patient = pat)
1126
1127 wx.EndBusyCursor()
1128
1129 if not success:
1130 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1131 return False
1132
1133 wx.CallAfter(gmDispatcher.send, signal = 'display_widget', name = 'gmShowMedDocs', sort_mode = 'review')
1134 return True
1135 #--------------------------------------------------------
1137
1138 msg = _('Supposedly there are unreviewed results\n'
1139 'for patient [%s]. However, I cannot find\n'
1140 'that patient in the GNUmed database.'
1141 ) % pk_patient
1142
1143 wx.BeginBusyCursor()
1144
1145 try:
1146 pat = gmPerson.cIdentity(aPK_obj = pk_patient)
1147 except gmExceptions.ConstructorError:
1148 wx.EndBusyCursor()
1149 _log.exception('patient [%s] not found', pk_patient)
1150 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1151 return False
1152
1153 success = gmPatSearchWidgets.set_active_patient(patient = pat)
1154
1155 wx.EndBusyCursor()
1156
1157 if not success:
1158 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1159 return False
1160
1161 wx.CallAfter(gmDispatcher.send, signal = 'display_widget', name = 'gmMeasurementsGridPlugin')
1162 return True
1163 #--------------------------------------------------------
1165
1166 msg = _('Supposedly there are conflicting vaccinations\n'
1167 'for patient [%s]. However, I cannot find\n'
1168 'that patient in the GNUmed database.'
1169 ) % pk_patient
1170
1171 wx.BeginBusyCursor()
1172
1173 try:
1174 pat = gmPerson.cIdentity(aPK_obj = pk_patient)
1175 except gmExceptions.ConstructorError:
1176 wx.EndBusyCursor()
1177 _log.exception('patient [%s] not found', pk_patient)
1178 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1179 return False
1180
1181 success = gmPatSearchWidgets.set_active_patient(patient = pat)
1182
1183 wx.EndBusyCursor()
1184
1185 if not success:
1186 gmGuiHelpers.gm_show_error(msg, _('handling provider inbox item'))
1187 return False
1188
1189 wx.CallAfter(gmVaccWidgets.manage_vaccinations)
1190
1191 return True
1192 #============================================================
1193 if __name__ == '__main__':
1194
1195 if len(sys.argv) < 2:
1196 sys.exit()
1197
1198 if sys.argv[1] != 'test':
1199 sys.exit()
1200
1201 gmI18N.activate_locale()
1202 gmI18N.install_domain(domain = 'gnumed')
1203
1207
1209 app = wx.PyWidgetTester(size = (800, 600))
1210 app.SetWidget(cProviderInboxPnl, -1)
1211 app.MainLoop()
1212
1214 app = wx.PyWidgetTester(size = (800, 600))
1215 app.SetWidget(cInboxMessageEAPnl, -1)
1216 app.MainLoop()
1217
1218
1219 #test_configure_wp_plugins()
1220 #test_message_inbox()
1221 test_msg_ea()
1222
1223 #============================================================
1224
| Home | Trees | Indices | Help |
|
|---|
| Generated by Epydoc 3.0.1 on Tue Oct 18 04:00:48 2011 | http://epydoc.sourceforge.net |