comparison pyink/FSM_window.py @ 1484:aa4137f3141e

Transition will follow the moving state
author Thinker K.F. Li <thinker@codemud.net>
date Fri, 29 Apr 2011 23:33:53 +0800
parents 9df6ed043b87
children 20cf6ea263c6
comparison
equal deleted inserted replaced
1483:9df6ed043b87 1484:aa4137f3141e
194 state_name = self._state.state_name 194 state_name = self._state.state_name
195 trn_cond = self.trn_cond 195 trn_cond = self.trn_cond
196 trn = domview.get_transition(state_name, trn_cond) 196 trn = domview.get_transition(state_name, trn_cond)
197 return trn[3] 197 return trn[3]
198 198
199 @property
200 def target(self):
201 domview = self._domview
202 state_name = self._state.state_name
203 trn_cond = self.trn_cond
204 trn = domview.get_transition(state_name, trn_cond)
205 return trn[1]
206
199 def draw(self, parent): 207 def draw(self, parent):
200 path = self.path 208 path = self.path
201 trn_g, arrow_node, path_node = self._draw_transition_real(parent, path) 209 trn_g, arrow_node, path_node = self._draw_transition_real(parent, path)
202 self.trn_g = trn_g 210 self.trn_g = trn_g
203 self._arrow_node = arrow_node 211 self._arrow_node = arrow_node
213 def update(self): 221 def update(self):
214 path = self.path 222 path = self.path
215 arrow_node = self._arrow_node 223 arrow_node = self._arrow_node
216 path_node = self._path_node 224 path_node = self._path_node
217 self._update_graph(path, arrow_node, path_node) 225 self._update_graph(path, arrow_node, path_node)
226 pass
227
228 def adjust_by_ends(self, states):
229 import math
230
231 state = self._state
232 state_name = state.state_name
233 trn_cond = self.trn_cond
234
235 path = self.path
236
237 start_state = self._state
238 start_x, start_y = start_state.xy
239 start_r = start_state.r
240
241 target_name = self.target
242 stop_state = states[target_name]
243 stop_x, stop_y = stop_state.xy
244 stop_r = stop_state.r
245
246 c0x, c0y, c1x, c1y, c2x, c2y, c3x, c3y = tuple(path)
247
248 c0c1 = (c1x - c0x, c1y - c0y)
249 c0c1_len = math.sqrt(c0c1[0] ** 2 + c0c1[1] ** 2)
250 start_v = (c0c1[0] / c0c1_len, c0c1[1] / c0c1_len)
251
252 c3c2 = (c2x - c3x, c2y - c3y)
253 c3c2_len = math.sqrt(c3c2[0] ** 2 + c3c2[1] ** 2)
254 stop_v = (c3c2[0] / c3c2_len, c3c2[1] / c3c2_len)
255
256 c0x = start_v[0] * start_r + start_x
257 c0y = start_v[1] * start_r + start_y
258 c1x = start_v[0] * c0c1_len + c0x
259 c1y = start_v[1] * c0c1_len + c0y
260 c3x = stop_v[0] * stop_r + stop_x
261 c3y = stop_v[1] * stop_r + stop_y
262 c2x = stop_v[0] * c3c2_len + c3x
263 c2y = stop_v[1] * c3c2_len + c3y
264 new_path = [c0x, c0y, c1x, c1y, c2x, c2y, c3x, c3y]
265
266 domview = self._domview
267 domview.set_transition_path(state_name, trn_cond, new_path)
218 pass 268 pass
219 pass 269 pass
220 270
221 class FSM_state(object): 271 class FSM_state(object):
222 _doc = None 272 _doc = None
226 state_name = None 276 state_name = None
227 state_g = None 277 state_g = None
228 _text_node = None 278 _text_node = None
229 _circle_node = None 279 _circle_node = None
230 transitions = None 280 transitions = None
281 from_srcs = None
231 282
232 _state_g_hdl_id = None 283 _state_g_hdl_id = None
233 _selected_rect = None 284 _selected_rect = None
234 285
235 def __init__(self, state_name): 286 def __init__(self, state_name):
236 self.state_name = state_name 287 self.state_name = state_name
237 self.transitions = {} 288 self.transitions = {}
289 self.from_srcs = set()
238 pass 290 pass
239 291
240 def init(self, doc, domview, fsm_layer, control_layer): 292 def init(self, doc, domview, fsm_layer, control_layer):
241 self._doc = doc 293 self._doc = doc
242 self._domview = domview 294 self._domview = domview
400 r = self.r 452 r = self.r
401 x, y = self.xy 453 x, y = self.xy
402 self._update_graph(text_node, text_content, circle_node, state_name, 454 self._update_graph(text_node, text_content, circle_node, state_name,
403 r, x, y) 455 r, x, y)
404 pass 456 pass
457
458 def tell_target_states(self, states):
459 transitions = self.transitions
460 target_state_names = [trn.target for trn in transitions.values()]
461 target_states = [states[target_name]
462 for target_name in target_state_names]
463 state_name = self.state_name
464 for target_state in target_states:
465 target_state.from_srcs.add(state_name)
466 pass
467 pass
468
469 def adjust_transitions(self, states):
470 import itertools
471
472 for trn in self.transitions.values():
473 trn.adjust_by_ends(states)
474 trn.update()
475 pass
476
477 state_name = self.state_name
478 src_states = [states[src_state_name]
479 for src_state_name in self.from_srcs]
480 states_transitions = [state.transitions.values()
481 for state in src_states]
482 in_state_transitions = [[trn for trn in state_transitions
483 if trn.target == state_name]
484 for state_transitions in states_transitions]
485 in_transitions = itertools.chain(*in_state_transitions)
486 for trn in in_transitions:
487 trn.adjust_by_ends(states)
488 trn.update()
489 pass
490 pass
405 pass 491 pass
406 492
407 493
408 class FSM_move_state_mode(object): 494 class FSM_move_state_mode(object):
409 __metaclass__ = data_monitor.data_monitor 495 __metaclass__ = data_monitor.data_monitor
438 self._selected_state = None 524 self._selected_state = None
439 pass 525 pass
440 526
441 def handle_move_state_state(self, state, evtype, buttons, x, y): 527 def handle_move_state_state(self, state, evtype, buttons, x, y):
442 import pybInkscape 528 import pybInkscape
529
530 window = self._window
531 states = window._states
443 532
444 def moving_state(item, evtype, buttons, x, y): 533 def moving_state(item, evtype, buttons, x, y):
445 if evtype == pybInkscape.PYSPItem.PYB_EVENT_BUTTON_RELEASE: 534 if evtype == pybInkscape.PYSPItem.PYB_EVENT_BUTTON_RELEASE:
446 window.ungrab_mouse() 535 window.ungrab_mouse()
447 pass 536 pass
449 new_state_y = orign_state_y + start_y - y 538 new_state_y = orign_state_y + start_y - y
450 539
451 domview = self._domview 540 domview = self._domview
452 domview.set_state_xy(state.state_name, x, y) 541 domview.set_state_xy(state.state_name, x, y)
453 state.update() 542 state.update()
543 state.adjust_transitions(states)
454 state.show_selected() 544 state.show_selected()
455 pass 545 pass
456 546
457 window = self._window 547 window = self._window
458 548
528 (state_name)) 618 (state_name))
529 return 619 return
530 domview.set_state_xy(state_name, x, y) 620 domview.set_state_xy(state_name, x, y)
531 domview.set_state_r(state_name, r) 621 domview.set_state_r(state_name, r)
532 622
533 window._load_new_state(state_name) 623 window._load_new_state_incr(state_name)
534 624
535 window.hide_state_editor() 625 window.hide_state_editor()
536 pass 626 pass
537 627
538 def on_add_state_background(self, item, evtype, buttons, x, y): 628 def on_add_state_background(self, item, evtype, buttons, x, y):
710 800
711 self._draw_state_domview(state_name) 801 self._draw_state_domview(state_name)
712 state = states[state_name] 802 state = states[state_name]
713 self._install_state_event_handler(state) 803 self._install_state_event_handler(state)
714 pass 804 pass
805
806 ## \brief Load new state incrementally.
807 #
808 def _load_new_state_incr(self, state_name):
809 self._load_new_state(state_name)
810 states = self._states
811 state = states[state_name]
812 state.tell_target_states(states)
813 pass
814
815 def _rebuild_from_srcs(self):
816 states = self._states
817 domview = self._domview
818 state_names = domview.all_state_names()
819 for state_name in state_names:
820 state = states[state_name]
821 state.tell_target_states(states)
822 pass
823 pass
715 824
716 def _update_view(self): 825 def _update_view(self):
717 self._clear_view() 826 self._clear_view()
718 states = self._states 827 states = self._states
719 828
721 830
722 state_names = domview.all_state_names() 831 state_names = domview.all_state_names()
723 for state_name in state_names: 832 for state_name in state_names:
724 self._load_new_state(state_name) 833 self._load_new_state(state_name)
725 pass 834 pass
835 self._rebuild_from_srcs()
726 pass 836 pass
727 837
728 def set_svg_view(self, view): 838 def set_svg_view(self, view):
729 self._view_box.add(view) 839 self._view_box.add(view)
730 self._view_widget = view 840 self._view_widget = view