Exemple #1
0
void CutTool::updateHoverState(QPointF cursor_pos_screen, MapWidget* widget)
{
	HoverState new_hover_state = HoverFlag::OverNothing;
	const Object* new_hover_object = nullptr;
	MapCoordVector::size_type new_hover_point = 0;
	
	if (map()->selectedObjects().size() <= max_objects_for_handle_display)
	{
		auto best_distance_sq = std::numeric_limits<double>::max();
		for (const auto object : map()->selectedObjects())
		{
			MapCoordF handle_pos;
			auto hover_point = findHoverPoint(cursor_pos_screen, widget, object, false, &handle_pos);
			if (hover_point == std::numeric_limits<MapCoordVector::size_type>::max())
				continue;
			
			auto distance_sq = widget->viewportToMapF(cursor_pos_screen).distanceSquaredTo(handle_pos);
			if (distance_sq < best_distance_sq)
			{
				new_hover_state  = HoverFlag::OverObjectNode;
				new_hover_object = object;
				new_hover_point  = hover_point;
				best_distance_sq = distance_sq;
			}
		}
	}	
	
	if (new_hover_state  != hover_state  ||
	    new_hover_object != hover_object ||
	    new_hover_point  != hover_point)
	{
		hover_state  = new_hover_state;
		// We have got a Map*, so we may get a Object*.
		hover_object = const_cast<Object*>(new_hover_object);
		hover_point  = new_hover_point;
		updateDirtyRect();
	}
}
Exemple #2
0
void EditPointTool::updateHoverState(MapCoordF cursor_pos)
{
	HoverState new_hover_state = OverNothing;
	const Object* new_hover_object = nullptr;
	MapCoordVector::size_type new_hover_point = no_point;
	
	if (text_editor)
	{
		handle_offset = MapCoordF(0, 0);
	}
	else if (!map()->selectedObjects().empty())
	{
		if (map()->selectedObjects().size() <= max_objects_for_handle_display)
		{
			// Try to find object node.
			auto best_distance_sq = std::numeric_limits<double>::max();
			for (const auto object : map()->selectedObjects())
			{
				MapCoordF handle_pos;
				auto hover_point = findHoverPoint(cur_map_widget->mapToViewport(cursor_pos), cur_map_widget, object, true, &handle_pos);
				if (hover_point == no_point)
					continue;
				
				auto distance_sq = cursor_pos.distanceSquaredTo(handle_pos);
				if (distance_sq < best_distance_sq)
				{
					new_hover_state |= OverObjectNode;
					new_hover_object = object;
					new_hover_point  = hover_point;
					best_distance_sq = distance_sq;
					handle_offset    = handle_pos - cursor_pos;
				}
			}
			
			if (!new_hover_state.testFlag(OverObjectNode))
			{
				// No object node found. Try to find path object edge.
				/// \todo De-duplicate: Copied from EditLineTool
				auto click_tolerance_sq = qPow(0.001 * cur_map_widget->getMapView()->pixelToLength(clickTolerance()), 2);
				
				for (auto object : map()->selectedObjects())
				{
					if (object->getType() == Object::Path)
					{
						PathObject* path = object->asPath();
						float distance_sq;
						PathCoord path_coord;
						path->calcClosestPointOnPath(cursor_pos, distance_sq, path_coord);
						
						if (distance_sq >= +0.0 &&
						    distance_sq < best_distance_sq &&
						    distance_sq < qMax(click_tolerance_sq, qPow(path->getSymbol()->calculateLargestLineExtent(map()), 2)))
						{
							new_hover_state |= OverPathEdge;
							new_hover_object = path;
							new_hover_point  = path_coord.index;
							best_distance_sq = distance_sq;
							handle_offset    = path_coord.pos - cursor_pos;
						}
					}
				}
			}
		}
		
		if (!new_hover_state.testFlag(OverObjectNode) && selection_extent.isValid())
		{
			QRectF selection_extent_viewport = cur_map_widget->mapToViewport(selection_extent);
			if (pointOverRectangle(cur_map_widget->mapToViewport(cursor_pos), selection_extent_viewport))
			{
				new_hover_state |= OverFrame;
				handle_offset    = closestPointOnRect(cursor_pos, selection_extent) - cursor_pos;
			}
		}
	}
	
	if (new_hover_state  != hover_state  ||
	    new_hover_object != hover_object ||
	    new_hover_point  != hover_point)
	{
		hover_state = new_hover_state;
		// We have got a Map*, so we may get an non-const Object*.
		hover_object = const_cast<Object*>(new_hover_object);
		hover_point  = new_hover_point;
		if (hover_state != OverNothing)
			start_drag_distance = 0;
		else
			start_drag_distance = Settings::getInstance().getStartDragDistancePx();
		updateDirtyRect();
	}
	
	Q_ASSERT((hover_state.testFlag(OverObjectNode) || hover_state.testFlag(OverPathEdge)) == (hover_object != nullptr));
}