<commit_before>#include "CameraForm.h"
#include "Object.h"
#include "Director.h"
#include "TransformPipelineParam.h"

using namespace Math;
using namespace std;
using namespace Rendering::Light;
using namespace Device;
using namespace Core;
using namespace Rendering::Camera;
using namespace Rendering::Manager;

CameraForm::CameraForm()
	: Component(), _frustum(nullptr), _renderTarget(nullptr)
{
}

CameraForm::~CameraForm(void)
{

}

void CameraForm::OnInitialize()
{
	_fieldOfViewDegree	= 60.0f;
	_clippingNear		= 0.1f;
	_clippingFar		= 1000.0f;

	const Size<unsigned int>& backBufferSize = Director::GetInstance()->GetBackBufferSize();
	_aspect = (float)backBufferSize.w / (float)backBufferSize.h;

	_projectionType    = ProjectionType::Perspective;
	_clearColor = Color(0.5f, 0.5f, 1.0f, 1.0f);

	_frustum = new Frustum(0.0f);

	_renderTarget = new Texture::RenderTexture;
	_renderTarget->Initialize(backBufferSize, DXGI_FORMAT_R8G8B8A8_UNORM);

	_camConstBuffer = new Buffer::ConstBuffer;
	if(_camConstBuffer->Initialize(sizeof(ConstBufferParam)) == false)
		ASSERT_MSG("Error, cam->constbuffer->Initialize");

	//_clearFlag = ClearFlag::FlagSolidColor;
}

void CameraForm::OnDestroy()
{
	SAFE_DELETE(_frustum);
	SAFE_DELETE(_renderTarget);
}

void CameraForm::CalcAspect()
{
	const Size<unsigned int>& backBufferSize =  Device::Director::GetInstance()->GetBackBufferSize();
	_aspect = (float)backBufferSize.w / (float)backBufferSize.h;
}

void CameraForm::GetProjectionMatrix(Math::Matrix& outMatrix) const
{
	if(_projectionType == ProjectionType::Perspective)
	{
		float fovRadian = Math::Common::Deg2Rad(_fieldOfViewDegree);
		Matrix::PerspectiveFovLH(outMatrix, _aspect, fovRadian, _clippingFar, _clippingNear);
	}
	else if(_projectionType == ProjectionType::Orthographic)
	{
		const Size<unsigned int>& backBufferSize = Device::Director::GetInstance()->GetBackBufferSize();
		Matrix::OrthoLH(outMatrix, (float)(backBufferSize.w), (float)(backBufferSize.h), _clippingNear, _clippingFar);
	}
}

void CameraForm::GetViewMatrix(Math::Matrix &outMatrix, const Math::Matrix &worldMatrix)
{
	outMatrix = worldMatrix;

	Vector3 worldPos;
	worldPos.x = worldMatrix._41;
	worldPos.y = worldMatrix._42;
	worldPos.z = worldMatrix._43;

	Math::Vector3 right		= Math::Vector3(worldMatrix._11, worldMatrix._21, worldMatrix._31);
	Math::Vector3 up		= Math::Vector3(worldMatrix._12, worldMatrix._22, worldMatrix._32);
	Math::Vector3 forward	= Math::Vector3(worldMatrix._13, worldMatrix._23, worldMatrix._33);

	Vector3 p;
	p.x = -Vector3::Dot(right,		worldPos);
	p.y = -Vector3::Dot(up,			worldPos);
	p.z = -Vector3::Dot(forward,	worldPos);

	outMatrix._41 = p.x;
	outMatrix._42 = p.y;
	outMatrix._43 = p.z;
	outMatrix._44 = 1.0f;
}

void CameraForm::GetViewMatrix(Math::Matrix& outMatrix) const
{
	Matrix worldMat;
	_owner->GetTransform()->FetchWorldMatrix(worldMat);

	GetViewMatrix(outMatrix, worldMat);
}

void CameraForm::UpdateTransformCB(const std::vector<Core::Object*>& objects)
{
	TransformPipelineParam tfParam;
	GetProjectionMatrix(tfParam.projMat);
	GetViewMatrix(tfParam.viewMat);

	_viewProjMatrixInPrevRenderState = tfParam.viewMat * tfParam.projMat;
	_frustum->Make(_viewProjMatrixInPrevRenderState);

	ConstBufferParam camCB;
	{
		Matrix worldMat;
		_owner->GetTransform()->FetchWorldMatrix(worldMat);

		camCB.worldPos		= Vector4(worldMat._41, worldMat._42, worldMat._43, 1.0f);
		camCB.clippingNear	= _clippingNear;
		camCB.clippingFar	= _clippingFar;
		camCB.screenSize	= Device::Director::GetInstance()->GetBackBufferSize().Cast<float>();
	}

	if( memcmp(&_prevConstBufferData, &camCB, sizeof(ConstBufferParam)) != 0 )
	{
		ID3D11DeviceContext* context = Device::Director::GetInstance()->GetDirectX()->GetContext();
		_camConstBuffer->UpdateSubResource(context, &camCB);

		_prevConstBufferData = camCB;
	}

	for(auto iter = objects.begin(); iter != objects.end(); ++iter)
	{
		(*iter)->Culling(_frustum);
		(*iter)->UpdateTransformCB(tfParam);
	}
}

void CameraForm::SortTransparentMeshRenderQueue(const RenderManager* renderMgr)
{
	const RenderManager::MeshList transparentList = renderMgr->GetTransparentMeshes();
	if( transparentList.updateCounter > _transparentMeshQueue.updateCounter )
	{
		const auto& renderMgrMeshes = transparentList.meshes.GetVector();
		auto& thisCamMeshes = _transparentMeshQueue.meshes;

		thisCamMeshes.clear();
		thisCamMeshes.insert( thisCamMeshes.end(), renderMgrMeshes.begin(), renderMgrMeshes.end());

		_transparentMeshQueue.updateCounter = transparentList.updateCounter;
	}

	const Transform* transform = _owner->GetTransform();

	Math::Vector3 camPos;
	transform->FetchWorldPosition(camPos);

	auto SortingByDistance = [&](const Mesh::Mesh*& left, const Mesh::Mesh*& right) -> bool
	{
		float leftDistance = D3D11_FLOAT32_MAX;
		{
			Math::Vector3 leftPos;
			left->GetOwner()->GetTransform()->FetchWorldPosition(leftPos);
			leftDistance = Math::Vector3::Distance(leftPos, camPos);
		}

		float rightDistance = D3D11_FLOAT32_MAX;
		{
			Math::Vector3 rightPos;
			right->GetOwner()->GetTransform()->FetchWorldPosition(rightPos);
			rightDistance = Math::Vector3::Distance(rightPos, camPos);
		}

		return leftDistance < rightDistance;
	};

	std::sort(_transparentMeshQueue.meshes.begin(), _transparentMeshQueue.meshes.end(), SortingByDistance);
}

void CameraForm::_Clone(CameraForm* newCam) const
{
	(*newCam) = (*this);
	newCam->_frustum		= new Frustum(0.0f);
	newCam->_renderTarget	= new Texture::RenderTexture;
	{
		const Size<unsigned int>& size = Director::GetInstance()->GetBackBufferSize();
		newCam->_renderTarget->Initialize(size, DXGI_FORMAT_R8G8B8A8_UNORM);
	}

	newCam->_camConstBuffer	= new Buffer::ConstBuffer;
	if(_camConstBuffer->Initialize(sizeof(ConstBufferParam)) == false)
		ASSERT_MSG("Error, cant create const buffer in _Clone");
}<commit_msg>CameraForm - RenderTexture의 포맷을 r16g16b16a16으로 변경함(원래는 r8g8b8a8) #64<commit_after>#include "CameraForm.h"
#include "Object.h"
#include "Director.h"
#include "TransformPipelineParam.h"

using namespace Math;
using namespace std;
using namespace Rendering::Light;
using namespace Device;
using namespace Core;
using namespace Rendering::Camera;
using namespace Rendering::Manager;

CameraForm::CameraForm()
	: Component(), _frustum(nullptr), _renderTarget(nullptr)
{
}

CameraForm::~CameraForm(void)
{

}

void CameraForm::OnInitialize()
{
	_fieldOfViewDegree	= 60.0f;
	_clippingNear		= 0.1f;
	_clippingFar		= 1000.0f;

	const Size<unsigned int>& backBufferSize = Director::GetInstance()->GetBackBufferSize();
	_aspect = (float)backBufferSize.w / (float)backBufferSize.h;

	_projectionType    = ProjectionType::Perspective;
	_clearColor = Color(0.5f, 0.5f, 1.0f, 1.0f);

	_frustum = new Frustum(0.0f);

	_renderTarget = new Texture::RenderTexture;
	_renderTarget->Initialize(backBufferSize, DXGI_FORMAT_R16G16B16A16_FLOAT);

	_camConstBuffer = new Buffer::ConstBuffer;
	if(_camConstBuffer->Initialize(sizeof(ConstBufferParam)) == false)
		ASSERT_MSG("Error, cam->constbuffer->Initialize");

	//_clearFlag = ClearFlag::FlagSolidColor;
}

void CameraForm::OnDestroy()
{
	SAFE_DELETE(_frustum);
	SAFE_DELETE(_renderTarget);
}

void CameraForm::CalcAspect()
{
	const Size<unsigned int>& backBufferSize =  Device::Director::GetInstance()->GetBackBufferSize();
	_aspect = (float)backBufferSize.w / (float)backBufferSize.h;
}

void CameraForm::GetProjectionMatrix(Math::Matrix& outMatrix) const
{
	if(_projectionType == ProjectionType::Perspective)
	{
		float fovRadian = Math::Common::Deg2Rad(_fieldOfViewDegree);
		Matrix::PerspectiveFovLH(outMatrix, _aspect, fovRadian, _clippingFar, _clippingNear);
	}
	else if(_projectionType == ProjectionType::Orthographic)
	{
		const Size<unsigned int>& backBufferSize = Device::Director::GetInstance()->GetBackBufferSize();
		Matrix::OrthoLH(outMatrix, (float)(backBufferSize.w), (float)(backBufferSize.h), _clippingNear, _clippingFar);
	}
}

void CameraForm::GetViewMatrix(Math::Matrix &outMatrix, const Math::Matrix &worldMatrix)
{
	outMatrix = worldMatrix;

	Vector3 worldPos;
	worldPos.x = worldMatrix._41;
	worldPos.y = worldMatrix._42;
	worldPos.z = worldMatrix._43;

	Math::Vector3 right		= Math::Vector3(worldMatrix._11, worldMatrix._21, worldMatrix._31);
	Math::Vector3 up		= Math::Vector3(worldMatrix._12, worldMatrix._22, worldMatrix._32);
	Math::Vector3 forward	= Math::Vector3(worldMatrix._13, worldMatrix._23, worldMatrix._33);

	Vector3 p;
	p.x = -Vector3::Dot(right,		worldPos);
	p.y = -Vector3::Dot(up,			worldPos);
	p.z = -Vector3::Dot(forward,	worldPos);

	outMatrix._41 = p.x;
	outMatrix._42 = p.y;
	outMatrix._43 = p.z;
	outMatrix._44 = 1.0f;
}

void CameraForm::GetViewMatrix(Math::Matrix& outMatrix) const
{
	Matrix worldMat;
	_owner->GetTransform()->FetchWorldMatrix(worldMat);

	GetViewMatrix(outMatrix, worldMat);
}

void CameraForm::UpdateTransformCB(const std::vector<Core::Object*>& objects)
{
	TransformPipelineParam tfParam;
	GetProjectionMatrix(tfParam.projMat);
	GetViewMatrix(tfParam.viewMat);

	_viewProjMatrixInPrevRenderState = tfParam.viewMat * tfParam.projMat;
	_frustum->Make(_viewProjMatrixInPrevRenderState);

	ConstBufferParam camCB;
	{
		Matrix worldMat;
		_owner->GetTransform()->FetchWorldMatrix(worldMat);

		camCB.worldPos		= Vector4(worldMat._41, worldMat._42, worldMat._43, 1.0f);
		camCB.clippingNear	= _clippingNear;
		camCB.clippingFar	= _clippingFar;
		camCB.screenSize	= Device::Director::GetInstance()->GetBackBufferSize().Cast<float>();
	}

	if( memcmp(&_prevConstBufferData, &camCB, sizeof(ConstBufferParam)) != 0 )
	{
		ID3D11DeviceContext* context = Device::Director::GetInstance()->GetDirectX()->GetContext();
		_camConstBuffer->UpdateSubResource(context, &camCB);

		_prevConstBufferData = camCB;
	}

	for(auto iter = objects.begin(); iter != objects.end(); ++iter)
	{
		(*iter)->Culling(_frustum);
		(*iter)->UpdateTransformCB(tfParam);
	}
}

void CameraForm::SortTransparentMeshRenderQueue(const RenderManager* renderMgr)
{
	const RenderManager::MeshList transparentList = renderMgr->GetTransparentMeshes();
	if( transparentList.updateCounter > _transparentMeshQueue.updateCounter )
	{
		const auto& renderMgrMeshes = transparentList.meshes.GetVector();
		auto& thisCamMeshes = _transparentMeshQueue.meshes;

		thisCamMeshes.clear();
		thisCamMeshes.insert( thisCamMeshes.end(), renderMgrMeshes.begin(), renderMgrMeshes.end());

		_transparentMeshQueue.updateCounter = transparentList.updateCounter;
	}

	const Transform* transform = _owner->GetTransform();

	Math::Vector3 camPos;
	transform->FetchWorldPosition(camPos);

	auto SortingByDistance = [&](const Mesh::Mesh*& left, const Mesh::Mesh*& right) -> bool
	{
		float leftDistance = D3D11_FLOAT32_MAX;
		{
			Math::Vector3 leftPos;
			left->GetOwner()->GetTransform()->FetchWorldPosition(leftPos);
			leftDistance = Math::Vector3::Distance(leftPos, camPos);
		}

		float rightDistance = D3D11_FLOAT32_MAX;
		{
			Math::Vector3 rightPos;
			right->GetOwner()->GetTransform()->FetchWorldPosition(rightPos);
			rightDistance = Math::Vector3::Distance(rightPos, camPos);
		}

		return leftDistance < rightDistance;
	};

	std::sort(_transparentMeshQueue.meshes.begin(), _transparentMeshQueue.meshes.end(), SortingByDistance);
}

void CameraForm::_Clone(CameraForm* newCam) const
{
	(*newCam) = (*this);
	newCam->_frustum		= new Frustum(0.0f);
	newCam->_renderTarget	= new Texture::RenderTexture;
	{
		const Size<unsigned int>& size = Director::GetInstance()->GetBackBufferSize();
		newCam->_renderTarget->Initialize(size, DXGI_FORMAT_R8G8B8A8_UNORM);
	}

	newCam->_camConstBuffer	= new Buffer::ConstBuffer;
	if(_camConstBuffer->Initialize(sizeof(ConstBufferParam)) == false)
		ASSERT_MSG("Error, cant create const buffer in _Clone");
}<|endoftext|>


<commit_before>/**************************************************************************************/
/*                                                                                */
/*  Visualization Library                                                             */
/*  http://www.visualizationlibrary.com                                               */
/*                                                                                */
/*  Copyright (c) 2005-2010, Michele Bosi                                             */
/*  All rights reserved.                                                              */
/*                                                                                */
/*  Redistribution and use in source and binary forms, with or without modification,  */
/*  are permitted provided that the following conditions are met:                     */
/*                                                                                */
/*  - Redistributions of source code must retain the above copyright notice, this     */
/*  list of conditions and the following disclaimer.                                  */
/*                                                                                */
/*  - Redistributions in binary form must reproduce the above copyright notice, this  */
/*  list of conditions and the following disclaimer in the documentation and/or       */
/*  other materials provided with the distribution.                                   */
/*                                                                                */
/*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND   */
/*  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED     */
/*  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE            */
/*  DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR  */
/*  ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES    */
/*  (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;      */
/*  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON    */
/*  ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT           */
/*  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS     */
/*  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.                      */
/*                                                                                */
/**************************************************************************************/

#ifndef Applet_INCLUDE_ONCE
#define Applet_INCLUDE_ONCE

#include <vlGraphics/UIEventListener.hpp>
#include <vlGraphics/TrackballManipulator.hpp>
#include <vlGraphics/GhostCameraManipulator.hpp>
#include <vlGraphics/SceneManagerActorTree.hpp>
#include <vlGraphics/Rendering.hpp>
#include <vlGraphics/ReadPixels.hpp>

namespace vl
{
//-----------------------------------------------------------------------------
// Applet
//-----------------------------------------------------------------------------
  /** The Applet class is an utilitly UIEventListener that features a ghost manipulator,
      trackball manipulator, an FPS counter and a simple rendering pipeline.

      Default key bindings:
      - Key_Escape: calls openglContext()->quitApplication()
      - Key_T: enables the TrackballManipulator.
      - Key_F: enables the GhostCameraManipulator (fly mode).
      - Key_F1: toggles fullscreen mode if supported.
      - Key_F5: saves a screenshot of the current OpenGL window.
      - Key_C: toggles the continuous update fo the OpenGL window (see also OpenGLContext::setContinuousUpdate()).
      - Key_U: updates the OpenGL window content by calling openglContext()->update(). */
  class Applet: public UIEventListener
  {
  public:
    virtual const char* className() { return "Applet"; }

    /** Constructor */
    Applet();

    /** Initializes the default rendering (with Rendering), the default scene manager (with SceneManagerActorTree) and camera manipulators (GhostCameraManipulator and TrackballManipulator). */
    void initialize();

    // --- UIEventListener ---

    virtual void addedListenerEvent(OpenGLContext* openglContext);

    virtual void removedListenerEvent(OpenGLContext*);

    virtual void keyReleaseEvent(unsigned short, EKey key);

    virtual void destroyEvent();

    virtual void updateEvent();

    virtual void resizeEvent(int, int);

    virtual void initEvent() {}

    virtual void enableEvent(bool) {}

    virtual void mouseMoveEvent(int, int) {}

    virtual void mouseUpEvent(EMouseButton, int, int) {}

    virtual void mouseDownEvent(EMouseButton, int, int) {}

    virtual void mouseWheelEvent(int) {}

    virtual void keyPressEvent(unsigned short, EKey) {}

    virtual void fileDroppedEvent(const std::vector<String>&) {}

    virtual void visibilityEvent(bool) {}

    // --- --- ---

    /** The rendering used by the Applet, by default a Rendering. */
    RenderingAbstract* rendering() { return mRendering.get(); }

    /** The rendering used by the Applet, by default a Rendering. */
    const RenderingAbstract* rendering() const { return mRendering.get(); }

    /** Sets the rendering used by the Applet, by default a Rendering. */
    void setRendering(RenderingAbstract* rendering) { mRendering = rendering; }

    /** The scene manager used by the default rendering. */
    SceneManagerActorTree* sceneManager() { return mSceneManagerActorTree.get(); }

    /** The scene manager used by the default rendering. */
    const SceneManagerActorTree* sceneManager() const { return mSceneManagerActorTree.get(); }

    /** GhostCameraManipulator used by the applet, activated by the "F" key. */
    GhostCameraManipulator* ghostCamera() { return mFly.get(); }

    /** TrackballManipulator used by the applet, activated by the "T" key. */
    TrackballManipulator* trackball() { return mTrackball.get(); }

    /** Current average frames per second (updated every 500ms). */
    double fps() const { return mFPS; }

    /** Override this to update the content of your scene.
        Called by updateEvent() right before rendering()->render() and swapping opengl front/back buffers.
        \note Since updateScene() is called by updateEvent() this function is called only if somebody
        requests a OpenGLContext::update() or if OpenGLContext::continuousUpdate() is set to \p true. */
	  virtual void updateScene() {}

    /** Sets the applet name, used for the window title and for naming screenshots. */
    void setAppletName(const String& app_name) { mAppletName = app_name; }

    /** The applet name, used for the window title and for naming screenshots. */
    const String& appletName() const { return mAppletName; }

  protected:
    void bindManipulators(Camera* camera);

  private:
    ref<RenderingAbstract> mRendering;
    ref<GhostCameraManipulator> mFly;
    ref<TrackballManipulator> mTrackball;
    ref<SceneManagerActorTree> mSceneManagerActorTree;
    ref<ReadPixels> mReadPixels;
    String mAppletName;
    double mStartTime;
    double mFPS;
    int mFrameCount;
  };
}

#endif
<commit_msg>updated comments.<commit_after>/**************************************************************************************/
/*                                                                                */
/*  Visualization Library                                                             */
/*  http://www.visualizationlibrary.com                                               */
/*                                                                                */
/*  Copyright (c) 2005-2010, Michele Bosi                                             */
/*  All rights reserved.                                                              */
/*                                                                                */
/*  Redistribution and use in source and binary forms, with or without modification,  */
/*  are permitted provided that the following conditions are met:                     */
/*                                                                                */
/*  - Redistributions of source code must retain the above copyright notice, this     */
/*  list of conditions and the following disclaimer.                                  */
/*                                                                                */
/*  - Redistributions in binary form must reproduce the above copyright notice, this  */
/*  list of conditions and the following disclaimer in the documentation and/or       */
/*  other materials provided with the distribution.                                   */
/*                                                                                */
/*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND   */
/*  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED     */
/*  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE            */
/*  DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR  */
/*  ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES    */
/*  (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;      */
/*  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON    */
/*  ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT           */
/*  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS     */
/*  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.                      */
/*                                                                                */
/**************************************************************************************/

#ifndef Applet_INCLUDE_ONCE
#define Applet_INCLUDE_ONCE

#include <vlGraphics/UIEventListener.hpp>
#include <vlGraphics/TrackballManipulator.hpp>
#include <vlGraphics/GhostCameraManipulator.hpp>
#include <vlGraphics/SceneManagerActorTree.hpp>
#include <vlGraphics/Rendering.hpp>
#include <vlGraphics/ReadPixels.hpp>

namespace vl
{
//-----------------------------------------------------------------------------
// Applet
//-----------------------------------------------------------------------------
  /**
   * The Applet class is an utilitly UIEventListener that features a ghost manipulator,
   * trackball manipulator, an FPS counter and a simple rendering pipeline.
   *
   * Default key bindings:
   * - Key_Escape: calls openglContext()->quitApplication()
   * - Key_T: enables the TrackballManipulator.
   * - Key_F: enables the GhostCameraManipulator (fly mode).
   * - Key_F1: toggles fullscreen mode if supported.
   * - Key_F5: saves a screenshot of the current OpenGL window.
   * - Key_C: toggles the continuous update fo the OpenGL window (see also OpenGLContext::setContinuousUpdate()).
   * - Key_U: updates the OpenGL window content by calling openglContext()->update().
   */
  class Applet: public UIEventListener
  {
  public:
    virtual const char* className() { return "Applet"; }

    /** Constructor */
    Applet();

    /**
     * Initializes the default rendering (with Rendering), the default scene manager (with SceneManagerActorTree)
     * and camera manipulators (GhostCameraManipulator and TrackballManipulator).
     */
    void initialize();

    // --- UIEventListener ---

    virtual void addedListenerEvent(OpenGLContext* openglContext);

    virtual void removedListenerEvent(OpenGLContext*);

    virtual void keyReleaseEvent(unsigned short, EKey key);

    virtual void destroyEvent();

    virtual void updateEvent();

    virtual void resizeEvent(int, int);

    virtual void initEvent() {}

    virtual void enableEvent(bool) {}

    virtual void mouseMoveEvent(int, int) {}

    virtual void mouseUpEvent(EMouseButton, int, int) {}

    virtual void mouseDownEvent(EMouseButton, int, int) {}

    virtual void mouseWheelEvent(int) {}

    virtual void keyPressEvent(unsigned short, EKey) {}

    virtual void fileDroppedEvent(const std::vector<String>&) {}

    virtual void visibilityEvent(bool) {}

    // --- --- ---

    /** The rendering used by the Applet, by default a Rendering. */
    RenderingAbstract* rendering() { return mRendering.get(); }

    /** The rendering used by the Applet, by default a Rendering. */
    const RenderingAbstract* rendering() const { return mRendering.get(); }

    /** Sets the rendering used by the Applet, by default a Rendering. */
    void setRendering(RenderingAbstract* rendering) { mRendering = rendering; }

    /** The scene manager used by the default rendering. */
    SceneManagerActorTree* sceneManager() { return mSceneManagerActorTree.get(); }

    /** The scene manager used by the default rendering. */
    const SceneManagerActorTree* sceneManager() const { return mSceneManagerActorTree.get(); }

    /** GhostCameraManipulator used by the applet, activated by the "F" key. */
    GhostCameraManipulator* ghostCamera() { return mFly.get(); }

    /** TrackballManipulator used by the applet, activated by the "T" key. */
    TrackballManipulator* trackball() { return mTrackball.get(); }

    /** Current average frames per second (updated every 500ms). */
    double fps() const { return mFPS; }

    /**
     * Override this to update the content of your scene.
     * Called by updateEvent() right before rendering()->render() and swapping opengl front/back buffers.
     * \note Since updateScene() is called by updateEvent() this function is called only if somebody
     * requests a OpenGLContext::update() or if OpenGLContext::continuousUpdate() is set to \p true.
     */
	  virtual void updateScene() {}

    /** Sets the applet name, used for the window title and for naming screenshots. */
    void setAppletName(const String& app_name) { mAppletName = app_name; }

    /** The applet name, used for the window title and for naming screenshots. */
    const String& appletName() const { return mAppletName; }

  protected:
    void bindManipulators(Camera* camera);

  private:
    ref<RenderingAbstract> mRendering;
    ref<GhostCameraManipulator> mFly;
    ref<TrackballManipulator> mTrackball;
    ref<SceneManagerActorTree> mSceneManagerActorTree;
    ref<ReadPixels> mReadPixels;
    String mAppletName;
    double mStartTime;
    double mFPS;
    int mFrameCount;
  };
}

#endif
<|endoftext|>


<commit_before>#pragma once

#include "..\Quantities\Dimensionless.hpp"
#include "..\Quantities\Quantities.hpp"
#include "R3Element.hpp"

namespace Principia {
namespace Geometry {
template<typename Scalar, typename Frame, unsigned int Rank>
struct Multivector;

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 1> {
  Multivector(R3Element<Scalar> coordinates) : coordinates(coordinates) {};
  R3Element<Scalar> coordinates;
};

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 2> {
  Multivector(R3Element<Scalar> coordinates) : coordinates(coordinates) {};
  R3Element<Scalar> Coordinates;
};

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 3> {
  Multivector(Scalar coordinates) : coordinates(coordinates) {};
  Scalar Coordinates;
};

template<typename Scalar, typename Frame>
using Vector = Multivector<Scalar, Frame, 1>;

template<typename Scalar, typename Frame>
using Bivector = Multivector<Scalar, Frame, 2>;

template<typename Scalar, typename Frame>
using Trivector = Multivector<Scalar, Frame, 3>;

template<typename Scalar, typename Frame>
Scalar InnerProduct(Vector<Scalar, Frame> const& left,
                    Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Scalar InnerProduct(Bivector<Scalar, Frame> const& left,
                    Bivector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Scalar InnerProduct(Trivector<Scalar, Frame> const& left,
                    Trivector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Bivector<Scalar, Frame> Wedge(Vector<Scalar, Frame> const& Left,
                              Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Trivector<Scalar, Frame> Wedge(Bivector<Scalar, Frame> const& Left,
                               Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Trivector<Scalar, Frame> Wedge(Vector<Scalar, Frame> const& Left,
                               Bivector<Scalar, Frame> const& right);

template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator+ (Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator- (Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>

Multivector<T, Frame,
            Rank> operator+ (Multivector<T, Frame, Rank> const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator- (Multivector<T, Frame, Rank> const& left,
                             Multivector<T, Frame, Rank> const& right);

template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator* (Quantities::Dimensionless const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator* (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator/ (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);

template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Product<U, T> , Frame,
            Rank> operator* (U const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Product<T, U>, Frame,
            Rank> operator* (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);
template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Quotient<T, U>, Frame,
            Rank> operator/ (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);

}
}

#include "Grassmann-body.hpp"
<commit_msg>Styleguide compliance.<commit_after>#pragma once

#include "..\Quantities\Dimensionless.hpp"
#include "..\Quantities\Quantities.hpp"
#include "R3Element.hpp"

namespace Principia {
namespace Geometry {
template<typename Scalar, typename Frame, unsigned int Rank>
struct Multivector;

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 1> {
  Multivector(R3Element<Scalar> coordinates) : coordinates(coordinates) {};
  R3Element<Scalar> coordinates;
};

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 2> {
  Multivector(R3Element<Scalar> coordinates) : coordinates(coordinates) {};
  R3Element<Scalar> coordinates;
};

template<typename Scalar, typename Frame>
struct Multivector<Scalar, Frame, 3> {
  Multivector(Scalar coordinates) : coordinates(coordinates) {};
  Scalar coordinates;
};

template<typename Scalar, typename Frame>
using Vector = Multivector<Scalar, Frame, 1>;

template<typename Scalar, typename Frame>
using Bivector = Multivector<Scalar, Frame, 2>;

template<typename Scalar, typename Frame>
using Trivector = Multivector<Scalar, Frame, 3>;

template<typename Scalar, typename Frame>
Scalar InnerProduct(Vector<Scalar, Frame> const& left,
                    Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Scalar InnerProduct(Bivector<Scalar, Frame> const& left,
                    Bivector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Scalar InnerProduct(Trivector<Scalar, Frame> const& left,
                    Trivector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Bivector<Scalar, Frame> Wedge(Vector<Scalar, Frame> const& Left,
                              Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Trivector<Scalar, Frame> Wedge(Bivector<Scalar, Frame> const& Left,
                               Vector<Scalar, Frame> const& right);

template<typename Scalar, typename Frame>
Trivector<Scalar, Frame> Wedge(Vector<Scalar, Frame> const& Left,
                               Bivector<Scalar, Frame> const& right);

template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator+ (Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator- (Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>

Multivector<T, Frame,
            Rank> operator+ (Multivector<T, Frame, Rank> const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator- (Multivector<T, Frame, Rank> const& left,
                             Multivector<T, Frame, Rank> const& right);

template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator* (Quantities::Dimensionless const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator* (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);
template<typename T, typename Frame, unsigned int Rank>
Multivector<T, Frame,
            Rank> operator/ (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);

template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Product<U, T> , Frame,
            Rank> operator* (U const& left,
                             Multivector<T, Frame, Rank> const& right);
template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Product<T, U>, Frame,
            Rank> operator* (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);
template<typename T, typename U, typename Frame, unsigned int Rank>
Multivector<Quantities::Quotient<T, U>, Frame,
            Rank> operator/ (Multivector<T, Frame, Rank> const& left,
                             Quantities::Dimensionless const& right);

}
}

#include "Grassmann-body.hpp"
<|endoftext|>


<commit_before>// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "net/socket/client_socket.h"

#include "base/histogram.h"

namespace net {

ClientSocket::ClientSocket()
    : omnibox_speculation_(false),
      subresource_speculation_(false),
      was_used_to_transmit_data_(false) {}

ClientSocket::~ClientSocket() {
  EmitPreconnectionHistograms();
}

void ClientSocket::EmitPreconnectionHistograms() const {
  DCHECK(!subresource_speculation_ || !omnibox_speculation_);
  // 0 ==> non-speculative, never connected.
  // 1 ==> non-speculative never used (but connected).
  // 2 ==> non-spculative and used.
  // 3 ==> omnibox_speculative never connected.
  // 4 ==> omnibox_speculative never used (but connected).
  // 5 ==> omnibox_speculative and used.
  // 6 ==> subresource_speculative never connected.
  // 7 ==> subresource_speculative never used (but connected).
  // 8 ==> subresource_speculative and used.
  int result;
  if (was_used_to_transmit_data_)
    result = 2;
  else if (was_ever_connected_)
    result = 1;
  else
    result = 0;  // Never used, and not really connected.

  if (omnibox_speculation_)
    result += 3;
  else if (subresource_speculation_)
    result += 6;
  UMA_HISTOGRAM_ENUMERATION("Net.PreconnectUtilization", result, 9);
}

void ClientSocket::SetSubresourceSpeculation() {
  if (was_used_to_transmit_data_)
    return;
  subresource_speculation_ = true;
}

void ClientSocket::SetOmniboxSpeculation() {
  if (was_used_to_transmit_data_)
    return;
  omnibox_speculation_ = true;
}

void ClientSocket::UpdateConnectivityState(bool is_reused) {
  // Record if this connection has every actually connected successfully.
  // Note that IsConnected() won't be defined at destruction time, so we need
  // to record this data now, while the derived class is present.
  was_ever_connected_ |= IsConnected();
  // A socket is_reused only after it has transmitted some data.
  was_used_to_transmit_data_ |= is_reused;
}

}  // namespace net

<commit_msg>Initialize was_ever_connected_ in ClientSocket.<commit_after>// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "net/socket/client_socket.h"

#include "base/histogram.h"

namespace net {

ClientSocket::ClientSocket()
    : was_ever_connected_(false),
      omnibox_speculation_(false),
      subresource_speculation_(false),
      was_used_to_transmit_data_(false) {}

ClientSocket::~ClientSocket() {
  EmitPreconnectionHistograms();
}

void ClientSocket::EmitPreconnectionHistograms() const {
  DCHECK(!subresource_speculation_ || !omnibox_speculation_);
  // 0 ==> non-speculative, never connected.
  // 1 ==> non-speculative never used (but connected).
  // 2 ==> non-spculative and used.
  // 3 ==> omnibox_speculative never connected.
  // 4 ==> omnibox_speculative never used (but connected).
  // 5 ==> omnibox_speculative and used.
  // 6 ==> subresource_speculative never connected.
  // 7 ==> subresource_speculative never used (but connected).
  // 8 ==> subresource_speculative and used.
  int result;
  if (was_used_to_transmit_data_)
    result = 2;
  else if (was_ever_connected_)
    result = 1;
  else
    result = 0;  // Never used, and not really connected.

  if (omnibox_speculation_)
    result += 3;
  else if (subresource_speculation_)
    result += 6;
  UMA_HISTOGRAM_ENUMERATION("Net.PreconnectUtilization", result, 9);
}

void ClientSocket::SetSubresourceSpeculation() {
  if (was_used_to_transmit_data_)
    return;
  subresource_speculation_ = true;
}

void ClientSocket::SetOmniboxSpeculation() {
  if (was_used_to_transmit_data_)
    return;
  omnibox_speculation_ = true;
}

void ClientSocket::UpdateConnectivityState(bool is_reused) {
  // Record if this connection has every actually connected successfully.
  // Note that IsConnected() won't be defined at destruction time, so we need
  // to record this data now, while the derived class is present.
  was_ever_connected_ |= IsConnected();
  // A socket is_reused only after it has transmitted some data.
  was_used_to_transmit_data_ |= is_reused;
}

}  // namespace net

<|endoftext|>


<commit_before>// VisualBlock.cpp

#include "VisualBlock.h"
#include "VisualPainter.h"
#include "Assert.h"
#include <algorithm>

#undef min
#undef max

VisualBlock::VisualBlock( size_t length )
	: m_length( length )
{
	m_lines.push_back( VisualLine() );
}

VisualBlock::VisualBlock( size_t length, LayoutAllocator& allocator, ArrayOf<SCRIPT_ITEM> items )
	: m_length( length )
{
	m_layout.Copy( allocator, items );

	ArrayOf<size_t> lines = allocator.lines.Allocated();
	m_lines.reserve( lines.size() );

	TextRun* runs      = m_layout.runs;
	size_t   lastEnd   = 0;
	size_t   textStart = 0;

	for ( size_t* it = lines.begin(); it != lines.end(); ++it )
	{
		TextRun* runStart = runs + lastEnd;
		TextRun* runEnd   = runs + *it;

		m_lines.push_back( VisualLine( textStart, runStart, runEnd ) );

		textStart = m_lines.back().TextEnd();
		lastEnd = *it;
	}
}

void VisualBlock::Draw( VisualPainter& painter, RECT rect ) const
{
	size_t i = rect.top / painter.style.lineHeight;
	rect.top = i * painter.style.lineHeight;

	if ( 0 < i && i < m_lines.size() )
		painter.prevSelection.Swap( m_lines[i-1].MakeVisualSelection( painter.selection, m_layout ) );

	for ( ; i < m_lines.size() && !IsRectEmpty( &rect ); ++i )
	{
		DrawSelection( m_lines[i], painter, rect );
		m_lines[i].Draw( painter, rect, m_layout );

		rect.top += painter.style.lineHeight;
	}
}

void VisualBlock::DrawSelection( const VisualLine& line, VisualPainter& painter, RECT rect ) const
{
	VisualSelection selection;

	if ( painter.selection.Intersects( line.TextStart(), line.TextEnd() ) )
		selection = line.MakeVisualSelection( painter.selection, m_layout );

	if ( &line == &m_lines.back() && painter.selection.Intersects( line.TextEnd(), m_length ) )
		selection.Add( line.Width(), line.Width() + painter.style.avgCharWidth );

	selection.Draw( painter, rect );
	selection.Swap( painter.prevSelection );
}

POINT VisualBlock::PointFromChar( size_t pos, bool advancing, TextStyle& style ) const
{
	POINT result;
	bool trailingEdge = advancing;

	if ( pos == 0 )
		trailingEdge = false;
	else if ( pos >= m_lines.back().TextEnd() )
		trailingEdge = true;

	if ( trailingEdge )
		--pos;

	size_t line = LineContaining( pos );

 	if ( line < m_lines.size() )
	{
		result.x = m_lines[line].CPtoX( pos, trailingEdge, m_layout );
		result.y = line * style.lineHeight;
	}
	else
	{
		result.x = 0;
		result.y = 0;
	}

	return result;
}

size_t VisualBlock::CharFromPoint( POINT* point, TextStyle& style ) const
{
	int line = point->y / style.lineHeight;

	if ( line < 0 || size_t( line ) >= m_lines.size() )
		line = m_lines.size() - 1;

	point->y = line * style.lineHeight;
	return m_lines[line].XtoCP( &point->x, m_layout );
}

size_t VisualBlock::LineStart( LONG y, TextStyle& style ) const
{
	int line = y / style.lineHeight;
	Assert( line >= 0 && size_t( line ) < m_lines.size() );
	return m_lines[line].TextStart();
}

size_t VisualBlock::LineEnd( LONG y, TextStyle& style ) const
{
	int line = y / style.lineHeight;
	Assert( line >= 0 && size_t( line ) < m_lines.size() );
	return m_lines[line].TextEnd();
}

size_t VisualBlock::LineCount() const
{
	return m_lines.size();
}

struct CompareLines
{
	bool operator()( const VisualLine& line, size_t pos ) const
	{
		return line.TextEnd() <= pos;
	}

	bool operator()( size_t pos, const VisualLine& line ) const
	{
		return pos < line.TextStart();
	}

	bool operator()( const VisualLine& a, const VisualLine& b ) const
	{
		return a.TextStart() < b.TextStart();
	}
};

size_t VisualBlock::LineContaining( size_t pos ) const
{
	return std::lower_bound( m_lines.begin(), m_lines.end(), pos, CompareLines() ) - m_lines.begin();
}

size_t VisualBlock::Length() const
{
	return m_length;
}

LONG VisualBlock::Height( TextStyle& style ) const
{
	return m_lines.size() * style.lineHeight;
}

bool VisualBlock::EndsWithNewline() const
{
	return m_lines.back().TextEnd() < m_length;
}
<commit_msg>Only draw the newline selection if the block ends with a newline.<commit_after>// VisualBlock.cpp

#include "VisualBlock.h"
#include "VisualPainter.h"
#include "Assert.h"
#include <algorithm>

#undef min
#undef max

VisualBlock::VisualBlock( size_t length )
	: m_length( length )
{
	m_lines.push_back( VisualLine() );
}

VisualBlock::VisualBlock( size_t length, LayoutAllocator& allocator, ArrayOf<SCRIPT_ITEM> items )
	: m_length( length )
{
	m_layout.Copy( allocator, items );

	ArrayOf<size_t> lines = allocator.lines.Allocated();
	m_lines.reserve( lines.size() );

	TextRun* runs      = m_layout.runs;
	size_t   lastEnd   = 0;
	size_t   textStart = 0;

	for ( size_t* it = lines.begin(); it != lines.end(); ++it )
	{
		TextRun* runStart = runs + lastEnd;
		TextRun* runEnd   = runs + *it;

		m_lines.push_back( VisualLine( textStart, runStart, runEnd ) );

		textStart = m_lines.back().TextEnd();
		lastEnd = *it;
	}
}

void VisualBlock::Draw( VisualPainter& painter, RECT rect ) const
{
	size_t i = rect.top / painter.style.lineHeight;
	rect.top = i * painter.style.lineHeight;

	if ( 0 < i && i < m_lines.size() )
		painter.prevSelection.Swap( m_lines[i-1].MakeVisualSelection( painter.selection, m_layout ) );

	for ( ; i < m_lines.size() && !IsRectEmpty( &rect ); ++i )
	{
		DrawSelection( m_lines[i], painter, rect );
		m_lines[i].Draw( painter, rect, m_layout );

		rect.top += painter.style.lineHeight;
	}
}

void VisualBlock::DrawSelection( const VisualLine& line, VisualPainter& painter, RECT rect ) const
{
	VisualSelection selection;

	if ( painter.selection.Intersects( line.TextStart(), line.TextEnd() ) )
		selection = line.MakeVisualSelection( painter.selection, m_layout );

	if ( &line == &m_lines.back() && painter.selection.Intersects( line.TextEnd(), m_length ) && EndsWithNewline() )
		selection.Add( line.Width(), line.Width() + painter.style.avgCharWidth );

	selection.Draw( painter, rect );
	selection.Swap( painter.prevSelection );
}

POINT VisualBlock::PointFromChar( size_t pos, bool advancing, TextStyle& style ) const
{
	POINT result;
	bool trailingEdge = advancing;

	if ( pos == 0 )
		trailingEdge = false;
	else if ( pos >= m_lines.back().TextEnd() )
		trailingEdge = true;

	if ( trailingEdge )
		--pos;

	size_t line = LineContaining( pos );

 	if ( line < m_lines.size() )
	{
		result.x = m_lines[line].CPtoX( pos, trailingEdge, m_layout );
		result.y = line * style.lineHeight;
	}
	else
	{
		result.x = 0;
		result.y = 0;
	}

	return result;
}

size_t VisualBlock::CharFromPoint( POINT* point, TextStyle& style ) const
{
	int line = point->y / style.lineHeight;

	if ( line < 0 || size_t( line ) >= m_lines.size() )
		line = m_lines.size() - 1;

	point->y = line * style.lineHeight;
	return m_lines[line].XtoCP( &point->x, m_layout );
}

size_t VisualBlock::LineStart( LONG y, TextStyle& style ) const
{
	int line = y / style.lineHeight;
	Assert( line >= 0 && size_t( line ) < m_lines.size() );
	return m_lines[line].TextStart();
}

size_t VisualBlock::LineEnd( LONG y, TextStyle& style ) const
{
	int line = y / style.lineHeight;
	Assert( line >= 0 && size_t( line ) < m_lines.size() );
	return m_lines[line].TextEnd();
}

size_t VisualBlock::LineCount() const
{
	return m_lines.size();
}

struct CompareLines
{
	bool operator()( const VisualLine& line, size_t pos ) const
	{
		return line.TextEnd() <= pos;
	}

	bool operator()( size_t pos, const VisualLine& line ) const
	{
		return pos < line.TextStart();
	}

	bool operator()( const VisualLine& a, const VisualLine& b ) const
	{
		return a.TextStart() < b.TextStart();
	}
};

size_t VisualBlock::LineContaining( size_t pos ) const
{
	return std::lower_bound( m_lines.begin(), m_lines.end(), pos, CompareLines() ) - m_lines.begin();
}

size_t VisualBlock::Length() const
{
	return m_length;
}

LONG VisualBlock::Height( TextStyle& style ) const
{
	return m_lines.size() * style.lineHeight;
}

bool VisualBlock::EndsWithNewline() const
{
	return m_lines.back().TextEnd() < m_length;
}
<|endoftext|>


<commit_before>#include "Judge.h"
#include <iostream>
#include <sstream>
#include <unordered_map>
#include <unordered_set>
#include <vector>

using namespace WinnerPoker;

std::vector<size_t> test(const std::vector<size_t> &t)
{
    std::stringstream ss;
    ss << "{ ";
    for (auto &&item : t)
    {
        ss << item << ", ";
    }
    ss.seekp(-2, ss.end);
    ss << " }" << std::endl;

    std::cout << ss.str();

    std::vector<size_t> vector;
    auto                zip = Judge::getInstance().zip(t);
    for (auto &&x : zip)
    {
        for (int i = 1; i <= x.second; ++i)
        {
            vector.push_back((x.first << 8) | i);
        }
    }

    ss.str("");
    ss << "{ ";
    for (auto &&item : vector)
    {
        ss << item << ", ";
    }
    ss.seekp(-2, ss.end);
    ss << " }" << std::endl;

    // std::cout << ss.str();
    std::cout << std::endl;
    return vector;
}

int main()
{
    // std::vector<size_t> hands = { 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 6, 6, 6, 6, 7, 7, 7, 7 };
    // std::vector<size_t> hands = { 3, 3, 4, 6, 6, 7, 8, 10, 10, 11, 12, 13, 13, 14, 15 };
    // std::vector<size_t> hands = { 3, 3, 4, 4, 5, 5, 7, 7 };
    // std::vector<size_t> hands = { 3, 4, 5, 5, 5, 5, 7, 7, 8, 9, 10 };

    // std::vector<size_t> hands = { 3, 3, 3, 3, 4,  4,  4,  4,  5,  5,  5,  5,  6,  6,  6,  6,  7,  7,  7,  7,
    //                              8, 8, 9, 9, 10, 10, 10, 10, 11, 11, 12, 12, 13, 13, 13, 13, 14, 14, 14, 15 };

    // std::vector<size_t> tv = {3, 3, 3, 4, 4, 4, 4, 5, 5, 6};
    // std::vector<size_t> tv = {3, 3, 3, 4, 4, 4};
    // Judge::getInstance().setCurrentHandsCategory(test(tv));

    std::vector<size_t> hands;
    hands = { 3, 3, 3, 4, 5, 5, 5, 6, 6, 7 };
    hands = { 3, 3, 3, 4, 4, 5, 5, 7 };
    hands = { 3, 3, 3, 4, 4, 4, 5, 5, 6, 6, 7 };
    hands = { 3, 3, 5, 6, 6, 7, 7, 8 };
    hands = { 3, 4, 4, 5, 5, 6, 6, 7 };
    hands = { 3, 4, 5, 5, 6, 6, 7 };
    hands = { 3, 4, 4, 5, 5, 5, 6, 6, 7 };
    hands = { 3, 4, 5, 5, 5, 6, 6 };
    hands = { 3, 3, 3, 4, 4, 5, 5, 5, 6, 6 };
    hands = { 3, 3, 4, 4, 5, 5, 5, 6 };
    hands = { 3, 3, 3, 5, 14, 14, 14 };
    hands = { 3, 3, 3, 14, 14, 14 };
    hands = { 3, 3, 4, 4, 4, 5, 5, 5, 5, 6 };
    hands = { 3, 3, 4, 4, 4, 5, 5, 5, 6, 6, 6, 6, 8 };
    hands = { 3, 3, 4, 4, 4, 4, 5, 5, 5, 6, 7 };
    hands = { 3, 3, 4, 4, 4, 5, 5, 5, 6, 6, 6, 6, 8 };
    hands = { 3, 3, 4, 4, 4, 4, 5, 5, 5, 6, 7 };
    hands = { 3, 4, 4, 5, 5, 5, 5, 6 };
    hands = { 3, 4, 4, 5, 5, 5, 5, 6, 6 };
    hands = { 4, 5, 6, 6, 7, 8, 8, 8, 9, 9, 9, 12, 12, 12, 12 };

    Judge::getInstance().setCurrentHandsCategory(std::vector<size_t>{});

    auto              ret = Judge::getInstance().cardIntentions(test(hands));
    std::stringstream ss;

    for (auto &&item : ret)
    {
        ss.str("");

        ss << "{ ";
        for (auto &&element : item)
        {
            ss << element << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        // std::cout << ss.str();
    }

    for (auto &&item : ret)
    {
        ss.str("");

        ss << "{ ";
        for (auto &&element : item)
        {
            ss << (element >> 8) << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        std::cout << ss.str();
    }

    /*
    for (int i = 0; i < 1024; ++i)
    {
        const auto &ret = Judge::getInstance().intentions(test(hands));

        std::stringstream ss;

        ss.str("");
        ss << "{ ";
        for (auto &&item : ret)
        {
            ss << (item >> 8) << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        std::cout << ss.str();
    }
 */
    return 0;
}
<commit_msg>marks<commit_after>#include "Judge.h"
#include <iostream>
#include <sstream>
#include <unordered_map>
#include <unordered_set>
#include <vector>

using namespace WinnerPoker;

std::vector<size_t> test(const std::vector<size_t> &t)
{
    std::stringstream ss;
    ss << "{ ";
    for (auto &&item : t)
    {
        ss << item << ", ";
    }
    ss.seekp(-2, ss.end);
    ss << " }" << std::endl;

    // std::cout << ss.str();

    std::vector<size_t> vector;
    auto                zip = Judge::getInstance().zip(t);
    for (auto &&x : zip)
    {
        for (int i = 1; i <= x.second; ++i)
        {
            vector.push_back((x.first << 8) | i);
        }
    }

    ss.str("");
    ss << "{ ";
    for (auto &&item : vector)
    {
        ss << item << ", ";
    }
    ss.seekp(-2, ss.end);
    ss << " }" << std::endl;

    // std::cout << ss.str();
    // std::cout << std::endl;
    return vector;
}

int main()
{
    // std::vector<size_t> hands = { 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 6, 6, 6, 6, 7, 7, 7, 7 };
    // std::vector<size_t> hands = { 3, 3, 4, 6, 6, 7, 8, 10, 10, 11, 12, 13, 13, 14, 15 };
    // std::vector<size_t> hands = { 3, 3, 4, 4, 5, 5, 7, 7 };
    // std::vector<size_t> hands = { 3, 4, 5, 5, 5, 5, 7, 7, 8, 9, 10 };

    std::vector<size_t> hands = { 3, 3, 3, 3, 4,  4,  4,  4,  5,  5,  5,  5,  6,  6,  6,  6,  7,  7,  7,  7,
                                  8, 8, 9, 9, 10, 10, 10, 10, 11, 11, 12, 12, 13, 13, 13, 13, 14, 14, 14, 15 };

    std::vector<size_t> tv = {3, 3, 3, 4, 4, 4, 4, 5};
    // std::vector<size_t> tv = { 3, 3, 3, 4, 4, 4 };
    Judge::getInstance().setCurrentHandsCategory(test(tv));

    // std::vector<size_t> hands;
    // hands = { 3, 3, 3, 4, 5, 5, 5, 6, 6, 7 };
    // hands = { 3, 3, 3, 4, 4, 5, 5, 7 };
    // hands = { 3, 3, 3, 4, 4, 4, 5, 5, 6, 6, 7 };
    // hands = { 3, 3, 5, 6, 6, 7, 7, 8 };
    // hands = { 3, 4, 4, 5, 5, 6, 6, 7 };
    // hands = { 3, 4, 5, 5, 6, 6, 7 };
    // hands = { 3, 4, 4, 5, 5, 5, 6, 6, 7 };
    // hands = { 3, 4, 5, 5, 5, 6, 6 };
    // hands = { 3, 3, 3, 4, 4, 5, 5, 5, 6, 6 };
    // hands = { 3, 3, 4, 4, 5, 5, 5, 6 };
    // hands = { 3, 3, 3, 5, 14, 14, 14 };
    // hands = { 3, 3, 3, 14, 14, 14 };
    // hands = { 3, 3, 4, 4, 4, 5, 5, 5, 5, 6 };
    // hands = { 3, 3, 4, 4, 4, 5, 5, 5, 6, 6, 6, 6, 8 };
    // hands = { 3, 3, 4, 4, 4, 4, 5, 5, 5, 6, 7 };
    // hands = { 3, 3, 4, 4, 4, 5, 5, 5, 6, 6, 6, 6, 8 };
    // hands = { 3, 3, 4, 4, 4, 4, 5, 5, 5, 6, 7 };
    // hands = { 3, 4, 4, 5, 5, 5, 5, 6 };
    // hands = { 3, 4, 4, 5, 5, 5, 5, 6, 6 };
    // hands = { 4, 5, 6, 6, 7, 8, 8, 8, 9, 9, 9, 12, 12, 12, 12 };

    /*
    Judge::getInstance().setCurrentHandsCategory(std::vector<size_t>{});

    auto              ret = Judge::getInstance().cardIntentions(test(hands));
    std::stringstream ss;

    for (auto &&item : ret)
    {
        ss.str("");

        ss << "{ ";
        for (auto &&element : item)
        {
            ss << element << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        // std::cout << ss.str();
    }

    for (auto &&item : ret)
    {
        ss.str("");

        ss << "{ ";
        for (auto &&element : item)
        {
            ss << (element >> 8) << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        std::cout << ss.str();
    }
*/

    for (int i = 0; i < 1024; ++i)
    {
        const auto &ret = Judge::getInstance().intentions(test(hands));

        std::stringstream ss;

        ss.str("");
        ss << "{ ";
        for (auto &&item : ret)
        {
            ss << (item >> 8) << ", ";
        }
        ss.seekp(-2, ss.end);
        ss << " }" << std::endl;

        std::cout << ss.str();
    }

    return 0;
}
<|endoftext|>


<commit_before>//courseID:CIS165-001
//name: David Ribeiro
//Prof. Wang
//Assignment#2
//Due by 9/22/2015

/*
 steps
 1.Input:
 a. sales numbers for each of the divisions

 2.Processing:
 a. Rewrites the sales figures for each division to the input number.

 3.Output:
 a. Computes the highest number and the corresponding Sales division name
 */

#include <iostream>
#include <string>
using namespace std;

double getSales(string, double);
void findHighest();

                                            /*Global Variables*/

     // Establishing Integer values for Sales figures in Each Sales Division as a Global Variable
double salesNe,
salesNw,
salesSe,
salesSw;

                                                    /*Main*/

int main()
{

                                                    // Establish the String Values for Each Sales Division
    string northE = " NorthEast sales division",
    northW = " NorthWest sales division",
    southE = " SouthEast sales division",
    southW = " SouthWest sales division";

                                                    // Input the Sales for each division
                                                    // Call getSale function for each Division and pass name of Division
    salesNe = getSales(northE, salesNe);
    salesNw = getSales(northW, salesNw);
    salesSe = getSales(southE, salesSe);
    salesSw = getSales(southW, salesSw);
                                                    // Call the findHighest function
    findHighest();

    return 0;

}

                                                                    // Proccessing
                                                                    /*getSales*/

double getSales(string name, double sales){

    cout << "What are the quarterly earnings for the " << name << "?" << endl;

    cin >> sales;

    while (sales < 0)
    {
        cout << "That was an invalid sales number, please enter a number over 0." << endl;

        cin >> sales;
    }

    return sales;
}

                                                                    /*findHighest*/
void findHighest(){

        double array[5] = {salesNe, salesNw, salesSe, salesSw};
        int temp = 0;

        for(int i=0;i<4;i++)
        {
            if(array[i]>temp)
                temp=array[i];
        }

                                                                    // Output
    if (temp == salesNe)
    {
    cout << "The highest grossing division is the Northeast sales division and it's sales figure was $"
        << salesNe << "." << endl;
    }
    else if (temp == salesNw)
    {
        cout << "The highest grossing division is the NorthWest sales division and it's sales figure was $"
        << salesNw << "." << endl;

    }
    else if (temp == salesSe)
    {
        cout << "The highest grossing division is the Southeast sales division and it's sales figure was $"
        << salesSe << "." << endl;

    }
    else if (temp == salesSw)
    {
        cout << "The highest grossing division is the Southwest sales division and it's sales figure was $"
        << salesSw << "." << endl;

    }

        }

<commit_msg>Fixing detached Head<commit_after><|endoftext|>


<commit_before>// Module:  Log4CPLUS
// File:    loglevel.cxx
// Created: 6/2001
// Author:  Tad E. Smith
//
//
// Copyright 2001-2009 Tad E. Smith
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <log4cplus/loglevel.h>
#include <log4cplus/helpers/loglog.h>
#include <log4cplus/helpers/stringhelper.h>
#include <log4cplus/internal/internal.h>
#include <algorithm>

namespace log4cplus
{

namespace
{

static tstring const ALL_STRING (LOG4CPLUS_TEXT("ALL"));
static tstring const TRACE_STRING (LOG4CPLUS_TEXT("TRACE"));
static tstring const DEBUG_STRING (LOG4CPLUS_TEXT("DEBUG"));
static tstring const INFO_STRING (LOG4CPLUS_TEXT("INFO"));
static tstring const WARN_STRING (LOG4CPLUS_TEXT("WARN"));
static tstring const ERROR_STRING (LOG4CPLUS_TEXT("ERROR"));
static tstring const FATAL_STRING (LOG4CPLUS_TEXT("FATAL"));
static tstring const OFF_STRING (LOG4CPLUS_TEXT("OFF"));
static tstring const NOTSET_STRING (LOG4CPLUS_TEXT("NOTSET"));
static tstring const UNKNOWN_STRING (LOG4CPLUS_TEXT("UNKNOWN"));

struct log_levels_table_rec
{
    LogLevel const ll;
    tstring const * const str;
};

#define DEF_LLTAB_REC(x) { x ## _LOG_LEVEL, &(x ## _STRING) }

static log_levels_table_rec const log_levels_table[8] = {
    DEF_LLTAB_REC (OFF),
    DEF_LLTAB_REC (FATAL),
    DEF_LLTAB_REC (ERROR),
    DEF_LLTAB_REC (WARN),
    DEF_LLTAB_REC (INFO),
    DEF_LLTAB_REC (DEBUG),
    DEF_LLTAB_REC (TRACE),
    DEF_LLTAB_REC (ALL),
};

#undef DEF_LLTAB_REC

static
tstring const &
defaultLogLevelToStringMethod(LogLevel ll)
{
    switch(ll) {
        case OFF_LOG_LEVEL:     return OFF_STRING;
        case FATAL_LOG_LEVEL:   return FATAL_STRING;
        case ERROR_LOG_LEVEL:   return ERROR_STRING;
        case WARN_LOG_LEVEL:    return WARN_STRING;
        case INFO_LOG_LEVEL:    return INFO_STRING;
        case DEBUG_LOG_LEVEL:   return DEBUG_STRING;
        case TRACE_LOG_LEVEL:   return TRACE_STRING;
        //case ALL_LOG_LEVEL:     return ALL_STRING;
        case NOT_SET_LOG_LEVEL: return NOTSET_STRING;
    };

    return internal::empty_str;
}

static
LogLevel
defaultStringToLogLevelMethod(const tstring& arg)
{
    tstring s = helpers::toUpper(arg);

    size_t const tbl_size
        = sizeof (log_levels_table) / sizeof (log_levels_table[0]);

    for (log_levels_table_rec const * it = log_levels_table;
        it != log_levels_table + tbl_size; ++it)
    {
        if (*it->str == arg)
            return it->ll;
    }

    return NOT_SET_LOG_LEVEL;
}

} // namespace

//////////////////////////////////////////////////////////////////////////////
// public static methods
//////////////////////////////////////////////////////////////////////////////

LogLevelManager&
getLogLevelManager()
{
    static LogLevelManager singleton;
    return singleton;
}

//////////////////////////////////////////////////////////////////////////////
// LogLevelManager ctors and dtor
//////////////////////////////////////////////////////////////////////////////

LogLevelManager::LogLevelManager()
{
    toStringMethods.push_back (defaultLogLevelToStringMethod);
    fromStringMethods.push_back (defaultStringToLogLevelMethod);
}

LogLevelManager::~LogLevelManager()
{ }

//////////////////////////////////////////////////////////////////////////////
// LogLevelManager public methods
//////////////////////////////////////////////////////////////////////////////

tstring const &
LogLevelManager::toString(LogLevel ll) const
{
    for (LogLevelToStringMethodList::const_iterator it
        = toStringMethods.begin (); it != toStringMethods.end (); ++it)
    {
        tstring const & ret = (*it) (ll);
        if (! ret.empty ())
            return ret;
    }

    return UNKNOWN_STRING;
}

LogLevel
LogLevelManager::fromString(const tstring& s) const
{
    for (StringToLogLevelMethodList::const_iterator it
        = fromStringMethods.begin (); it != fromStringMethods.end (); ++it)
    {
        LogLevel ret = (*it) (s);
        if (ret != NOT_SET_LOG_LEVEL)
            return ret;
    }

    return NOT_SET_LOG_LEVEL;
}

void
LogLevelManager::pushToStringMethod(LogLevelToStringMethod newToString)
{
    toStringMethods.push_back (newToString);
}

void
LogLevelManager::pushFromStringMethod(StringToLogLevelMethod newFromString)
{
    fromStringMethods.push_back (newFromString);
}

} // namespace log4cplus
<commit_msg>loglevel.cxx: Move toUpper() call from defaultStringToLogLevelMethod() to fromString().<commit_after>// Module:  Log4CPLUS
// File:    loglevel.cxx
// Created: 6/2001
// Author:  Tad E. Smith
//
//
// Copyright 2001-2009 Tad E. Smith
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <log4cplus/loglevel.h>
#include <log4cplus/helpers/loglog.h>
#include <log4cplus/helpers/stringhelper.h>
#include <log4cplus/internal/internal.h>
#include <algorithm>

namespace log4cplus
{

namespace
{

static tstring const ALL_STRING (LOG4CPLUS_TEXT("ALL"));
static tstring const TRACE_STRING (LOG4CPLUS_TEXT("TRACE"));
static tstring const DEBUG_STRING (LOG4CPLUS_TEXT("DEBUG"));
static tstring const INFO_STRING (LOG4CPLUS_TEXT("INFO"));
static tstring const WARN_STRING (LOG4CPLUS_TEXT("WARN"));
static tstring const ERROR_STRING (LOG4CPLUS_TEXT("ERROR"));
static tstring const FATAL_STRING (LOG4CPLUS_TEXT("FATAL"));
static tstring const OFF_STRING (LOG4CPLUS_TEXT("OFF"));
static tstring const NOTSET_STRING (LOG4CPLUS_TEXT("NOTSET"));
static tstring const UNKNOWN_STRING (LOG4CPLUS_TEXT("UNKNOWN"));

struct log_levels_table_rec
{
    LogLevel const ll;
    tstring const * const str;
};

#define DEF_LLTAB_REC(x) { x ## _LOG_LEVEL, &(x ## _STRING) }

static log_levels_table_rec const log_levels_table[8] = {
    DEF_LLTAB_REC (OFF),
    DEF_LLTAB_REC (FATAL),
    DEF_LLTAB_REC (ERROR),
    DEF_LLTAB_REC (WARN),
    DEF_LLTAB_REC (INFO),
    DEF_LLTAB_REC (DEBUG),
    DEF_LLTAB_REC (TRACE),
    DEF_LLTAB_REC (ALL),
};

#undef DEF_LLTAB_REC

static
tstring const &
defaultLogLevelToStringMethod(LogLevel ll)
{
    switch(ll) {
        case OFF_LOG_LEVEL:     return OFF_STRING;
        case FATAL_LOG_LEVEL:   return FATAL_STRING;
        case ERROR_LOG_LEVEL:   return ERROR_STRING;
        case WARN_LOG_LEVEL:    return WARN_STRING;
        case INFO_LOG_LEVEL:    return INFO_STRING;
        case DEBUG_LOG_LEVEL:   return DEBUG_STRING;
        case TRACE_LOG_LEVEL:   return TRACE_STRING;
        //case ALL_LOG_LEVEL:     return ALL_STRING;
        case NOT_SET_LOG_LEVEL: return NOTSET_STRING;
    };

    return internal::empty_str;
}

static
LogLevel
defaultStringToLogLevelMethod(const tstring& s)
{
    size_t const tbl_size
        = sizeof (log_levels_table) / sizeof (log_levels_table[0]);

    for (log_levels_table_rec const * it = log_levels_table;
        it != log_levels_table + tbl_size; ++it)
    {
        if (*it->str == s)
            return it->ll;
    }

    return NOT_SET_LOG_LEVEL;
}

} // namespace

//////////////////////////////////////////////////////////////////////////////
// public static methods
//////////////////////////////////////////////////////////////////////////////

LogLevelManager&
getLogLevelManager()
{
    static LogLevelManager singleton;
    return singleton;
}

//////////////////////////////////////////////////////////////////////////////
// LogLevelManager ctors and dtor
//////////////////////////////////////////////////////////////////////////////

LogLevelManager::LogLevelManager()
{
    toStringMethods.push_back (defaultLogLevelToStringMethod);
    fromStringMethods.push_back (defaultStringToLogLevelMethod);
}

LogLevelManager::~LogLevelManager()
{ }

//////////////////////////////////////////////////////////////////////////////
// LogLevelManager public methods
//////////////////////////////////////////////////////////////////////////////

tstring const &
LogLevelManager::toString(LogLevel ll) const
{
    for (LogLevelToStringMethodList::const_iterator it
        = toStringMethods.begin (); it != toStringMethods.end (); ++it)
    {
        tstring const & ret = (*it) (ll);
        if (! ret.empty ())
            return ret;
    }

    return UNKNOWN_STRING;
}

LogLevel
LogLevelManager::fromString(const tstring& arg) const
{
    tstring s = helpers::toUpper(arg);

    for (StringToLogLevelMethodList::const_iterator it
        = fromStringMethods.begin (); it != fromStringMethods.end (); ++it)
    {
        LogLevel ret = (*it) (s);
        if (ret != NOT_SET_LOG_LEVEL)
            return ret;
    }

    return NOT_SET_LOG_LEVEL;
}

void
LogLevelManager::pushToStringMethod(LogLevelToStringMethod newToString)
{
    toStringMethods.push_back (newToString);
}

void
LogLevelManager::pushFromStringMethod(StringToLogLevelMethod newFromString)
{
    fromStringMethods.push_back (newFromString);
}

} // namespace log4cplus
<|endoftext|>


<commit_before>//=======================================================================
// Copyright Baptiste Wicht 2011.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
//  http://www.boost.org/LICENSE_1_0.txt)
//=======================================================================

#include <sstream>
#include <cctype>

#include "mangling.hpp"
#include "assert.hpp"
#include "Utils.hpp"
#include "VisitorUtils.hpp"
#include "Type.hpp"

#include "ast/GetTypeVisitor.hpp"

using namespace eddic;

std::string eddic::mangle(std::shared_ptr<const Type> type){
    if(type->is_array()){
        return "A" + mangle(type->data_type());
    }

    if(type->is_pointer()){
        return "P" + mangle(type->data_type());
    }

    if(type->is_standard_type()){
        if(type == INT){
            return "I";
        } else if(type == CHAR){
            return "C";
        } else if(type == STRING){
            return "S";
        } else if(type == BOOL){
            return "B";
        } else if(type == FLOAT){
            return "F";
        } else if(type == VOID){
            return "V";
        }

        ASSERT_PATH_NOT_TAKEN("Not a standard type");
    } else {
        std::ostringstream ss;

        ss << "C";
        ss << type->type().length();
        ss << type->type();

        return ss.str();
    }
}

std::string eddic::mangle(std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_F";

    if(!function->struct_.empty()){
        ss << function->struct_.length();
        ss << function->struct_;
    }

    ss << function->name.length();
    ss << function->name;

    for(auto type : function->parameters){
        if(type.name != "this"){
            ss << mangle(type.paramType);
        }
    }

    return ss.str();
}

std::string eddic::mangle_ctor(const std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_C";

    ss << function->struct_.length();
    ss << function->struct_;

    for(auto type : function->parameters){
        if(type.name != "this"){
            ss << mangle(type.paramType);
        }
    }

    return ss.str();
}

std::string eddic::mangle_dtor(const std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_D";

    ss << function->struct_.length();
    ss << function->struct_;

    return ss.str();
}

std::string eddic::mangle(const std::string& functionName, const std::vector<ast::Value>& values, const std::string& struct_){
    std::ostringstream ss;

    ss << "_F";

    if(!struct_.empty()){
        ss << struct_.length();
        ss << struct_;
    }

    ss << functionName.length();
    ss << functionName;

    ast::GetTypeVisitor visitor;
    for(auto& value : values){
        auto type = visit(visitor, value);
        ss << mangle(type);
    }

    return ss.str();
}

std::string eddic::mangle_ctor(const std::vector<ast::Value>& values, const std::string& struct_){
    std::ostringstream ss;

    ss << "_C";

    ss << struct_.length();
    ss << struct_;

    ast::GetTypeVisitor visitor;
    for(auto& value : values){
        auto type = visit(visitor, value);
        ss << mangle(type);
    }

    return ss.str();
}

std::string eddic::mangle_dtor(const std::string& struct_){
    std::ostringstream ss;

    ss << "_D";

    ss << struct_.length();
    ss << struct_;

    return ss.str();
}

std::string eddic::mangle(const std::string& functionName, const std::vector<std::shared_ptr<const Type>>& types, const std::string& struct_){
    std::ostringstream ss;

    ss << "_F";

    if(!struct_.empty()){
        ss << struct_.length();
        ss << struct_;
    }

    ss << functionName.length();
    ss << functionName;

    for(auto type : types){
        ss << mangle(type);
    }

    return ss.str();
}

std::string get_name_from_length(const std::string& mangled, unsigned int& i){
    std::ostringstream length;
    int digits = 0;

    for(; i < mangled.length(); ++i){
        if(isdigit(mangled[i])){
            length << mangled[i];
            ++digits;
        } else {
            break;
        }
    }

    int l = toNumber<unsigned int>(length.str());

    std::ostringstream name;

    auto start = i;
    for(; i < start + l; ++i){
        name << mangled[i];
    }

    return name.str();
}

std::string eddic::unmangle(std::string mangled){
    unsigned int o = 2;

    std::ostringstream function;

    function << get_name_from_length(mangled, o);

    //Test if inside a struct
    if(isdigit(mangled[o])){
        function << "::";

        function << get_name_from_length(mangled, o);
    }

    function << '(';

    for(; o < mangled.length(); ++o){
        char current = mangled[o];

        bool array = false;
        if(current == 'A'){
            array = true;
            current = mangled[++o];
        }

        bool pointer = false;
        if(current == 'P'){
            pointer = true;
            current = mangled[++o];
        }

        if(current == 'I'){
            function << "int";
        } else if(current == 'C'){
            function << "char";
        } else if(current == 'S'){
            function << "string";
        } else if(current == 'B'){
            function << "bool";
        } else if(current == 'F'){
            function << "float";
        }

        if(array){
            function << "[]";
        }

        if(pointer){
            function << "&";
        }

        if(o < mangled.length() - 1){
            function << ", ";
        }
    }

    function << ')';

    return function.str();
}
<commit_msg>Handle template types in mangling<commit_after>//=======================================================================
// Copyright Baptiste Wicht 2011.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
//  http://www.boost.org/LICENSE_1_0.txt)
//=======================================================================

#include <sstream>
#include <cctype>

#include "mangling.hpp"
#include "assert.hpp"
#include "Utils.hpp"
#include "VisitorUtils.hpp"
#include "Type.hpp"

#include "ast/GetTypeVisitor.hpp"

using namespace eddic;

std::string eddic::mangle(std::shared_ptr<const Type> type){
    if(type->is_array()){
        return "A" + mangle(type->data_type());
    }

    if(type->is_pointer()){
        return "P" + mangle(type->data_type());
    }

    if(type->is_standard_type()){
        if(type == INT){
            return "I";
        } else if(type == CHAR){
            return "C";
        } else if(type == STRING){
            return "S";
        } else if(type == BOOL){
            return "B";
        } else if(type == FLOAT){
            return "F";
        } else if(type == VOID){
            return "V";
        }
    }

    if(type->is_custom_type()){
        std::ostringstream ss;

        ss << "C";
        ss << type->type().length();
        ss << type->type();

        return ss.str();
    }

    if(type->is_template()){
        std::ostringstream ss;

        ss << "CT";
        ss << type->type().length();
        ss << type->type();

        auto types = type->template_types();

        ss << types.size();

        for(auto& sub_type : types){
            ss << mangle(sub_type);
        }

        return ss.str();
    }

    ASSERT_PATH_NOT_TAKEN("Invalid type");
}

std::string eddic::mangle(std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_F";

    if(!function->struct_.empty()){
        ss << function->struct_.length();
        ss << function->struct_;
    }

    ss << function->name.length();
    ss << function->name;

    for(auto type : function->parameters){
        if(type.name != "this"){
            ss << mangle(type.paramType);
        }
    }

    return ss.str();
}

std::string eddic::mangle_ctor(const std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_C";

    ss << function->struct_.length();
    ss << function->struct_;

    for(auto type : function->parameters){
        if(type.name != "this"){
            ss << mangle(type.paramType);
        }
    }

    return ss.str();
}

std::string eddic::mangle_dtor(const std::shared_ptr<Function> function){
    std::ostringstream ss;

    ss << "_D";

    ss << function->struct_.length();
    ss << function->struct_;

    return ss.str();
}

std::string eddic::mangle(const std::string& functionName, const std::vector<ast::Value>& values, const std::string& struct_){
    std::ostringstream ss;

    ss << "_F";

    if(!struct_.empty()){
        ss << struct_.length();
        ss << struct_;
    }

    ss << functionName.length();
    ss << functionName;

    ast::GetTypeVisitor visitor;
    for(auto& value : values){
        auto type = visit(visitor, value);
        ss << mangle(type);
    }

    return ss.str();
}

std::string eddic::mangle_ctor(const std::vector<ast::Value>& values, const std::string& struct_){
    std::ostringstream ss;

    ss << "_C";

    ss << struct_.length();
    ss << struct_;

    ast::GetTypeVisitor visitor;
    for(auto& value : values){
        auto type = visit(visitor, value);
        ss << mangle(type);
    }

    return ss.str();
}

std::string eddic::mangle_dtor(const std::string& struct_){
    std::ostringstream ss;

    ss << "_D";

    ss << struct_.length();
    ss << struct_;

    return ss.str();
}

std::string eddic::mangle(const std::string& functionName, const std::vector<std::shared_ptr<const Type>>& types, const std::string& struct_){
    std::ostringstream ss;

    ss << "_F";

    if(!struct_.empty()){
        ss << struct_.length();
        ss << struct_;
    }

    ss << functionName.length();
    ss << functionName;

    for(auto type : types){
        ss << mangle(type);
    }

    return ss.str();
}

std::string get_name_from_length(const std::string& mangled, unsigned int& i){
    std::ostringstream length;
    int digits = 0;

    for(; i < mangled.length(); ++i){
        if(isdigit(mangled[i])){
            length << mangled[i];
            ++digits;
        } else {
            break;
        }
    }

    int l = toNumber<unsigned int>(length.str());

    std::ostringstream name;

    auto start = i;
    for(; i < start + l; ++i){
        name << mangled[i];
    }

    return name.str();
}

std::string eddic::unmangle(std::string mangled){
    unsigned int o = 2;

    std::ostringstream function;

    function << get_name_from_length(mangled, o);

    //Test if inside a struct
    if(isdigit(mangled[o])){
        function << "::";

        function << get_name_from_length(mangled, o);
    }

    function << '(';

    for(; o < mangled.length(); ++o){
        char current = mangled[o];

        bool array = false;
        if(current == 'A'){
            array = true;
            current = mangled[++o];
        }

        bool pointer = false;
        if(current == 'P'){
            pointer = true;
            current = mangled[++o];
        }

        if(current == 'I'){
            function << "int";
        } else if(current == 'C'){
            function << "char";
        } else if(current == 'S'){
            function << "string";
        } else if(current == 'B'){
            function << "bool";
        } else if(current == 'F'){
            function << "float";
        }

        if(array){
            function << "[]";
        }

        if(pointer){
            function << "&";
        }

        if(o < mangled.length() - 1){
            function << ", ";
        }
    }

    function << ')';

    return function.str();
}
<|endoftext|>


<commit_before>// Copyright 2014-2017 Open Source Robotics Foundation, Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <set>
#include <map>
#include <string>

#include "rcutils/allocator.h"
#include "rcutils/logging_macros.h"
#include "rcutils/strdup.h"
#include "rmw/error_handling.h"
#include "rmw/names_and_types.h"
#include "rmw/get_service_names_and_types.h"
#include "rmw/types.h"
#include "rmw/convert_rcutils_ret_to_rmw_ret.h"
#include "rmw/impl/cpp/macros.hpp"

#include "identifier.hpp"
#include "types.hpp"
#include "demangle.hpp"

// The extern "C" here enforces that overloading is not used.
extern "C"
{
rmw_ret_t
rmw_get_service_names_and_types(
  const rmw_node_t * node,
  rcutils_allocator_t * allocator,
  rmw_names_and_types_t * service_names_and_types)
{
  if (!allocator) {
    RMW_SET_ERROR_MSG("allocator is null")
    return RMW_RET_INVALID_ARGUMENT;
  }
  if (!node) {
    RMW_SET_ERROR_MSG_ALLOC("null node handle", *allocator)
    return RMW_RET_INVALID_ARGUMENT;
  }
  RMW_CHECK_TYPE_IDENTIFIERS_MATCH(
    node handle,
    node->implementation_identifier, opensplice_cpp_identifier,
    return RMW_RET_ERROR)

  rmw_ret_t ret = rmw_names_and_types_check_zero(service_names_and_types);
  if (ret != RMW_RET_OK) {
    return ret;
  }
  auto node_info = static_cast<OpenSpliceStaticNodeInfo *>(node->data);
  if (!node_info) {
    RMW_SET_ERROR_MSG("node info handle is null");
  }
  if (!node_info->publisher_listener) {
    RMW_SET_ERROR_MSG("publisher listener handle is null");
    return RMW_RET_ERROR;
  }
  if (!node_info->publisher_listener) {
    RMW_SET_ERROR_MSG("publisher listener handle is null");
    return RMW_RET_ERROR;
  }
  if (!node_info->subscriber_listener) {
    RMW_SET_ERROR_MSG("subscriber listener handle is null");
    return RMW_RET_ERROR;
  }

  // combine publisher and subscriber information
  std::map<std::string, std::set<std::string>> services;
  node_info->publisher_listener->fill_service_names_and_types(services);
  node_info->subscriber_listener->fill_service_names_and_types(services);

  // Fill out service_names_and_types
  if (services.size()) {
    // Setup string array to store names
    rmw_ret_t rmw_ret =
      rmw_names_and_types_init(service_names_and_types, services.size(), allocator);
    if (rmw_ret != RMW_RET_OK) {
      return rmw_ret;
    }
    // Setup cleanup function, in case of failure below
    auto fail_cleanup = [&service_names_and_types]() {
        rmw_ret_t rmw_ret = rmw_names_and_types_fini(service_names_and_types);
        if (rmw_ret != RMW_RET_OK) {
          RCUTILS_LOG_ERROR("error during report of error: %s", rmw_get_error_string_safe())
        }
      };
    // For each service, store the name, initialize the string array for types, and store all types
    size_t index = 0;
    for (const auto & service_n_types : services) {
      // Duplicate and store the service_name
      char * service_name = rcutils_strdup(service_n_types.first.c_str(), *allocator);
      if (!service_name) {
        RMW_SET_ERROR_MSG_ALLOC("failed to allocate memory for service name", *allocator);
        fail_cleanup();
        return RMW_RET_BAD_ALLOC;
      }
      service_names_and_types->names.data[index] = service_name;
      // Setup storage for types
      {
        rcutils_ret_t rcutils_ret = rcutils_string_array_init(
          &service_names_and_types->types[index],
          service_n_types.second.size(),
          allocator);
        if (rcutils_ret != RCUTILS_RET_OK) {
          RMW_SET_ERROR_MSG(rcutils_get_error_string_safe())
          fail_cleanup();
          return rmw_convert_rcutils_ret_to_rmw_ret(rcutils_ret);
        }
      }
      // Duplicate and store each type for the service
      size_t type_index = 0;
      for (const auto & type : service_n_types.second) {
        char * type_name = rcutils_strdup(type.c_str(), *allocator);
        if (!type_name) {
          RMW_SET_ERROR_MSG_ALLOC("failed to allocate memory for type name", *allocator)
          fail_cleanup();
          return RMW_RET_BAD_ALLOC;
        }
        service_names_and_types->types[index].data[type_index] = type_name;
        ++type_index;
      }  // for each type
      ++index;
    }  // for each service
  }
  return RMW_RET_OK;
}
}  // extern "C"
<commit_msg>strip 'Sample_' from reported types (#234)<commit_after>// Copyright 2014-2017 Open Source Robotics Foundation, Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <set>
#include <map>
#include <string>

#include "rcutils/allocator.h"
#include "rcutils/logging_macros.h"
#include "rcutils/strdup.h"
#include "rmw/error_handling.h"
#include "rmw/names_and_types.h"
#include "rmw/get_service_names_and_types.h"
#include "rmw/types.h"
#include "rmw/convert_rcutils_ret_to_rmw_ret.h"
#include "rmw/impl/cpp/macros.hpp"

#include "identifier.hpp"
#include "types.hpp"
#include "demangle.hpp"

#define SAMPLE_PREFIX "/Sample_"
// The extern "C" here enforces that overloading is not used.
extern "C"
{
rmw_ret_t
rmw_get_service_names_and_types(
  const rmw_node_t * node,
  rcutils_allocator_t * allocator,
  rmw_names_and_types_t * service_names_and_types)
{
  if (!allocator) {
    RMW_SET_ERROR_MSG("allocator is null")
    return RMW_RET_INVALID_ARGUMENT;
  }
  if (!node) {
    RMW_SET_ERROR_MSG_ALLOC("null node handle", *allocator)
    return RMW_RET_INVALID_ARGUMENT;
  }
  RMW_CHECK_TYPE_IDENTIFIERS_MATCH(
    node handle,
    node->implementation_identifier, opensplice_cpp_identifier,
    return RMW_RET_ERROR)

  rmw_ret_t ret = rmw_names_and_types_check_zero(service_names_and_types);
  if (ret != RMW_RET_OK) {
    return ret;
  }
  auto node_info = static_cast<OpenSpliceStaticNodeInfo *>(node->data);
  if (!node_info) {
    RMW_SET_ERROR_MSG("node info handle is null");
  }
  if (!node_info->publisher_listener) {
    RMW_SET_ERROR_MSG("publisher listener handle is null");
    return RMW_RET_ERROR;
  }
  if (!node_info->publisher_listener) {
    RMW_SET_ERROR_MSG("publisher listener handle is null");
    return RMW_RET_ERROR;
  }
  if (!node_info->subscriber_listener) {
    RMW_SET_ERROR_MSG("subscriber listener handle is null");
    return RMW_RET_ERROR;
  }

  // combine publisher and subscriber information
  std::map<std::string, std::set<std::string>> services;
  node_info->publisher_listener->fill_service_names_and_types(services);
  node_info->subscriber_listener->fill_service_names_and_types(services);

  // Fill out service_names_and_types
  if (services.size()) {
    // Setup string array to store names
    rmw_ret_t rmw_ret =
      rmw_names_and_types_init(service_names_and_types, services.size(), allocator);
    if (rmw_ret != RMW_RET_OK) {
      return rmw_ret;
    }
    // Setup cleanup function, in case of failure below
    auto fail_cleanup = [&service_names_and_types]() {
        rmw_ret_t rmw_ret = rmw_names_and_types_fini(service_names_and_types);
        if (rmw_ret != RMW_RET_OK) {
          RCUTILS_LOG_ERROR("error during report of error: %s", rmw_get_error_string_safe())
        }
      };
    // For each service, store the name, initialize the string array for types, and store all types
    size_t index = 0;
    for (const auto & service_n_types : services) {
      // Duplicate and store the service_name
      char * service_name = rcutils_strdup(service_n_types.first.c_str(), *allocator);
      if (!service_name) {
        RMW_SET_ERROR_MSG_ALLOC("failed to allocate memory for service name", *allocator);
        fail_cleanup();
        return RMW_RET_BAD_ALLOC;
      }
      service_names_and_types->names.data[index] = service_name;
      // Setup storage for types
      {
        rcutils_ret_t rcutils_ret = rcutils_string_array_init(
          &service_names_and_types->types[index],
          service_n_types.second.size(),
          allocator);
        if (rcutils_ret != RCUTILS_RET_OK) {
          RMW_SET_ERROR_MSG(rcutils_get_error_string_safe())
          fail_cleanup();
          return rmw_convert_rcutils_ret_to_rmw_ret(rcutils_ret);
        }
      }
      // Duplicate and store each type for the service
      size_t type_index = 0;
      for (const auto & type : service_n_types.second) {
        size_t n = type.find(SAMPLE_PREFIX);
        if (std::string::npos == n) {
          char * error_msg = rcutils_format_string(
            *allocator,
            "failed to convert DDS type name to ROS service type name: '" SAMPLE_PREFIX
            "' not found in type: '%s'", type.c_str());
          RMW_SET_ERROR_MSG(error_msg)
          allocator->deallocate(error_msg, allocator->state);
          fail_cleanup();
          return RMW_RET_ERROR;
        }
        std::string stripped_type = type.substr(0, n + 1) + type.substr(n + strlen(SAMPLE_PREFIX));
        char * type_name = rcutils_strdup(stripped_type.c_str(), *allocator);
        if (!type_name) {
          RMW_SET_ERROR_MSG_ALLOC("failed to allocate memory for type name", *allocator)
          fail_cleanup();
          return RMW_RET_BAD_ALLOC;
        }
        service_names_and_types->types[index].data[type_index] = type_name;
        ++type_index;
      }  // for each type
      ++index;
    }  // for each service
  }
  return RMW_RET_OK;
}
}  // extern "C"
<|endoftext|>


<commit_before>#include "testing/testing.hpp"

#include "platform/local_country_file.hpp"

#include "geometry/mercator.hpp"
#include "geometry/point2d.hpp"

#include "indexer/classificator_loader.hpp"
#include "indexer/data_source.hpp"
#include "indexer/feature_altitude.hpp"
#include "indexer/mwm_set.hpp"

#include "routing_common/car_model.hpp"
#include "routing/features_road_graph.hpp"
#include "routing/road_graph.hpp"

#include "routing/routing_integration_tests/routing_test_tools.hpp"

#include <vector>

using namespace routing;
using namespace integration;

// The test on combinatorial explosion of number of fake edges at FeaturesRoadGraph.
// It might happen when a lot of roads intersect at one point. For example,
// https://www.openstreetmap.org/#map=19/50.73197/-1.21295
UNIT_TEST(FakeEdgesCombinatorialExplosion)
{
  classificator::Load();

  std::vector<LocalCountryFile> localFiles;
  GetAllLocalFiles(localFiles);
  TEST(!localFiles.empty(), ());

  FrozenDataSource dataSource;
  for (auto const & file : localFiles)
  {
    auto const result = dataSource.Register(file);
    TEST_EQUAL(result.second, MwmSet::RegResult::Success, ());
  }

  FeaturesRoadGraph graph(dataSource, IRoadGraph::Mode::ObeyOnewayTag,
                          make_shared<CarModelFactory>(CountryParentNameGetterFn()));
  Junction const j(m2::PointD(MercatorBounds::FromLatLon(50.73208, -1.21279)), feature::kDefaultAltitudeMeters);
  std::vector<std::pair<routing::Edge, routing::Junction>> sourceVicinity;
  graph.FindClosestEdges(MercatorBounds::RectByCenterXYAndSizeInMeters(
                             j.GetPoint(), FeaturesRoadGraph::kClosestEdgesRadiusM),
                         20 /* count */, sourceVicinity);
  // In case of the combinatorial explosion mentioned above all the memory was consumed for
  // FeaturesRoadGraph::m_fakeIngoingEdges and FeaturesRoadGraph::m_fakeOutgoingEdges fields.
  graph.AddFakeEdges(j, sourceVicinity);
}
<commit_msg>Fixing FakeEdgesCombinatorialExplosion test. Some memory for example (WorldCoasts_obsolete.mwm) may not be registered.<commit_after>#include "testing/testing.hpp"

#include "platform/local_country_file.hpp"

#include "geometry/mercator.hpp"
#include "geometry/point2d.hpp"

#include "indexer/classificator_loader.hpp"
#include "indexer/data_source.hpp"
#include "indexer/feature_altitude.hpp"
#include "indexer/mwm_set.hpp"

#include "routing_common/car_model.hpp"
#include "routing/features_road_graph.hpp"
#include "routing/road_graph.hpp"

#include "routing/routing_integration_tests/routing_test_tools.hpp"

#include <vector>

using namespace routing;
using namespace integration;

// The test on combinatorial explosion of number of fake edges at FeaturesRoadGraph.
// It might happen when a lot of roads intersect at one point. For example,
// https://www.openstreetmap.org/#map=19/50.73197/-1.21295
UNIT_TEST(FakeEdgesCombinatorialExplosion)
{
  classificator::Load();

  std::vector<LocalCountryFile> localFiles;
  GetAllLocalFiles(localFiles);
  TEST(!localFiles.empty(), ());

  FrozenDataSource dataSource;
  for (auto const & file : localFiles)
    dataSource.Register(file);

  FeaturesRoadGraph graph(dataSource, IRoadGraph::Mode::ObeyOnewayTag,
                          make_shared<CarModelFactory>(CountryParentNameGetterFn()));
  Junction const j(m2::PointD(MercatorBounds::FromLatLon(50.73208, -1.21279)), feature::kDefaultAltitudeMeters);
  std::vector<std::pair<routing::Edge, routing::Junction>> sourceVicinity;
  graph.FindClosestEdges(MercatorBounds::RectByCenterXYAndSizeInMeters(
                             j.GetPoint(), FeaturesRoadGraph::kClosestEdgesRadiusM),
                         20 /* count */, sourceVicinity);
  // In case of the combinatorial explosion mentioned above all the memory was consumed for
  // FeaturesRoadGraph::m_fakeIngoingEdges and FeaturesRoadGraph::m_fakeOutgoingEdges fields.
  graph.AddFakeEdges(j, sourceVicinity);
}
<|endoftext|>