static int set_Cmiss_mesh(struct Parse_state *state, void *region_void, void *mesh_address_void) { Cmiss_region_id region = reinterpret_cast<Cmiss_region_id>(region_void); Cmiss_mesh_id *mesh_address = reinterpret_cast<Cmiss_mesh_id*>(mesh_address_void); if (!(state && region && mesh_address)) return 0; const char *current_token = state->current_token; int return_code = 1; if (!current_token) { display_message(WARNING_MESSAGE, "Missing mesh name"); display_parse_state_location(state); return_code = 0; } else if ((0 == strcmp(PARSER_HELP_STRING, current_token)) || (0 == strcmp(PARSER_RECURSIVE_HELP_STRING, current_token))) { display_message(INFORMATION_MESSAGE, " ELEMENT_GROUP_FIELD_NAME|[GROUP_NAME.]cmiss_mesh_1d|cmiss_mesh_2d|cmiss_mesh_3d["); if (*mesh_address) { char *mesh_name = Cmiss_mesh_get_name(*mesh_address); make_valid_token(&mesh_name); display_message(INFORMATION_MESSAGE, "%s]", mesh_name); DEALLOCATE(mesh_name); } else { display_message(INFORMATION_MESSAGE, "none]"); } } else { Cmiss_field_module_id field_module = Cmiss_region_get_field_module(region); Cmiss_mesh_id new_mesh = Cmiss_field_module_find_mesh_by_name(field_module, current_token); if (new_mesh) { if (*mesh_address) Cmiss_mesh_destroy(mesh_address); *mesh_address = new_mesh; shift_Parse_state(state, 1); } else { display_message(ERROR_MESSAGE, "Invalid mesh: %s", current_token); display_parse_state_location(state); return_code = 0; } Cmiss_field_module_destroy(&field_module); } return return_code; }
StrainMeasures::StrainMeasures(std::vector<std::string> mesh) : mySegments(NULL) { num_level_sets = 10; num_elements = 48; num_nodes = 98; elements.resize(num_elements); x_discret = 25; y_discret = 25; lagrangian = true; modelPGS = 0.0; computeModelPGS = false; ejectionFraction = 0.0; extraNodeStartID = 100000; LVMyocardialVolume* lvm = new LVMyocardialVolume(mesh); volumes = lvm->getMyocardialVolumes(); delete lvm; //Read the mesh context_ = Cmiss_context_create("strainmeasure"); /**< Handle to the context */ Cmiss_region_id root_region = Cmiss_context_get_default_region(context_); //This required for using the cmiss_context_execute_command Cmiss_context_enable_user_interface(context_, NULL); //Load the finite element mesh of the heart std::string region_name = "heart"; Cmiss_region_id heart_region = Cmiss_region_create_child(root_region, region_name.c_str()); //Get the field module of the heart region field_module = Cmiss_region_get_field_module(heart_region); fieldCache = Cmiss_field_module_create_cache(field_module); numberOfModelFrames_ = mesh.size(); double denom = numberOfModelFrames_ - 1; for (unsigned int i = 0; i < numberOfModelFrames_; i++) { double time = static_cast<double>(i) / denom; Cmiss_stream_information_id stream_information = Cmiss_region_create_stream_information(root_region); Cmiss_stream_information_region_id stream_information_region = Cmiss_stream_information_cast_region(stream_information); Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, mesh[i].c_str(), mesh[i].length()); Cmiss_stream_information_region_set_resource_attribute_real(stream_information_region, stream_resource, CMISS_STREAM_INFORMATION_REGION_ATTRIBUTE_TIME, time); Cmiss_region_read(root_region, stream_information); Cmiss_stream_resource_destroy(&stream_resource); Cmiss_stream_information_destroy(&stream_information); Cmiss_stream_information_region_destroy(&stream_information_region); } { //Define the necessary fields std::string referenceMesh = mesh[0]; //Change coordinate name to reference_coordinates boost::replace_all(referenceMesh, "1) coordinates", "1) reference_coordinates"); //Load the reference coordinates mesh Cmiss_stream_information_id stream_information = Cmiss_region_create_stream_information(root_region); Cmiss_stream_information_region_id stream_information_region = Cmiss_stream_information_cast_region(stream_information); Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, referenceMesh.c_str(), referenceMesh.length()); Cmiss_region_read(root_region, stream_information); Cmiss_stream_resource_destroy(&stream_resource); Cmiss_stream_information_destroy(&stream_information); } coordianteField = Cmiss_field_module_find_field_by_name(field_module, "reference_coordinates"); if (!coordianteField) { std::cout << "reference_coordinates field not found " << std::endl; } Cmiss_region_destroy(&heart_region); //#Calculate the strains Cmiss_field_module_define_field(field_module, "F", "gradient coordinate reference_coordinates field coordinates"); Cmiss_field_module_define_field(field_module, "F_transpose", "transpose source_number_of_rows 3 field F"); Cmiss_field_module_define_field(field_module, "C", "matrix_multiply number_of_rows 3 fields F_transpose F"); Cmiss_field_module_define_field(field_module, "principal_strains", "eigenvalues field C"); Cmiss_field_destroy(&coordianteField); //Assign the coordinates field to the handle for downstream use coordianteField = Cmiss_field_module_find_field_by_name(field_module, "coordinates"); //Define the fibre field { //Load the reference fibre data and reference coordinates { if (Cmiss_field_module_find_field_by_name(field_module, "fibres") == NULL) { Cmiss_stream_information_id stream_information = Cmiss_region_create_stream_information(root_region); Cmiss_stream_information_region_id stream_information_region = Cmiss_stream_information_cast_region(stream_information); //Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, reffibre_exregion, reffibre_exregion_len); Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, humandtifibre_exregion, humandtifibre_exregion_len); Cmiss_region_read(root_region, stream_information); Cmiss_stream_resource_destroy(&stream_resource); Cmiss_stream_information_destroy(&stream_information); } //Define fibre field //#Calculate the deformed fibre axes Cmiss_field_module_define_field(field_module, "fibre_axes", "fibre_axes coordinate reference_coordinates fibre fibres"); Cmiss_field_module_define_field(field_module, "deformed_fibre_axes", "matrix_multiply number_of_rows 3 fields fibre_axes F_transpose"); Cmiss_field_module_define_field(field_module, "deformed_fibre", "composite deformed_fibre_axes.1 deformed_fibre_axes.2 deformed_fibre_axes.3"); Cmiss_field_module_define_field(field_module, "principal_fibre_strain1", "composite deformed_fibre_axes.1"); } } //Determine the myocardial volume //Get the element and node handles Cmiss_mesh_id cmiss_mesh = Cmiss_field_module_find_mesh_by_name(field_module, "cmiss_mesh_3d"); Cmiss_element_iterator_id elementIterator = Cmiss_mesh_create_element_iterator(cmiss_mesh); Cmiss_element_id element = Cmiss_element_iterator_next(elementIterator); while (element != NULL) { int elementId = Cmiss_element_get_identifier(element) - 1; //Cmiss numbering starts at 1 elements[elementId] = element; element = Cmiss_element_iterator_next(elementIterator); } Cmiss_element_iterator_destroy(&elementIterator); Cmiss_mesh_destroy(&cmiss_mesh); Cmiss_region_destroy(&root_region); }
static void Element_tool_interactive_event_handler(void *device_id, struct Interactive_event *event,void *element_tool_void, struct Graphics_buffer *graphics_buffer) /******************************************************************************* LAST MODIFIED 18 November 2005 DESCRIPTION : Input handler for input from devices. <device_id> is a unique address enabling the editor to handle input from more than one device at a time. The <event> describes the type of event, button numbers and key modifiers, and the volume of space affected by the interaction. Main events are button press, movement and release. ==============================================================================*/ { enum Interactive_event_type event_type; FE_value time, xi[MAXIMUM_ELEMENT_XI_DIMENSIONS]; int clear_selection, element_dimension, i, input_modifier, number_of_xi_points, shift_pressed; int number_in_xi[MAXIMUM_ELEMENT_XI_DIMENSIONS]; struct FE_element *picked_element; struct FE_element_shape *element_shape; struct Element_tool *element_tool; struct Interaction_volume *interaction_volume,*temp_interaction_volume; struct LIST(Scene_picked_object) *scene_picked_object_list; struct Scene *scene; struct Cmiss_rendition *rendition = NULL; FE_value_triple *xi_points; ENTER(Element_tool_interactive_event_handler); if (device_id&&event&&(element_tool= (struct Element_tool *)element_tool_void)) { Cmiss_region_begin_hierarchical_change(element_tool->region); interaction_volume=Interactive_event_get_interaction_volume(event); scene=Interactive_event_get_scene(event); if (scene != 0) { event_type=Interactive_event_get_type(event); input_modifier=Interactive_event_get_input_modifier(event); shift_pressed=(INTERACTIVE_EVENT_MODIFIER_SHIFT & input_modifier); switch (event_type) { case INTERACTIVE_EVENT_BUTTON_PRESS: { /* interaction only works with first mouse button */ if (1==Interactive_event_get_button_number(event)) { scene_picked_object_list= Scene_pick_objects(scene,interaction_volume,graphics_buffer); if (scene_picked_object_list != 0) { element_tool->picked_element_was_unselected=1; if (0 != (picked_element=Scene_picked_object_list_get_nearest_element( scene_picked_object_list,(struct Cmiss_region *)NULL, element_tool->select_elements_enabled, element_tool->select_faces_enabled, element_tool->select_lines_enabled, (struct Scene_picked_object **)NULL, &rendition, (struct Cmiss_graphic **)NULL))) { /* Open command_field of picked_element in browser */ if (element_tool->command_field) { if (element_tool->time_keeper) { time = Time_keeper_get_time(element_tool->time_keeper); } else { time = 0; } /* since we don't really have fields constant over an element, evaluate at its centre */ element_dimension = get_FE_element_dimension(picked_element); for (i = 0; i < element_dimension; i++) { number_in_xi[i] = 1; } get_FE_element_shape(picked_element, &element_shape); if (FE_element_shape_get_xi_points_cell_centres( element_shape, number_in_xi, &number_of_xi_points, &xi_points)) { /*???debug*/printf("element_tool: xi ="); for (i = 0; i < element_dimension; i++) { xi[i] = xi_points[0][i]; /*???debug*/printf(" %g",xi[i]); } /*???debug*/printf("\n"); Cmiss_field_module_id field_module = Cmiss_field_get_field_module(element_tool->command_field); Cmiss_field_cache_id field_cache = Cmiss_field_module_create_cache(field_module); Cmiss_field_cache_set_time(field_cache, time); Cmiss_field_cache_set_mesh_location(field_cache, picked_element, element_dimension, xi); char *command_string = Cmiss_field_evaluate_string(element_tool->command_field, field_cache); if (command_string) { Execute_command_execute_string(element_tool->execute_command, command_string); DEALLOCATE(command_string); } Cmiss_field_cache_destroy(&field_cache); Cmiss_field_module_destroy(&field_module); DEALLOCATE(xi_points); } } Cmiss_field_group_id group = Cmiss_rendition_get_selection_group(rendition); if (group) { Cmiss_region_id temp_region = Cmiss_rendition_get_region(rendition); Cmiss_field_module_id field_module = Cmiss_region_get_field_module(temp_region); int dimension = Cmiss_element_get_dimension(picked_element); Cmiss_mesh_id master_mesh = Cmiss_field_module_find_mesh_by_dimension(field_module, dimension); Cmiss_field_element_group_id element_group = Cmiss_field_group_get_element_group(group, master_mesh); Cmiss_mesh_destroy(&master_mesh); if (element_group) { Cmiss_mesh_group_id mesh_group = Cmiss_field_element_group_get_mesh(element_group); element_tool->picked_element_was_unselected = !Cmiss_mesh_contains_element(Cmiss_mesh_group_base_cast(mesh_group), picked_element); Cmiss_mesh_group_destroy(&mesh_group); Cmiss_field_element_group_destroy(&element_group); } Cmiss_field_group_destroy(&group); Cmiss_field_module_destroy(&field_module); } } REACCESS(FE_element)(&(element_tool->last_picked_element), picked_element); /*(if ((clear_selection = !shift_pressed) &&((!picked_element)|| (element_tool->picked_element_was_unselected)))*/ clear_selection = !shift_pressed; if (clear_selection) { if (element_tool->region) { Cmiss_rendition *root_rendition = Cmiss_region_get_rendition_internal(element_tool->region); Cmiss_field_group_id root_group = Cmiss_rendition_get_selection_group(root_rendition); if (root_group) { Cmiss_field_group_clear_region_tree_element(root_group); Cmiss_field_group_destroy(&root_group); } Cmiss_rendition_destroy(&root_rendition); } } if (picked_element) { REACCESS(Cmiss_rendition)(&(element_tool->rendition), rendition); Cmiss_region *sub_region = NULL; Cmiss_field_group_id sub_group = NULL; Cmiss_mesh_group_id mesh_group = 0; if (element_tool->rendition) { sub_region = Cmiss_rendition_get_region(element_tool->rendition); sub_group = Cmiss_rendition_get_or_create_selection_group(element_tool->rendition); if (sub_group) { int dimension = Cmiss_element_get_dimension(picked_element); Cmiss_field_module_id field_module = Cmiss_region_get_field_module(sub_region); Cmiss_mesh_id temp_mesh = Cmiss_field_module_find_mesh_by_dimension(field_module, dimension); Cmiss_field_element_group_id element_group = Cmiss_field_group_get_element_group(sub_group, temp_mesh); if (!element_group) element_group = Cmiss_field_group_create_element_group(sub_group, temp_mesh); mesh_group = Cmiss_field_element_group_get_mesh(element_group); Cmiss_field_element_group_destroy(&element_group); Cmiss_mesh_destroy(&temp_mesh); Cmiss_field_module_destroy(&field_module); } } if (mesh_group) { Cmiss_mesh_group_add_element(mesh_group, picked_element); Cmiss_mesh_group_destroy(&mesh_group); } if (sub_group) { Cmiss_field_group_destroy(&sub_group); } } DESTROY(LIST(Scene_picked_object))(&(scene_picked_object_list)); } element_tool->motion_detected=0; REACCESS(Interaction_volume)( &(element_tool->last_interaction_volume),interaction_volume); } } break; case INTERACTIVE_EVENT_MOTION_NOTIFY: case INTERACTIVE_EVENT_BUTTON_RELEASE: { if (element_tool->last_interaction_volume&& ((INTERACTIVE_EVENT_MOTION_NOTIFY==event_type) || (1==Interactive_event_get_button_number(event)))) { if (INTERACTIVE_EVENT_MOTION_NOTIFY==event_type) { element_tool->motion_detected=1; } if (element_tool->last_picked_element) { /* unselect last_picked_element if not just added */ if ((INTERACTIVE_EVENT_BUTTON_RELEASE==event_type)&& shift_pressed&&(!(element_tool->picked_element_was_unselected))) { struct LIST(FE_element) *temp_element_list = CREATE(LIST(FE_element))(); ADD_OBJECT_TO_LIST(FE_element)(element_tool->last_picked_element, temp_element_list); Cmiss_rendition_remove_selection_from_element_list_of_dimension(element_tool->rendition, temp_element_list, Cmiss_element_get_dimension(element_tool->last_picked_element)); DESTROY(LIST(FE_element))(&temp_element_list); } } else if (element_tool->motion_detected) { /* rubber band select */ temp_interaction_volume= create_Interaction_volume_bounding_box( element_tool->last_interaction_volume,interaction_volume); if (temp_interaction_volume != 0) { if (INTERACTIVE_EVENT_MOTION_NOTIFY==event_type) { if (!element_tool->rubber_band) { /* create rubber_band object and put in scene */ element_tool->rubber_band=CREATE(GT_object)( "element_tool_rubber_band",g_POLYLINE, element_tool->rubber_band_material); ACCESS(GT_object)(element_tool->rubber_band); } Interaction_volume_make_polyline_extents( temp_interaction_volume,element_tool->rubber_band); } else { #if defined (USE_SCENE_OBJECT) Scene_remove_graphics_object(scene,element_tool->rubber_band); #endif DEACCESS(GT_object)(&(element_tool->rubber_band)); } if (INTERACTIVE_EVENT_BUTTON_RELEASE==event_type) { scene_picked_object_list= Scene_pick_objects(scene,temp_interaction_volume, graphics_buffer); if (scene_picked_object_list != 0) { Region_element_map *element_map = (Region_element_map *)Scene_picked_object_list_get_picked_region_sorted_elements( scene_picked_object_list, element_tool->select_elements_enabled, element_tool->select_faces_enabled, element_tool->select_lines_enabled); if (element_map) { Cmiss_region *sub_region = NULL; Cmiss_field_group_id sub_group = NULL; Cmiss_rendition *region_rendition = NULL; Cmiss_mesh_group_id mesh_group[MAXIMUM_ELEMENT_XI_DIMENSIONS]; int iter = 0; for (iter = 0; iter < MAXIMUM_ELEMENT_XI_DIMENSIONS; iter++) { mesh_group[iter] = 0; } Region_element_map::iterator pos; for (pos = element_map->begin(); pos != element_map->end(); ++pos) { if (pos->first != sub_region) { if (sub_group) { Cmiss_field_group_destroy(&sub_group); } for (iter = 0; iter < MAXIMUM_ELEMENT_XI_DIMENSIONS; iter++) { if (mesh_group[iter]) { Cmiss_mesh_group_destroy(&(mesh_group[iter])); } } if (region_rendition) { Cmiss_rendition_destroy(®ion_rendition); } sub_region = pos->first; if (sub_region) { region_rendition= Cmiss_region_get_rendition_internal(sub_region); sub_group = Cmiss_rendition_get_or_create_selection_group(region_rendition); } } if (sub_region && sub_group) { Cmiss_field_module_id field_module = Cmiss_region_get_field_module(sub_region); int dimension = Cmiss_element_get_dimension(pos->second); if (dimension <= MAXIMUM_ELEMENT_XI_DIMENSIONS) { if (!mesh_group[dimension - 1]) { Cmiss_mesh_id temp_mesh = Cmiss_field_module_find_mesh_by_dimension(field_module, dimension); Cmiss_field_element_group_id element_group = Cmiss_field_group_get_element_group(sub_group, temp_mesh); if (!element_group) { element_group = Cmiss_field_group_create_element_group(sub_group, temp_mesh); } mesh_group[dimension - 1] = Cmiss_field_element_group_get_mesh(element_group); Cmiss_field_element_group_destroy(&element_group); Cmiss_mesh_destroy(&temp_mesh); } Cmiss_mesh_group_add_element(mesh_group[dimension - 1], pos->second); } Cmiss_field_module_destroy(&field_module); } } if (sub_group) { Cmiss_field_group_destroy(&sub_group); } for (iter = 0; iter < MAXIMUM_ELEMENT_XI_DIMENSIONS; iter++) { if (mesh_group[iter]) { Cmiss_mesh_group_destroy(&(mesh_group[iter])); } } if (region_rendition) { Cmiss_rendition_destroy(®ion_rendition); } delete element_map; } DESTROY(LIST(Scene_picked_object))( &(scene_picked_object_list)); } } DESTROY(Interaction_volume)(&temp_interaction_volume); } } if (INTERACTIVE_EVENT_BUTTON_RELEASE==event_type) { Element_tool_reset((void *)element_tool); } } } break; default: { display_message(ERROR_MESSAGE, "Element_tool_interactive_event_handler. Unknown event type"); } break; }
ShortAxisFitting::ShortAxisFitting(std::vector<std::string> mesh, std::vector<std::vector<Point3D> > markers) : inputMesh(mesh), saxMarkers(markers) { numberOfModelFrames_ = mesh.size(); cmiss_nodes.resize(98); //Load the mesh //Initialise cmgui and get context context_ = Cmiss_context_create("saxfit"); //This required for using the cmiss_context_execute_command Cmiss_context_enable_user_interface(context_, NULL); /**< Handle to the context */ Cmiss_region_id root_region = Cmiss_context_get_default_region(context_); std::string region_name = "heart"; // Create a heart region Cmiss_region_id heart_region = Cmiss_region_create_child(root_region, region_name.c_str()); // Read in the heart model spaced over the number of model frames for (unsigned int i = 0; i < numberOfModelFrames_ - 1; i++) { double time = static_cast<double>(i) / numberOfModelFrames_; Cmiss_stream_information_id stream_information = Cmiss_region_create_stream_information(root_region); Cmiss_stream_information_region_id stream_information_region = Cmiss_stream_information_cast_region(stream_information); Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, mesh[i].c_str(), mesh[i].length()); Cmiss_stream_information_region_set_resource_attribute_real(stream_information_region, stream_resource, CMISS_STREAM_INFORMATION_REGION_ATTRIBUTE_TIME, time); Cmiss_region_read(root_region, stream_information); Cmiss_stream_resource_destroy(&stream_resource); Cmiss_stream_information_destroy(&stream_information); Cmiss_stream_information_region_destroy(&stream_information_region); } // Wrap the end point add another set of nodes at time 1.0 { Cmiss_stream_information_id stream_information = Cmiss_region_create_stream_information(root_region); Cmiss_stream_information_region_id stream_information_region = Cmiss_stream_information_cast_region(stream_information); Cmiss_stream_resource_id stream_resource = Cmiss_stream_information_create_resource_memory_buffer(stream_information, mesh[0].c_str(), mesh[0].length()); int r = Cmiss_stream_information_region_set_resource_attribute_real(stream_information_region, stream_resource, CMISS_STREAM_INFORMATION_REGION_ATTRIBUTE_TIME, 1.0); Cmiss_region_read(root_region, stream_information); Cmiss_stream_resource_destroy(&stream_resource); Cmiss_stream_information_destroy(&stream_information); Cmiss_stream_information_region_destroy(&stream_information_region); } //Cmiss_region_id heart_region = Cmiss_region_find_child_by_name(root_region, region_name.c_str()); //Get the field module of the heart region field_module_ = Cmiss_region_get_field_module(heart_region); if (field_module_ != 0) { Cmiss_field_module_begin_change(field_module_); // 'coordinates' is an assumed field in // a rc coordinate system. coordinates_rc_ = Cmiss_field_module_find_field_by_name(field_module_, "coordinates"); //Create the cache cache = Cmiss_field_module_create_cache(field_module_); Cmiss_field_module_end_change(field_module_); //Get node handles Cmiss_nodeset_id nodeset = Cmiss_field_module_find_nodeset_by_name(field_module_, "cmiss_nodes"); Cmiss_node_iterator_id nodeIterator = Cmiss_nodeset_create_node_iterator(nodeset); Cmiss_node_id node = Cmiss_node_iterator_next(nodeIterator); if (node != 0) { while (node) { int node_id = Cmiss_node_get_identifier(node); cmiss_nodes[node_id - 1] = node; node = Cmiss_node_iterator_next(nodeIterator); } } Cmiss_nodeset_destroy(&nodeset); Cmiss_node_iterator_destroy(&nodeIterator); int endo[] = { 55, 57, 71, 73, 66, 67, 69, 60, 61, 63, 52, 53, 54, 56, 70, 72, 64, 65, 68, 58, 59, 62, 50, 51, 77, 84, 85, 81, 82, 83, 78, 79, 80, 74, 75, 76, 89, 96, 97, 93, 94, 95, 90, 91, 92, 86, 87, 88, 98 }; memcpy(endoNodeIds, endo, sizeof(int) * 49); //int sax[] = { 73, 74, 75, 76, 83, 84, 80, 81, 82, 77, 78, 79 }; //int sax[] = { 79, 78, 77, 82, 81, 80, 84, 83, 76, 75, 74, 73 }; int sax[] = { 80, 81, 82, 77, 78, 79, 73, 74, 75, 76, 83, 84 }; memcpy(saxNodes, sax, sizeof(int) * NUMBER_OF_SAX_NODES); segmentNodes = new double*[24]; for (int i = 0; i < 24; i++) { segmentNodes[i] = new double[2]; } //Store the initial endo coordinates const int NUMBER_OF_ENDO_NODES = 48; //Skip apex double coord[3]; for(int frame = 0;frame<numberOfModelFrames_;frame++){ std::vector<Point3D> frameCoords; Cmiss_field_module_begin_change(field_module_); { double time = ((double) frame) / ((double) numberOfModelFrames_); if (frame == (numberOfModelFrames_ - 1)) { time = 1.0; } Cmiss_field_cache_set_time(cache, time); for (int nc = 0; nc < NUMBER_OF_ENDO_NODES; nc++) { Cmiss_field_cache_set_node(cache, cmiss_nodes[endoNodeIds[nc] - 1]); Cmiss_field_evaluate_real(coordinates_rc_, cache, 3, coord); Point3D start(coord); frameCoords.push_back(start); } initEndoCoordinates.push_back(frameCoords); } Cmiss_field_module_end_change(field_module_); } //Set the segment node ids segmentNodes[0][0] = aplaxNodes0; segmentNodes[0][1] = aplaxNodes1; segmentNodes[1][0] = aplaxNodes1; segmentNodes[1][1] = aplaxNodes2; segmentNodes[2][0] = aplaxNodes2; segmentNodes[2][1] = aplaxNodes3; segmentNodes[3][0] = aplaxNodes3; segmentNodes[3][1] = aplaxNodes4; segmentNodes[4][0] = aplaxNodes4; segmentNodes[4][1] = aplaxNodes5; segmentNodes[5][0] = aplaxNodes5; segmentNodes[5][1] = aplaxNodes6; segmentNodes[6][0] = aplaxNodes6; segmentNodes[6][1] = aplaxNodes7; segmentNodes[7][0] = aplaxNodes7; segmentNodes[7][1] = aplaxNodes8; segmentNodes[8][0] = tchNodes0; segmentNodes[8][1] = tchNodes1; segmentNodes[9][0] = tchNodes1; segmentNodes[9][1] = tchNodes2; segmentNodes[10][0] = tchNodes2; segmentNodes[10][1] = tchNodes3; segmentNodes[11][0] = tchNodes3; segmentNodes[11][1] = tchNodes4; segmentNodes[12][0] = tchNodes4; segmentNodes[12][1] = tchNodes5; segmentNodes[13][0] = tchNodes5; segmentNodes[13][1] = tchNodes6; segmentNodes[14][0] = tchNodes6; segmentNodes[14][1] = tchNodes7; segmentNodes[15][0] = tchNodes7; segmentNodes[15][1] = tchNodes8; segmentNodes[16][0] = fchNodes0; segmentNodes[16][1] = fchNodes1; segmentNodes[17][0] = fchNodes1; segmentNodes[17][1] = fchNodes2; segmentNodes[18][0] = fchNodes2; segmentNodes[18][1] = fchNodes3; segmentNodes[19][0] = fchNodes3; segmentNodes[19][1] = fchNodes4; segmentNodes[20][0] = fchNodes4; segmentNodes[20][1] = fchNodes5; segmentNodes[21][0] = fchNodes5; segmentNodes[21][1] = fchNodes6; segmentNodes[22][0] = fchNodes6; segmentNodes[22][1] = fchNodes7; segmentNodes[23][0] = fchNodes7; segmentNodes[23][1] = fchNodes8; //Compute the segment lengths initialSegmentLengths = new double[NUMBER_OF_SEGMENTS * numberOfModelFrames_]; ShortAxisOptimizationInput input; input.NUMBER_OF_SEGMENTS = NUMBER_OF_SEGMENTS; input.cache = cache; input.cmiss_nodes = &cmiss_nodes; input.coordinates_rc = coordinates_rc_; input.result = &initialSegmentLengths; input.numberOfModelFrames = numberOfModelFrames_; input.initialSegmentLengths = NULL; input.segmentNodes = segmentNodes; getSegmentLengths(&input); //Compute the average rotation that of the sax markers std::vector<Point3D>& iptCoord(saxMarkers[0]); unsigned int numSaxMarkers = iptCoord.size(); Point3D saxCentroid(0, 0, 0); for (int i = 0; i < numSaxMarkers; i++) { saxCentroid += iptCoord[i]; } saxCentroid = saxCentroid*(-1.0/numSaxMarkers); initFrame = iptCoord; for (int i = 0; i < numSaxMarkers; i++) { initFrame[i]+=saxCentroid; } for(int frame = 0;frame<numberOfModelFrames_;frame++){ std::vector<Point3D>& ipCoord(saxMarkers[frame]); unsigned int numSaxMarkers = ipCoord.size(); Point3D saxcentroid(0, 0, 0); for (int i = 0; i < numSaxMarkers; i++) { saxcentroid += ipCoord[i]; } saxcentroid = saxcentroid*(-1.0/numSaxMarkers); std::vector<Point3D> currentFrame(ipCoord); for (int i = 0; i < numSaxMarkers; i++) { currentFrame[i]+=saxcentroid; } double avgAngle = 0.0; for (int i = 0; i < numSaxMarkers; i++) { avgAngle += (atan2(currentFrame[i].z-initFrame[i].z,currentFrame[i].x-initFrame[i].x)); } avgAngle /=numSaxMarkers; targetDeltas.push_back(avgAngle); std::cout<<frame<<"\t"<<avgAngle*180/M_PI<<std::endl; } //The initFrame markers should correspond to the initFrame of the mesh as that is what is used in the comparisons initFrame.clear(); Point3D sax_centroid(0, 0, 0); for (int seg = 0; seg < NUMBER_OF_SAX_NODES; seg++) { Cmiss_field_cache_set_node(cache, cmiss_nodes[saxNodes[seg]]); Cmiss_field_evaluate_real(coordinates_rc_, cache, 3, coord); Point3D start(coord); initFrame.push_back(start); sax_centroid += start; } sax_centroid = sax_centroid * (-1.0 / NUMBER_OF_SAX_NODES); for (int seg = 0; seg < NUMBER_OF_SAX_NODES; seg++) { initFrame[seg] += sax_centroid; } } else { std::cout << "--- No field module for heart region!!! (Short Axis Fitting)"; std::cout << "No field module " << std::endl; throw -1; } Cmiss_region_destroy(&heart_region); Cmiss_region_destroy(&root_region); }