def __init__(self, state_m, size, custom_background_color, background_color, hierarchy_level): super(StateView, self).__init__(size[0], size[1]) assert isinstance(state_m, AbstractStateModel) # Reapply size, as Gaphas sets default minimum size to 1, which is too large for highly nested states self.min_width = self.min_height = 0 self.width = size[0] self.height = size[1] self.custom_background_color = custom_background_color self.background_color = background_color self.background_changed = False self._c_min_w = self._constraints[0] self._c_min_h = self._constraints[1] self.is_root_state_of_library = state_m.state.is_root_state_of_library self._state_m = ref(state_m) self.hierarchy_level = hierarchy_level self._income = None self._outcomes = [] self._inputs = [] self._outputs = [] self._scoped_variables = [] self._scoped_variables_ports = [] self.keep_rect_constraints = {} self.port_constraints = {} self._moving = False self._view = None self.__symbol_size_cache = {} self._image_cache = ImageCache() self._border_width = Variable( min(self.width, self.height) / constants.BORDER_WIDTH_STATE_SIZE_FACTOR) border_width_constraint = BorderWidthConstraint( self._handles[NW].pos, self._handles[SE].pos, self._border_width, constants.BORDER_WIDTH_STATE_SIZE_FACTOR) self._constraints.append(border_width_constraint) # Initialize NameView name_meta = state_m.get_meta_data_editor()['name'] if not contains_geometric_info(name_meta['size']): name_width = self.width - 2 * self._border_width name_height = self.height * 0.4 name_meta = state_m.set_meta_data_editor( 'name.size', (name_width, name_height))['name'] name_size = name_meta['size'] self._name_view = NameView(state_m.state.name, name_size) if not contains_geometric_info(name_meta['rel_pos']): name_meta['rel_pos'] = (self.border_width, self.border_width) name_pos = name_meta['rel_pos'] self.name_view.matrix.translate(*name_pos)
def _meta_data_editor_opengl2gaphas(self, vividict): from rafcon.gui.helpers.meta_data import contains_geometric_info if self.parent: rel_pos = vividict['inner_rel_pos'] state_size = self.parent.get_meta_data_editor()['size'] if contains_geometric_info(rel_pos) and contains_geometric_info(state_size): if isinstance(self.data_port, InputDataPort): vividict['rel_pos'] = (0, -rel_pos[1]) else: # OutputDataPort vividict['rel_pos'] = (state_size[1], -rel_pos[1]) else: del vividict['inner_rel_pos'] return vividict
def add_scoped_variable(self, scoped_variable_m): scoped_variable_port_v = ScopedVariablePortView(self, scoped_variable_m) self.canvas.add_port(scoped_variable_port_v) self._scoped_variables_ports.append(scoped_variable_port_v) self._ports.append(scoped_variable_port_v.port) self._handles.append(scoped_variable_port_v.handle) self._map_handles_port_v[scoped_variable_port_v.handle] = scoped_variable_port_v scoped_variable_port_v.handle.pos = self.width * (0.1 * len(self._scoped_variables_ports)), 0 port_meta = scoped_variable_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): # Distribute scoped variables on the top side of the state, starting from left # print "generate rel_pos" scoped_variable_port_v.side = SnappedSide.BOTTOM number_of_scoped_var = self.model.scoped_variables.index(scoped_variable_m) + 1 pos_x = self._calculate_port_pos_on_line(number_of_scoped_var, self.width, port_width=self.border_width * 4) pos_y = self.height port_meta = scoped_variable_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) # print "add scoped_variable", self.model, self.model.parent, port_meta['rel_pos'] scoped_variable_port_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(scoped_variable_port_v)
def add_outcome(self, outcome_m): outcome_v = OutcomeView(outcome_m, self) self.canvas.add_port(outcome_v) self._outcomes.append(outcome_v) self._ports.append(outcome_v.port) self._handles.append(outcome_v.handle) self._map_handles_port_v[outcome_v.handle] = outcome_v port_meta = outcome_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): # print "generate rel_pos" if outcome_m.outcome.outcome_id < 0: # Position aborted/preempted in upper right corner outcome_v.side = SnappedSide.TOP pos_x = self.width - self._calculate_port_pos_on_line(abs(outcome_m.outcome.outcome_id), self.width) pos_y = 0 else: # Distribute outcomes on the right side of the state, starting from top outcome_v.side = SnappedSide.RIGHT pos_x = self.width number_of_outcome = [o.model for o in self.outcomes if o.model.outcome.outcome_id >= 0].index(outcome_m) + 1 pos_y = self._calculate_port_pos_on_line(number_of_outcome, self.height) port_meta = outcome_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) # print "add outcome", self.model, self.model.parent, port_meta['rel_pos'] outcome_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(outcome_v)
def _meta_data_editor_opengl2gaphas(self, vividict): from rafcon.gui.helpers.meta_data import contains_geometric_info if self.parent: state_size = self.parent.get_meta_data_editor()['size'] if contains_geometric_info(state_size): vividict['rel_pos'] = (0, state_size[1] / 2.) return vividict
def _meta_data_editor_opengl2gaphas(self, vividict): from rafcon.gui.helpers.meta_data import contains_geometric_info rel_pos = vividict['inner_rel_pos'] if contains_geometric_info(rel_pos): vividict['rel_pos'] = (rel_pos[0], 0) else: del vividict['inner_rel_pos'] return vividict
def mirror_y_axis_in_vividict_element(vividict, key): from rafcon.gui.helpers.meta_data import contains_geometric_info rel_pos = vividict[key] if contains_geometric_info(rel_pos): vividict[key] = (rel_pos[0], -rel_pos[1]) else: del vividict[key] return vividict
def _meta_data_editor_opengl2gaphas(self, vividict): from rafcon.gui.helpers.meta_data import contains_geometric_info vividict = mirror_y_axis_in_vividict_element(vividict, 'rel_pos') if contains_geometric_info(vividict['size']): self.temp['conversion_from_opengl'] = True size = vividict['size'] # Determine size and position of NameView margin = min(size) / 12. name_height = min(size) / 8. name_width = size[0] - 2 * margin vividict['name']['size'] = (name_width, name_height) vividict['name']['rel_pos'] = (margin, margin) return vividict
def _meta_data_editor_opengl2gaphas(self, vividict): from rafcon.gui.helpers.meta_data import contains_geometric_info if self.parent: state_size = self.parent.get_meta_data_editor()['size'] if contains_geometric_info(state_size): step = min(state_size) / 10. if self.outcome.outcome_id == -1: # aborted vividict["rel_pos"] = (state_size[0] - step, 0) elif self.outcome.outcome_id == -2: # preempted vividict["rel_pos"] = (state_size[0] - step * 3, 0) else: # user defined outcome num_outcomes = len(self.parent.outcomes) - 2 # count user defined outcomes with smaller id than the current outcome outcome_num = sum(1 for outcome_id in self.parent.state.outcomes if 0 <= outcome_id < self.outcome.outcome_id) vividict["rel_pos"] = (state_size[0], state_size[1] / (num_outcomes + 1) * (outcome_num + 1)) return vividict
def add_income(self): income_v = IncomeView(self) self._ports.append(income_v.port) self._handles.append(income_v.handle) self._map_handles_port_v[income_v.handle] = income_v port_meta = self.model.get_meta_data_editor()['income'] if not contains_geometric_info(port_meta['rel_pos']): # print "generate rel_pos" # Position income on the top of the left state side income_v.side = SnappedSide.LEFT pos_x = 0 pos_y = self._calculate_port_pos_on_line(1, self.height) port_meta = self.model.set_meta_data_editor('income.rel_pos', (pos_x, pos_y))['income'] # print "add income", self.model, self.model.parent, port_meta['rel_pos'] income_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(income_v) return income_v
def add_output_port(self, port_m): output_port_v = OutputPortView(self, port_m) self.canvas.add_port(output_port_v) self._outputs.append(output_port_v) self._ports.append(output_port_v.port) self._handles.append(output_port_v.handle) self._map_handles_port_v[output_port_v.handle] = output_port_v port_meta = port_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): output_port_v.side = SnappedSide.RIGHT number_of_output = self.model.output_data_ports.index(port_m) + 1 pos_x = self.width pos_y = self.height - self._calculate_port_pos_on_line( number_of_output, self.height) port_meta = port_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) output_port_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(output_port_v)
def add_input_port(self, port_m): input_port_v = InputPortView(self, port_m) self.canvas.add_port(input_port_v) self._inputs.append(input_port_v) self._ports.append(input_port_v.port) self._handles.append(input_port_v.handle) self._map_handles_port_v[input_port_v.handle] = input_port_v port_meta = port_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): # Distribute input ports on the left side of the state, starting from bottom input_port_v.side = SnappedSide.LEFT number_of_input = self.model.input_data_ports.index(port_m) + 1 pos_x = 0 pos_y = self.height - self._calculate_port_pos_on_line( number_of_input, self.height) port_meta = port_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) input_port_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(input_port_v)
def add_income(self, income_m): income_v = IncomeView(income_m, self) self.canvas.add_port(income_v) self._income = income_v self._ports.append(income_v.port) self._handles.append(income_v.handle) self._map_handles_port_v[income_v.handle] = income_v port_meta = income_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): # Position income on the top of the left state side income_v.side = SnappedSide.LEFT pos_x = 0 pos_y = self._calculate_port_pos_on_line(1, self.height) port_meta = income_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) income_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(income_v) return income_v
def add_output_port(self, port_m): output_port_v = OutputPortView(self, port_m) self.canvas.add_port(output_port_v) self._outputs.append(output_port_v) self._ports.append(output_port_v.port) self._handles.append(output_port_v.handle) self._map_handles_port_v[output_port_v.handle] = output_port_v port_meta = port_m.get_meta_data_editor() if not contains_geometric_info(port_meta['rel_pos']): # Distribute output ports on the right side of the state, starting from bottom # print "generate rel_pos" output_port_v.side = SnappedSide.RIGHT number_of_output = self.model.output_data_ports.index(port_m) + 1 pos_x = self.width pos_y = self.height - self._calculate_port_pos_on_line(number_of_output, self.height) port_meta = port_m.set_meta_data_editor('rel_pos', (pos_x, pos_y)) # print "add output_port", self.model, self.model.parent, port_meta['rel_pos'] output_port_v.handle.pos = port_meta['rel_pos'] self.add_rect_constraint_for_port(output_port_v)
def update_port_position(port_v, meta_data): if contains_geometric_info(meta_data['rel_pos']): port_v.handle.pos = meta_data['rel_pos'] self.port_constraints[port_v].update_position( meta_data['rel_pos'])