<commit_before>/* Copyright 2017 Istio Authors. All Rights Reserved.
 *
 * 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 "src/grpc_transport.h"
#include <mutex>
#include <thread>

namespace istio {
namespace mixer_client {
namespace {

// A gRPC stream
template <class RequestType, class ResponseType>
class GrpcStream final : public WriteInterface<RequestType> {
 public:
  typedef std::unique_ptr<
      ::grpc::ClientReaderWriterInterface<RequestType, ResponseType>>
      StreamPtr;
  typedef std::function<StreamPtr(::grpc::ClientContext&)> StreamNewFunc;

  GrpcStream(ReadInterface<ResponseType>* reader, StreamNewFunc create_func)
      : reader_(reader), write_closed_(false) {
    stream_ = create_func(context_);
  }

  static void Start(
      std::shared_ptr<GrpcStream<RequestType, ResponseType>> grpc_stream) {
    std::thread t([grpc_stream]() { grpc_stream->ReadMainLoop(); });
    t.detach();
  }

  void Write(const RequestType& request) override {
    std::lock_guard<std::mutex> lock(write_mutex_);
    if (!stream_->Write(request)) {
      stream_->WritesDone();
      write_closed_ = true;
    }
  }

  void WritesDone() override {
    std::lock_guard<std::mutex> lock(write_mutex_);
    stream_->WritesDone();
    write_closed_ = true;
  }

  bool is_write_closed() const override { return write_closed_; }

 private:
  // The worker loop to read response messages.
  void ReadMainLoop() {
    ResponseType response;
    while (stream_->Read(&response)) {
      reader_->OnRead(response);
    }
    ::grpc::Status status = stream_->Finish();
    // Convert grpc status to protobuf status.
    ::google::protobuf::util::Status pb_status(
        ::google::protobuf::util::error::Code(status.error_code()),
        ::google::protobuf::StringPiece(status.error_message()));
    reader_->OnClose(pb_status);
  }

  // The client context.
  ::grpc::ClientContext context_;
  // Mutex to make sure not calling stream_->Write() parallelly.
  std::mutex write_mutex_;
  // The reader writer stream.
  StreamPtr stream_;
  // The reader interface from caller.
  ReadInterface<ResponseType>* reader_;
  // Indicates if write is closed.
  bool write_closed_;
};

typedef GrpcStream<::istio::mixer::v1::CheckRequest,
                   ::istio::mixer::v1::CheckResponse>
    CheckGrpcStream;
typedef GrpcStream<::istio::mixer::v1::ReportRequest,
                   ::istio::mixer::v1::ReportResponse>
    ReportGrpcStream;
typedef GrpcStream<::istio::mixer::v1::QuotaRequest,
                   ::istio::mixer::v1::QuotaResponse>
    QuotaGrpcStream;

}  // namespace

GrpcTransport::GrpcTransport(const std::string& mixer_server) {
  channel_ = CreateChannel(mixer_server, ::grpc::InsecureChannelCredentials());
  stub_ = ::istio::mixer::v1::Mixer::NewStub(channel_);
}

CheckWriterPtr GrpcTransport::NewStream(CheckReaderRawPtr reader) {
  auto writer = std::make_shared<CheckGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> CheckGrpcStream::StreamPtr {
        return stub_->Check(&context);
      });
  CheckGrpcStream::Start(writer);
  return writer;
}

ReportWriterPtr GrpcTransport::NewStream(ReportReaderRawPtr reader) {
  auto writer = std::make_shared<ReportGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> ReportGrpcStream::StreamPtr {
        return stub_->Report(&context);
      });
  ReportGrpcStream::Start(writer);
  return writer;
}

QuotaWriterPtr GrpcTransport::NewStream(QuotaReaderRawPtr reader) {
  auto writer = std::make_shared<QuotaGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> QuotaGrpcStream::StreamPtr {
        return stub_->Quota(&context);
      });
  QuotaGrpcStream::Start(writer);
  return writer;
}

}  // namespace mixer_client
}  // namespace istio
<commit_msg>Add fast_fail for gRPC (#36)<commit_after>/* Copyright 2017 Istio Authors. All Rights Reserved.
 *
 * 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 "src/grpc_transport.h"
#include <mutex>
#include <thread>

namespace istio {
namespace mixer_client {
namespace {

// A gRPC stream
template <class RequestType, class ResponseType>
class GrpcStream final : public WriteInterface<RequestType> {
 public:
  typedef std::unique_ptr<
      ::grpc::ClientReaderWriterInterface<RequestType, ResponseType>>
      StreamPtr;
  typedef std::function<StreamPtr(::grpc::ClientContext&)> StreamNewFunc;

  GrpcStream(ReadInterface<ResponseType>* reader, StreamNewFunc create_func)
      : reader_(reader), write_closed_(false) {
    context_.set_fail_fast(true);
    stream_ = create_func(context_);
  }

  static void Start(
      std::shared_ptr<GrpcStream<RequestType, ResponseType>> grpc_stream) {
    std::thread t([grpc_stream]() { grpc_stream->ReadMainLoop(); });
    t.detach();
  }

  void Write(const RequestType& request) override {
    std::lock_guard<std::mutex> lock(write_mutex_);
    if (!stream_->Write(request)) {
      stream_->Finish();
    }
  }

  void WritesDone() override {
    std::lock_guard<std::mutex> lock(write_mutex_);
    stream_->WritesDone();
    write_closed_ = true;
  }

  bool is_write_closed() const override { return write_closed_; }

 private:
  // The worker loop to read response messages.
  void ReadMainLoop() {
    ResponseType response;
    while (stream_->Read(&response)) {
      reader_->OnRead(response);
    }
    ::grpc::Status status = stream_->Finish();
    // Convert grpc status to protobuf status.
    ::google::protobuf::util::Status pb_status(
        ::google::protobuf::util::error::Code(status.error_code()),
        ::google::protobuf::StringPiece(status.error_message()));
    reader_->OnClose(pb_status);
  }

  // The client context.
  ::grpc::ClientContext context_;
  // Mutex to make sure not calling stream_->Write() parallelly.
  std::mutex write_mutex_;
  // The reader writer stream.
  StreamPtr stream_;
  // The reader interface from caller.
  ReadInterface<ResponseType>* reader_;
  // Indicates if write is closed.
  bool write_closed_;
};

typedef GrpcStream<::istio::mixer::v1::CheckRequest,
                   ::istio::mixer::v1::CheckResponse>
    CheckGrpcStream;
typedef GrpcStream<::istio::mixer::v1::ReportRequest,
                   ::istio::mixer::v1::ReportResponse>
    ReportGrpcStream;
typedef GrpcStream<::istio::mixer::v1::QuotaRequest,
                   ::istio::mixer::v1::QuotaResponse>
    QuotaGrpcStream;

}  // namespace

GrpcTransport::GrpcTransport(const std::string& mixer_server) {
  channel_ = CreateChannel(mixer_server, ::grpc::InsecureChannelCredentials());
  stub_ = ::istio::mixer::v1::Mixer::NewStub(channel_);
}

CheckWriterPtr GrpcTransport::NewStream(CheckReaderRawPtr reader) {
  auto writer = std::make_shared<CheckGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> CheckGrpcStream::StreamPtr {
        return stub_->Check(&context);
      });
  CheckGrpcStream::Start(writer);
  return writer;
}

ReportWriterPtr GrpcTransport::NewStream(ReportReaderRawPtr reader) {
  auto writer = std::make_shared<ReportGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> ReportGrpcStream::StreamPtr {
        return stub_->Report(&context);
      });
  ReportGrpcStream::Start(writer);
  return writer;
}

QuotaWriterPtr GrpcTransport::NewStream(QuotaReaderRawPtr reader) {
  auto writer = std::make_shared<QuotaGrpcStream>(
      reader,
      [this](::grpc::ClientContext& context) -> QuotaGrpcStream::StreamPtr {
        return stub_->Quota(&context);
      });
  QuotaGrpcStream::Start(writer);
  return writer;
}

}  // namespace mixer_client
}  // namespace istio
<|endoftext|>


<commit_before>	// This file is a part of the OpenSurgSim project.
// Copyright 2013, SimQuest Solutions 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 <math.h>
#include <iostream>
#include <fstream>
#include "SurgSim/Physics/RenderTests/RenderTest.h"

#include "SurgSim/Framework/ApplicationData.h"
#include "SurgSim/Graphics/PointCloudRepresentation.h"
#include "SurgSim/Graphics/OsgPointCloudRepresentation.h"
#include "SurgSim/Math/Quaternion.h"
#include "SurgSim/Math/Vector.h"
#include "SurgSim/Math/RigidTransform.h"

#include "SurgSim/Physics/PhysicsManager.h"
#include "SurgSim/Physics/Fem3DRepresentation.h"
#include "SurgSim/Physics/FemElement3DCube.h"
#include "SurgSim/Physics/PhysicsManager.h"
#include "SurgSim/Graphics/OsgViewElement.h"
#include "SurgSim/Framework/SceneElement.h"
#include "SurgSim/Graphics/OsgCamera.h"
#include "SurgSim/Graphics/OsgManager.h"
#include "SurgSim/Graphics/OsgView.h"
#include "SurgSim/Math/Quaternion.h"

using SurgSim::Math::Vector3d;
using SurgSim::Math::Quaterniond;
using SurgSim::Math::RigidTransform3d;
using SurgSim::Math::makeRigidTransform;
using SurgSim::Framework::SceneElement;
using SurgSim::Graphics::OsgPointCloudRepresentation;
using SurgSim::Physics::PhysicsManager;
using SurgSim::Framework::SceneElement;

namespace SurgSim
{
namespace Physics
{

/// Truth cube implementation by Fem3DRepresentation
class TruthCubeRepresentation : public Fem3DRepresentation
{
public:
	/// Constructor
	/// \param name	The name of the truth cube representation.
	/// \param size	The original length of the truth cube in mm.
	/// \param level	The subdivision level.
	explicit TruthCubeRepresentation(const std::string& name, double size, unsigned int level) :
		m_name(name),
		m_size(size),
		m_levelSubdivision(level),
		Fem3DRepresentation(name)
	{
		const int dofPerNode = 3;

		m_numNodesPerAxis = pow(2, m_levelSubdivision) + 1;
		m_displacement.resize(m_numNodesPerAxis * m_numNodesPerAxis * m_numNodesPerAxis * dofPerNode);
		m_boundary.resize(m_numNodesPerAxis * m_numNodesPerAxis * m_numNodesPerAxis * dofPerNode);
		m_cubeNodes = createCube(m_size);
	}

	/// Destructor
	~TruthCubeRepresentation()
	{
	}

	/// Gets the number of nodes per axis of truth cube
	/// \return The number of nodes per axis.
	unsigned int getNumNodesPerAxis()
	{
		return m_numNodesPerAxis;
	}

	/// Gets displacement values
	/// \return The vector of displacement
	std::vector<double> getDisplacements()
	{
		return m_displacement;
	}

	/// Get number of displacement
	/// \return the size of displacement vector
	int getNumofDisplacements()
	{
		return m_displacement.size();
	}

	/// Creates the subdivision truth cube nodes
	void createTruthCubeMesh()
	{
		m_nodes.resize(m_numNodesPerAxis);
		for (int i = 0; i < m_numNodesPerAxis; i++)
		{
			m_nodes[i].resize(m_numNodesPerAxis);
			Vector3d extremitiesX0[4] = {m_cubeNodes[0], m_cubeNodes[2], m_cubeNodes[4], m_cubeNodes[6]};
			Vector3d extremitiesX1[4] = {m_cubeNodes[1], m_cubeNodes[3], m_cubeNodes[5], m_cubeNodes[7]};

			Vector3d extremitiesXi[4];
			for (int index = 0; index < 4; index++)
			{
				extremitiesXi[index] = extremitiesX0[index] * (1.0 - i / (m_numNodesPerAxis - 1.0)) +
					extremitiesX1[index] * i / (m_numNodesPerAxis - 1.0);
			}

			for (int j = 0; j < m_numNodesPerAxis; j++)
			{
				Vector3d extremitiesY0[2] = {extremitiesXi[0], extremitiesXi[2]};
				Vector3d extremitiesY1[2] = {extremitiesXi[1], extremitiesXi[3]};

				Vector3d extremitiesYi[2];
				for (int index = 0; index < 2; index++)
				{
					extremitiesYi[index] = extremitiesY0[index] * (1.0 - j/(m_numNodesPerAxis - 1.0)) +
						extremitiesY1[index] * j / (m_numNodesPerAxis - 1.0);
				}

				m_nodes[i][j].resize(m_numNodesPerAxis);
				for (int k=0; k < m_numNodesPerAxis; k++)
				{
					m_nodes[i][j][k] = extremitiesYi[0] * (1.0 - k / (m_numNodesPerAxis - 1.0)) + extremitiesYi[1]
										* k / (m_numNodesPerAxis - 1.0);
				}
			}
		}
	}

	/// Adds the Fem3D elements of small cubes
	/// \param state	The deformable state for initialization.
	void addFemCubes(std::shared_ptr<DeformableRepresentationState> state)
	{
		for (int i = 0; i < m_numNodesPerAxis - 1; i++)
		{
			for (int j = 0; j < m_numNodesPerAxis - 1; j++)
			{
				for (int k = 0; k < m_numNodesPerAxis - 1; k++)
				{
					std::array<int, 8> cubeNodeIds;
					cubeNodeIds[0] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i;
					cubeNodeIds[1] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i + 1;
					cubeNodeIds[2] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + (j + 1) * m_numNodesPerAxis + i;
					cubeNodeIds[3] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + (j + 1) * m_numNodesPerAxis + i + 1;
					cubeNodeIds[4] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i;
					cubeNodeIds[5] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i + 1;
					cubeNodeIds[6] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) +
										(j + 1) * m_numNodesPerAxis + i;
					cubeNodeIds[7] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) +
										(j+1) * m_numNodesPerAxis + i + 1;

					std::array<unsigned int, 8> cube = {
						cubeNodeIds[0], cubeNodeIds[1], cubeNodeIds[3], cubeNodeIds[2],
						cubeNodeIds[4], cubeNodeIds[5], cubeNodeIds[7], cubeNodeIds[6]};

					// Add FemElement3DCube for each cube
					std::shared_ptr<FemElement3DCube> femElement = std::make_shared<FemElement3DCube>(cube, *state);
					femElement->setMassDensity(1250.0);
					femElement->setPoissonRatio(0.499);
					femElement->setYoungModulus(15.3e5);
					femElement->initialize(*state);

					this->addFemElement(femElement);

				}
			}
		}
	}

private:
	typedef std::array<SurgSim::Math::Vector3d, 8> CubeNodesType;

	/// Creates the truth cube nodes
	/// \param size	The size in m of the truth cube.
	CubeNodesType createCube(double size)
	{
		CubeNodesType cubeNodes;
		cubeNodes[0] = Vector3d(-0.5,-0.5,-0.5) * size; cubeNodes[1] = Vector3d(0.5,-0.5,-0.5) * size;
		cubeNodes[2] = Vector3d(-0.5, 0.5,-0.5) * size; cubeNodes[3] = Vector3d( 0.5, 0.5,-0.5) * size;
		cubeNodes[4] = Vector3d(-0.5,-0.5, 0.5) * size; cubeNodes[5] = Vector3d( 0.5,-0.5, 0.5) * size;
		cubeNodes[6] = Vector3d(-0.5, 0.5, 0.5) * size; cubeNodes[7] = Vector3d( 0.5, 0.5, 0.5) * size;

		return cubeNodes;
	}

	// Name of the truth cube representation
	std::string m_name;
	// Size in m of the original truth cube
	double m_size;

	// Level of subdivision
	unsigned int m_levelSubdivision;

	// Number of point per dimensions for each subdivision level
	int m_numNodesPerAxis;

	// Displacement
	std::vector<double> m_displacement;

	// BoundaryCondition
	std::vector<bool> m_boundary;

	// Nodes of the original truth cube
	CubeNodesType m_cubeNodes;

	// Nodes of the subdivision cubes in 3D
	std::vector<std::vector<std::vector<Vector3d>>> m_nodes;
};

}; // namespace Physics
}; // namespace SurgSim

<commit_msg>Add accessors for boundary conditions and state of the truth cube.<commit_after>	// This file is a part of the OpenSurgSim project.
// Copyright 2013, SimQuest Solutions 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 <math.h>
#include <iostream>
#include <fstream>
#include "SurgSim/Physics/RenderTests/RenderTest.h"

#include "SurgSim/Framework/ApplicationData.h"
#include "SurgSim/Graphics/PointCloudRepresentation.h"
#include "SurgSim/Graphics/OsgPointCloudRepresentation.h"
#include "SurgSim/Math/Quaternion.h"
#include "SurgSim/Math/Vector.h"
#include "SurgSim/Math/RigidTransform.h"

#include "SurgSim/Physics/PhysicsManager.h"
#include "SurgSim/Physics/Fem3DRepresentation.h"
#include "SurgSim/Physics/FemElement3DCube.h"
#include "SurgSim/Physics/PhysicsManager.h"
#include "SurgSim/Graphics/OsgViewElement.h"
#include "SurgSim/Framework/SceneElement.h"
#include "SurgSim/Graphics/OsgCamera.h"
#include "SurgSim/Graphics/OsgManager.h"
#include "SurgSim/Graphics/OsgView.h"
#include "SurgSim/Math/Quaternion.h"

using SurgSim::Math::Vector3d;
using SurgSim::Math::Quaterniond;
using SurgSim::Math::RigidTransform3d;
using SurgSim::Math::makeRigidTransform;
using SurgSim::Framework::SceneElement;
using SurgSim::Graphics::OsgPointCloudRepresentation;
using SurgSim::Physics::PhysicsManager;
using SurgSim::Framework::SceneElement;

namespace SurgSim
{
namespace Physics
{

/// Truth cube implementation by Fem3DRepresentation
class TruthCubeRepresentation : public Fem3DRepresentation
{
public:
	/// Constructor
	/// \param name	The name of the truth cube representation.
	/// \param size	The original length of the truth cube in mm.
	/// \param level	The subdivision level.
	explicit TruthCubeRepresentation(const std::string& name, double size, unsigned int level) :
		m_name(name),
		m_size(size),
		m_levelSubdivision(level),
		Fem3DRepresentation(name)
	{
		const int dofPerNode = 3;

		m_numNodesPerAxis = pow(2, m_levelSubdivision) + 1;
		m_displacement.resize(m_numNodesPerAxis * m_numNodesPerAxis * m_numNodesPerAxis * dofPerNode);
		m_boundary.resize(m_numNodesPerAxis * m_numNodesPerAxis * m_numNodesPerAxis * dofPerNode);
		m_cubeNodes = createCube(m_size);
	}

	/// Destructor
	~TruthCubeRepresentation()
	{
	}

	/// Gets the number of nodes per axis of truth cube
	/// \return The number of nodes per axis.
	unsigned int getNumNodesPerAxis()
	{
		return m_numNodesPerAxis;
	}

	/// Gets displacement values
	/// \return The vector of displacement
	std::vector<double> getDisplacements()
	{
		return m_displacement;
	}

	/// Get number of displacement
	/// \return the size of displacement vector
	int getNumofDisplacements()
	{
		return m_displacement.size();
	}

	/// Sets state for the truth cube representation
	/// \param state	The deformable state.
	void setDeformableState(std::shared_ptr<DeformableRepresentationState> state)
	{
		int nodeId = 0;
		for (int k = 0; k < m_numNodesPerAxis; k++)
		{
			for (int j = 0; j < m_numNodesPerAxis; j++)
			{
				for (int i = 0; i < m_numNodesPerAxis; i++)
				{
					state->getPositions()[nodeId * 3 + 0] = m_nodes[i][j][k][0];
					state->getPositions()[nodeId * 3 + 1] = m_nodes[i][j][k][1];
					state->getPositions()[nodeId * 3 + 2] = m_nodes[i][j][k][2];
					nodeId++;
				}
			}
		}
	}

	/// Sets the boundary condition for the truth cube
	/// \param displacement	The displacement of the boundary conditions
	void setBoundaryCondition(double displacement)
	{
		int nodeId = 0;
		for (int k = 0; k < m_numNodesPerAxis; k++)
		{
			for (int j = 0; j < m_numNodesPerAxis; j++)
			{
				for (int i = 0; i < m_numNodesPerAxis; i++)
				{

					// Boundary conditions at bottom layer
					if (j == 0)
					{
						m_boundary[nodeId * 3 + 0] = true;
						m_boundary[nodeId * 3 + 1] = true;
						m_boundary[nodeId * 3 + 2] = true;
					}

					if (j == m_numNodesPerAxis-1)
					{
						// Apply displacement value
						m_displacement[nodeId * 3 + 1] = displacement;

					}
					nodeId++;
				}
			}
		}
	}

	std::vector<bool> getBoundaryConditions()
	{
		return m_boundary;
	}

	/// Creates the subdivision truth cube nodes
	void createTruthCubeMesh()
	{
		m_nodes.resize(m_numNodesPerAxis);
		for (int i = 0; i < m_numNodesPerAxis; i++)
		{
			m_nodes[i].resize(m_numNodesPerAxis);
			Vector3d extremitiesX0[4] = {m_cubeNodes[0], m_cubeNodes[2], m_cubeNodes[4], m_cubeNodes[6]};
			Vector3d extremitiesX1[4] = {m_cubeNodes[1], m_cubeNodes[3], m_cubeNodes[5], m_cubeNodes[7]};

			Vector3d extremitiesXi[4];
			for (int index = 0; index < 4; index++)
			{
				extremitiesXi[index] = extremitiesX0[index] * (1.0 - i / (m_numNodesPerAxis - 1.0)) +
					extremitiesX1[index] * i / (m_numNodesPerAxis - 1.0);
			}

			for (int j = 0; j < m_numNodesPerAxis; j++)
			{
				Vector3d extremitiesY0[2] = {extremitiesXi[0], extremitiesXi[2]};
				Vector3d extremitiesY1[2] = {extremitiesXi[1], extremitiesXi[3]};

				Vector3d extremitiesYi[2];
				for (int index = 0; index < 2; index++)
				{
					extremitiesYi[index] = extremitiesY0[index] * (1.0 - j/(m_numNodesPerAxis - 1.0)) +
						extremitiesY1[index] * j / (m_numNodesPerAxis - 1.0);
				}

				m_nodes[i][j].resize(m_numNodesPerAxis);
				for (int k=0; k < m_numNodesPerAxis; k++)
				{
					m_nodes[i][j][k] = extremitiesYi[0] * (1.0 - k / (m_numNodesPerAxis - 1.0)) + extremitiesYi[1]
										* k / (m_numNodesPerAxis - 1.0);
				}
			}
		}
	}

	/// Adds the Fem3D elements of small cubes
	/// \param state	The deformable state for initialization.
	void addFemCubes(std::shared_ptr<DeformableRepresentationState> state)
	{
		for (int i = 0; i < m_numNodesPerAxis - 1; i++)
		{
			for (int j = 0; j < m_numNodesPerAxis - 1; j++)
			{
				for (int k = 0; k < m_numNodesPerAxis - 1; k++)
				{
					std::array<int, 8> cubeNodeIds;
					cubeNodeIds[0] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i;
					cubeNodeIds[1] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i + 1;
					cubeNodeIds[2] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + (j + 1) * m_numNodesPerAxis + i;
					cubeNodeIds[3] = k * (m_numNodesPerAxis * m_numNodesPerAxis) + (j + 1) * m_numNodesPerAxis + i + 1;
					cubeNodeIds[4] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i;
					cubeNodeIds[5] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) + j * m_numNodesPerAxis + i + 1;
					cubeNodeIds[6] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) +
										(j + 1) * m_numNodesPerAxis + i;
					cubeNodeIds[7] = (k + 1) * (m_numNodesPerAxis * m_numNodesPerAxis) +
										(j+1) * m_numNodesPerAxis + i + 1;

					std::array<unsigned int, 8> cube = {
						cubeNodeIds[0], cubeNodeIds[1], cubeNodeIds[3], cubeNodeIds[2],
						cubeNodeIds[4], cubeNodeIds[5], cubeNodeIds[7], cubeNodeIds[6]};

					// Add FemElement3DCube for each cube
					std::shared_ptr<FemElement3DCube> femElement = std::make_shared<FemElement3DCube>(cube, *state);
					femElement->setMassDensity(1250.0);
					femElement->setPoissonRatio(0.499);
					femElement->setYoungModulus(15.3e5);
					femElement->initialize(*state);

					this->addFemElement(femElement);

				}
			}
		}
	}

private:
	typedef std::array<SurgSim::Math::Vector3d, 8> CubeNodesType;

	/// Creates the truth cube nodes
	/// \param size	The size in m of the truth cube.
	CubeNodesType createCube(double size)
	{
		CubeNodesType cubeNodes;
		cubeNodes[0] = Vector3d(-0.5,-0.5,-0.5) * size; cubeNodes[1] = Vector3d(0.5,-0.5,-0.5) * size;
		cubeNodes[2] = Vector3d(-0.5, 0.5,-0.5) * size; cubeNodes[3] = Vector3d( 0.5, 0.5,-0.5) * size;
		cubeNodes[4] = Vector3d(-0.5,-0.5, 0.5) * size; cubeNodes[5] = Vector3d( 0.5,-0.5, 0.5) * size;
		cubeNodes[6] = Vector3d(-0.5, 0.5, 0.5) * size; cubeNodes[7] = Vector3d( 0.5, 0.5, 0.5) * size;

		return cubeNodes;
	}

	// Name of the truth cube representation
	std::string m_name;
	// Size in m of the original truth cube
	double m_size;

	// Level of subdivision
	unsigned int m_levelSubdivision;

	// Number of point per dimensions for each subdivision level
	int m_numNodesPerAxis;

	// Displacement
	std::vector<double> m_displacement;

	// BoundaryCondition
	std::vector<bool> m_boundary;

	// Nodes of the original truth cube
	CubeNodesType m_cubeNodes;

	// Nodes of the subdivision cubes in 3D
	std::vector<std::vector<std::vector<Vector3d>>> m_nodes;
};

}; // namespace Physics
}; // namespace SurgSim

<|endoftext|>


<commit_before>/*
 * Copyright 2019 Centreon (https://www.centreon.com/)
 *
 * 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.
 *
 * For more information : contact@centreon.com
 *
 */

#include "com/centreon/broker/brokerrpc.hh"

#include <gtest/gtest.h>

#include <cstdio>
#include <fstream>
#include <json11.hpp>

#include "com/centreon/broker/log_v2.hh"
#include "com/centreon/broker/version.hh"

using namespace com::centreon;
using namespace com::centreon::broker;

class BrokerRpc : public ::testing::Test {
 public:
  void SetUp() override {}

  void TearDown() override {}

  std::list<std::string> execute(const std::string& command) {
    std::list<std::string> retval;
    char path[1024];
    std::ostringstream oss;
    oss << "test/rpc_client " << command;

    FILE* fp = popen(oss.str().c_str(), "r");
    while (fgets(path, sizeof(path), fp) != nullptr) {
      size_t count = strlen(path);
      if (count > 0)
        --count;
      retval.push_back(std::string(path, count));
    }
    pclose(fp);
    return retval;
  }
};

TEST_F(BrokerRpc, StartStop) {
  brokerrpc brpc("0.0.0.0", 40000, "test");
  ASSERT_NO_THROW(brpc.shutdown());
}

TEST_F(BrokerRpc, GetVersion) {
  std::ostringstream oss;
  oss << "GetVersion: major: " << version::major;
  brokerrpc brpc("0.0.0.0", 40000, "test");
  auto output = execute("GetVersion");
  ASSERT_EQ(output.size(), 3);
  ASSERT_EQ(output.front(), oss.str());
  oss.str("");
  oss << "patch: " << version::patch;
  ASSERT_EQ(output.back(), oss.str());
  brpc.shutdown();
}

TEST_F(BrokerRpc, ConfReloadBad) {
  brokerrpc brpc("0.0.0.0", 40000, "test");
  auto output = execute("DebugConfReload /root/testfail.json");
  ASSERT_EQ(output.size(), 1);
  ASSERT_EQ(output.back(),
            "DebugConfReload failed for file /root/testfail.json : file '/root/testfail.json' does not exist");
  brpc.shutdown();
}

TEST_F(BrokerRpc, ConfReloadOK) {
  json11::Json my_json = json11::Json::object{
      {"console", true}, {"loggers", json11::Json::array{}}};
  std::string output_str;
  my_json.dump(output_str);

  std::remove("/tmp/testok.json");
  std::ofstream conf("/tmp/testok.json");
  conf << output_str;
  conf.close();

  testing::internal::CaptureStdout();

  brokerrpc brpc("0.0.0.0", 40000, "broker");
  auto output = execute("DebugConfReload /tmp/testok.json");
  ASSERT_EQ(output.size(), 1);
  ASSERT_EQ(output.back(), "DebugConfReload OK");
  log_v2::core()->info("test");
  brpc.shutdown();

  std::string log_output = testing::internal::GetCapturedStdout();

  ASSERT_NE(log_output.find("] broker :"), std::string::npos);
  ASSERT_NE(log_output.find("] test"), std::string::npos);

  std::remove("/tmp/testok.json");
}
<commit_msg>fix(test): fix BrokerRpc.GetVersion unit test.<commit_after>/*
 * Copyright 2019 Centreon (https://www.centreon.com/)
 *
 * 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.
 *
 * For more information : contact@centreon.com
 *
 */

#include "com/centreon/broker/brokerrpc.hh"

#include <gtest/gtest.h>

#include <cstdio>
#include <fstream>
#include <json11.hpp>

#include "com/centreon/broker/log_v2.hh"
#include "com/centreon/broker/version.hh"

using namespace com::centreon;
using namespace com::centreon::broker;

class BrokerRpc : public ::testing::Test {
 public:
  void SetUp() override {}

  void TearDown() override {}

  std::list<std::string> execute(const std::string& command) {
    std::list<std::string> retval;
    char path[1024];
    std::ostringstream oss;
    oss << "test/rpc_client " << command;

    FILE* fp = popen(oss.str().c_str(), "r");
    while (fgets(path, sizeof(path), fp) != nullptr) {
      size_t count = strlen(path);
      if (count > 0)
        --count;
      retval.push_back(std::string(path, count));
    }
    pclose(fp);
    return retval;
  }
};

TEST_F(BrokerRpc, StartStop) {
  brokerrpc brpc("0.0.0.0", 40000, "test");
  ASSERT_NO_THROW(brpc.shutdown());
}

TEST_F(BrokerRpc, GetVersion) {
  std::ostringstream oss;
  oss << "GetVersion: major: " << version::major;
  brokerrpc brpc("0.0.0.0", 40000, "test");
  auto output = execute("GetVersion");
#if CENTREON_BROKER_PATCH == 0
  ASSERT_EQ(output.size(), 2);
  ASSERT_EQ(output.front(), oss.str());
  oss.str("");
  oss << "minor: " << version::minor;
  ASSERT_EQ(output.back(), oss.str());
#else
  ASSERT_EQ(output.size(), 3);
  ASSERT_EQ(output.front(), oss.str());
  oss.str("");
  oss << "patch: " << version::patch;
  ASSERT_EQ(output.back(), oss.str());
#endif
  brpc.shutdown();
}

TEST_F(BrokerRpc, ConfReloadBad) {
  brokerrpc brpc("0.0.0.0", 40000, "test");
  auto output = execute("DebugConfReload /root/testfail.json");
  ASSERT_EQ(output.size(), 1);
  ASSERT_EQ(output.back(),
            "DebugConfReload failed for file /root/testfail.json : file '/root/testfail.json' does not exist");
  brpc.shutdown();
}

TEST_F(BrokerRpc, ConfReloadOK) {
  json11::Json my_json = json11::Json::object{
      {"console", true}, {"loggers", json11::Json::array{}}};
  std::string output_str;
  my_json.dump(output_str);

  std::remove("/tmp/testok.json");
  std::ofstream conf("/tmp/testok.json");
  conf << output_str;
  conf.close();

  testing::internal::CaptureStdout();

  brokerrpc brpc("0.0.0.0", 40000, "broker");
  auto output = execute("DebugConfReload /tmp/testok.json");
  ASSERT_EQ(output.size(), 1);
  ASSERT_EQ(output.back(), "DebugConfReload OK");
  log_v2::core()->info("test");
  brpc.shutdown();

  std::string log_output = testing::internal::GetCapturedStdout();

  ASSERT_NE(log_output.find("] broker :"), std::string::npos);
  ASSERT_NE(log_output.find("] test"), std::string::npos);

  std::remove("/tmp/testok.json");
}
<|endoftext|>


<commit_before>/*
 * Android File Transfer for Linux: MTP client for android devices
 * Copyright (C) 2015  Vladimir Menshakov

 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.

 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.

 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 */
#include <stdio.h>
#include <stdexcept>

#include <usb/BulkPipe.h>
#include <usb/Context.h>
#include <mtp/ptp/Container.h>
#include <mtp/ptp/Device.h>
#include <mtp/ptp/Messages.h>

int main(int argc, char **argv)
{
	using namespace mtp;
	//USB_CALL(libusb_reset_device(device->GetHandle()));

	//printf("claiming interface %d...\n", interface->GetIndex());
	//USB_CALL(libusb_claim_interface(device->GetHandle(), interface->GetIndex()));
	//printf("claimed interface\n");
	//USB_CALL(libusb_set_interface_alt_setting(device->GetHandle(), mtp_interface, 0));

	DevicePtr mtp(Device::Find());
	if (!mtp)
	{
		printf("no mtp device found\n");
		return 1;
	}

	msg::DeviceInfo gdi = mtp->GetDeviceInfo();
	printf("%s\n", gdi.VendorExtensionDesc.c_str());
	printf("%s ", gdi.Manufactorer.c_str());
	printf("%s ", gdi.Model.c_str());
	printf("%s ", gdi.DeviceVersion.c_str());
	printf("%s\n", gdi.SerialNumber.c_str());
	printf("supported op codes: ");
	for(u16 code : gdi.OperationsSupported)
	{
		printf("%04x ", (unsigned)code);
	}
	printf("\n");
	printf("supported properties: ");
	for(u16 code : gdi.DevicePropertiesSupported)
	{
		printf("%04x ", (unsigned)code);
	}
	printf("\n");

	if (argc < 2)
		return 0;

	SessionPtr session = mtp->OpenSession(1);
	std::string command = argv[1];
	if (command == "list")
	{
		mtp::u32 parent = mtp::Session::Root;
		if (argc > 2)
			if (sscanf(argv[2], "%x", &parent) != 1)
				return 1;

		msg::ObjectHandles handles = session->GetObjectHandles(mtp::Session::AllStorages, mtp::Session::AllFormats, parent);

		for(u32 objectId : handles.ObjectHandles)
		{
			try
			{
				msg::ObjectInfo info = session->GetObjectInfo(objectId);
				printf("%08x %04x %s %u %ux%u, %s\n", objectId, info.ObjectFormat, info.Filename.c_str(), info.ObjectCompressedSize, info.ImagePixWidth, info.ImagePixHeight, info.CaptureDate.c_str());
			}
			catch(const std::exception &ex)
			{
				printf("error: %s\n", ex.what());
			}
		}
		//libusb_release_interface(device->GetHandle(), interface->GetIndex());
	}
	else if (command == "get")
	{
		if (argc < 3)
			return 1;
		mtp::u32 objectId;
		if (sscanf(argv[2], "%x", &objectId) != 1)
			return 1;
		printf("object id = %08x\n", objectId);
		msg::ObjectInfo info = session->GetObjectInfo(objectId);
		printf("filename = %s\n", info.Filename.c_str());
		FILE *f = fopen(info.Filename.c_str(), "wb");
		if (!f)
		{
			perror("open");
			return 1;
		}
		ByteArray object = session->GetObject(objectId);
		if (fwrite(object.data(), object.size(), 1, f) != 1)
			perror("fwriter");
		fclose(f);
	}
	else if (command == "set")
	{
		if (argc < 4)
			return 1;

		mtp::u32 parentObjectId;
		if (sscanf(argv[2], "%x", &parentObjectId) != 1)
			return 1;

		std::string filename(argv[3]);
		printf("uploading %s to %08x\n", filename.c_str(), parentObjectId);
		FILE *f = fopen(filename.c_str(), "rb");
		if (!f)
		{
			perror("open");
			return 1;
		}
		msg::ObjectInfo oi;
		oi.Filename = filename;
		oi.ObjectFormat = ObjectFormatFromFilename(filename);

		fseek(f, 0, SEEK_END);
		oi.ObjectCompressedSize = ftell(f);
		rewind(f);

		ByteArray data(oi.ObjectCompressedSize);
		if (fread(data.data(), data.size(), 1, f) != 1)
			throw std::runtime_error("read failed");

		fclose(f);

		Session::NewObjectInfo noi = session->SendObjectInfo(oi, 0, parentObjectId);
		printf("new object id = %08x\n", noi.ObjectId);
		session->SendObject(data);
		printf("done\n");
	}
	else if (command == "delete")
	{
		if (argc < 3)
			return 1;

		mtp::u32 objectId;
		if (sscanf(argv[2], "%x", &objectId) != 1)
			return 1;

		printf("object id = %08x\n", objectId);
		session->DeleteObject(objectId);
	}
	else if (command == "mkdir")
	{
		if (argc < 3)
			return 1;

		mtp::u32 parentObjectId = mtp::Session::Root;
		if (argc > 3 && sscanf(argv[3], "%x", &parentObjectId) != 1)
			return 1;

		std::string filename = argv[2];
		msg::ObjectInfo oi;
		oi.Filename = filename;
		oi.ObjectFormat = ObjectFormat::Association;
		session->SendObjectInfo(oi, 0, parentObjectId);
	}
	else if (command == "properties")
	{
		if (argc < 3)
			return 1;

		mtp::u32 objectId;
		if (sscanf(argv[2], "%x", &objectId) != 1)
			return 1;
		msg::ObjectPropsSupported ops = session->GetObjectPropsSupported(objectId);
		printf("properties supported: ");
		for(u16 prop: ops.ObjectPropCodes)
		{
			printf("%02x ", prop);
		}
		printf("\n");
	}

	return 0;
}
<commit_msg>replaced hexadecimal ids with decimal<commit_after>/*
 * Android File Transfer for Linux: MTP client for android devices
 * Copyright (C) 2015  Vladimir Menshakov

 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.

 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.

 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 */
#include <stdio.h>
#include <stdexcept>

#include <usb/BulkPipe.h>
#include <usb/Context.h>
#include <mtp/ptp/Container.h>
#include <mtp/ptp/Device.h>
#include <mtp/ptp/Messages.h>

int main(int argc, char **argv)
{
	using namespace mtp;
	//USB_CALL(libusb_reset_device(device->GetHandle()));

	//printf("claiming interface %d...\n", interface->GetIndex());
	//USB_CALL(libusb_claim_interface(device->GetHandle(), interface->GetIndex()));
	//printf("claimed interface\n");
	//USB_CALL(libusb_set_interface_alt_setting(device->GetHandle(), mtp_interface, 0));

	DevicePtr mtp(Device::Find());
	if (!mtp)
	{
		printf("no mtp device found\n");
		return 1;
	}

	msg::DeviceInfo gdi = mtp->GetDeviceInfo();
	printf("%s\n", gdi.VendorExtensionDesc.c_str());
	printf("%s ", gdi.Manufactorer.c_str());
	printf("%s ", gdi.Model.c_str());
	printf("%s ", gdi.DeviceVersion.c_str());
	printf("%s\n", gdi.SerialNumber.c_str());
	printf("supported op codes: ");
	for(u16 code : gdi.OperationsSupported)
	{
		printf("%04x ", (unsigned)code);
	}
	printf("\n");
	printf("supported properties: ");
	for(u16 code : gdi.DevicePropertiesSupported)
	{
		printf("%04x ", (unsigned)code);
	}
	printf("\n");

	if (argc < 2)
		return 0;

	SessionPtr session = mtp->OpenSession(1);
	std::string command = argv[1];
	if (command == "list")
	{
		mtp::u32 parent = mtp::Session::Root;
		if (argc > 2)
			if (sscanf(argv[2], "%u", &parent) != 1)
				return 1;

		msg::ObjectHandles handles = session->GetObjectHandles(mtp::Session::AllStorages, mtp::Session::AllFormats, parent);

		for(u32 objectId : handles.ObjectHandles)
		{
			try
			{
				msg::ObjectInfo info = session->GetObjectInfo(objectId);
				printf("%-10u %04x %s %u %ux%u, %s\n", objectId, info.ObjectFormat, info.Filename.c_str(), info.ObjectCompressedSize, info.ImagePixWidth, info.ImagePixHeight, info.CaptureDate.c_str());
			}
			catch(const std::exception &ex)
			{
				printf("error: %s\n", ex.what());
			}
		}
		//libusb_release_interface(device->GetHandle(), interface->GetIndex());
	}
	else if (command == "get")
	{
		if (argc < 3)
			return 1;
		mtp::u32 objectId;
		if (sscanf(argv[2], "%u", &objectId) != 1)
			return 1;
		printf("object id = %u\n", objectId);
		msg::ObjectInfo info = session->GetObjectInfo(objectId);
		printf("filename = %s\n", info.Filename.c_str());
		FILE *f = fopen(info.Filename.c_str(), "wb");
		if (!f)
		{
			perror("open");
			return 1;
		}
		ByteArray object = session->GetObject(objectId);
		if (fwrite(object.data(), object.size(), 1, f) != 1)
			perror("fwriter");
		fclose(f);
	}
	else if (command == "set")
	{
		if (argc < 4)
			return 1;

		mtp::u32 parentObjectId;
		if (sscanf(argv[2], "%u", &parentObjectId) != 1)
			return 1;

		std::string filename(argv[3]);
		printf("uploading %s to %u\n", filename.c_str(), parentObjectId);
		FILE *f = fopen(filename.c_str(), "rb");
		if (!f)
		{
			perror("open");
			return 1;
		}
		msg::ObjectInfo oi;
		oi.Filename = filename;
		oi.ObjectFormat = ObjectFormatFromFilename(filename);

		fseek(f, 0, SEEK_END);
		oi.ObjectCompressedSize = ftell(f);
		rewind(f);

		ByteArray data(oi.ObjectCompressedSize);
		if (fread(data.data(), data.size(), 1, f) != 1)
			throw std::runtime_error("read failed");

		fclose(f);

		Session::NewObjectInfo noi = session->SendObjectInfo(oi, 0, parentObjectId);
		printf("new object id = %u\n", noi.ObjectId);
		session->SendObject(data);
		printf("done\n");
	}
	else if (command == "delete")
	{
		if (argc < 3)
			return 1;

		mtp::u32 objectId;
		if (sscanf(argv[2], "%u", &objectId) != 1)
			return 1;

		printf("object id = %u\n", objectId);
		session->DeleteObject(objectId);
	}
	else if (command == "mkdir")
	{
		if (argc < 3)
			return 1;

		mtp::u32 parentObjectId = mtp::Session::Root;
		if (argc > 3 && sscanf(argv[3], "%u", &parentObjectId) != 1)
			return 1;

		std::string filename = argv[2];
		msg::ObjectInfo oi;
		oi.Filename = filename;
		oi.ObjectFormat = ObjectFormat::Association;
		session->SendObjectInfo(oi, 0, parentObjectId);
	}
	else if (command == "properties")
	{
		if (argc < 3)
			return 1;

		mtp::u32 objectId;
		if (sscanf(argv[2], "%u", &objectId) != 1)
			return 1;
		msg::ObjectPropsSupported ops = session->GetObjectPropsSupported(objectId);
		printf("properties supported: ");
		for(u16 prop: ops.ObjectPropCodes)
		{
			printf("%02x ", prop);
		}
		printf("\n");
	}

	return 0;
}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: twolinesitem.hxx,v $
 *
 *  $Revision: 1.3 $
 *
 *  last change: $Author: kz $ $Date: 2007-05-10 14:33:00 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/
#ifndef _SVX_TWOLINESITEM_HXX
#define _SVX_TWOLINESITEM_HXX

#ifndef _SAL_TYPES_H_
#include <sal/types.h>
#endif
#ifndef _SFXPOOLITEM_HXX
#include <svtools/poolitem.hxx>
#endif
#ifndef _SVX_SVXIDS_HRC
#include <svx/svxids.hrc>
#endif

#ifndef INCLUDED_SVXDLLAPI_H
#include "svx/svxdllapi.h"
#endif

class SvXMLUnitConverter;
namespace rtl
{
    class OUString;
}

class SVX_DLLPUBLIC SvxTwoLinesItem : public SfxPoolItem
{
    sal_Unicode cStartBracket, cEndBracket;
    sal_Bool bOn;
public:
    TYPEINFO();
    SvxTwoLinesItem( sal_Bool bOn /*= TRUE*/,
                     sal_Unicode nStartBracket /*= 0*/,
                     sal_Unicode nEndBracket /*= 0*/,
                     sal_uInt16 nId  );
    SvxTwoLinesItem( const SvxTwoLinesItem& rAttr );
    virtual ~SvxTwoLinesItem();

    // "pure virtual Methoden" vom SfxPoolItem
    virtual int             operator==( const SfxPoolItem& ) const;
    virtual SfxPoolItem*    Clone( SfxItemPool* pPool = 0 ) const;
    virtual SfxPoolItem*    Create(SvStream &, USHORT nVer) const;
    virtual SvStream&       Store(SvStream &, USHORT nIVer) const;
    virtual SfxItemPresentation GetPresentation( SfxItemPresentation ePres,
                                    SfxMapUnit eCoreMetric,
                                    SfxMapUnit ePresMetric,
                                    String &rText,
                                    const IntlWrapper* pIntl = 0 ) const;

    virtual sal_Bool        QueryValue( com::sun::star::uno::Any& rVal,
                                        BYTE nMemberId = 0 ) const;
    virtual sal_Bool        PutValue( const com::sun::star::uno::Any& rVal,
                                        BYTE nMemberId = 0 );

    virtual USHORT          GetVersion( USHORT nFFVer ) const;

    SvxTwoLinesItem&        operator=( const SvxTwoLinesItem& rCpy )
    {
        SetValue( rCpy.GetValue() );
        SetStartBracket( rCpy.GetStartBracket() );
        SetEndBracket( rCpy.GetEndBracket() );
        return *this;
    }

    sal_Bool GetValue() const                   { return bOn; }
    void SetValue( sal_Bool bFlag )             { bOn = bFlag; }

    sal_Unicode GetStartBracket() const         { return cStartBracket; }
    void SetStartBracket( sal_Unicode c )       { cStartBracket = c; }

    sal_Unicode GetEndBracket() const           { return cEndBracket; }
    void SetEndBracket( sal_Unicode c )         { cEndBracket = c; }
};

#endif

<commit_msg>INTEGRATION: CWS changefileheader (1.3.446); FILE MERGED 2008/04/01 15:49:40 thb 1.3.446.3: #i85898# Stripping all external header guards 2008/04/01 12:47:01 thb 1.3.446.2: #i85898# Stripping all external header guards 2008/03/31 14:18:21 rt 1.3.446.1: #i87441# Change license header to LPGL v3.<commit_after>/*************************************************************************
 *
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * Copyright 2008 by Sun Microsystems, Inc.
 *
 * OpenOffice.org - a multi-platform office productivity suite
 *
 * $RCSfile: twolinesitem.hxx,v $
 * $Revision: 1.4 $
 *
 * This file is part of OpenOffice.org.
 *
 * OpenOffice.org is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License version 3
 * only, as published by the Free Software Foundation.
 *
 * OpenOffice.org is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License version 3 for more details
 * (a copy is included in the LICENSE file that accompanied this code).
 *
 * You should have received a copy of the GNU Lesser General Public License
 * version 3 along with OpenOffice.org.  If not, see
 * <http://www.openoffice.org/license.html>
 * for a copy of the LGPLv3 License.
 *
 ************************************************************************/
#ifndef _SVX_TWOLINESITEM_HXX
#define _SVX_TWOLINESITEM_HXX

#include <sal/types.h>
#include <svtools/poolitem.hxx>
#ifndef _SVX_SVXIDS_HRC
#include <svx/svxids.hrc>
#endif
#include "svx/svxdllapi.h"

class SvXMLUnitConverter;
namespace rtl
{
    class OUString;
}

class SVX_DLLPUBLIC SvxTwoLinesItem : public SfxPoolItem
{
    sal_Unicode cStartBracket, cEndBracket;
    sal_Bool bOn;
public:
    TYPEINFO();
    SvxTwoLinesItem( sal_Bool bOn /*= TRUE*/,
                     sal_Unicode nStartBracket /*= 0*/,
                     sal_Unicode nEndBracket /*= 0*/,
                     sal_uInt16 nId  );
    SvxTwoLinesItem( const SvxTwoLinesItem& rAttr );
    virtual ~SvxTwoLinesItem();

    // "pure virtual Methoden" vom SfxPoolItem
    virtual int             operator==( const SfxPoolItem& ) const;
    virtual SfxPoolItem*    Clone( SfxItemPool* pPool = 0 ) const;
    virtual SfxPoolItem*    Create(SvStream &, USHORT nVer) const;
    virtual SvStream&       Store(SvStream &, USHORT nIVer) const;
    virtual SfxItemPresentation GetPresentation( SfxItemPresentation ePres,
                                    SfxMapUnit eCoreMetric,
                                    SfxMapUnit ePresMetric,
                                    String &rText,
                                    const IntlWrapper* pIntl = 0 ) const;

    virtual sal_Bool        QueryValue( com::sun::star::uno::Any& rVal,
                                        BYTE nMemberId = 0 ) const;
    virtual sal_Bool        PutValue( const com::sun::star::uno::Any& rVal,
                                        BYTE nMemberId = 0 );

    virtual USHORT          GetVersion( USHORT nFFVer ) const;

    SvxTwoLinesItem&        operator=( const SvxTwoLinesItem& rCpy )
    {
        SetValue( rCpy.GetValue() );
        SetStartBracket( rCpy.GetStartBracket() );
        SetEndBracket( rCpy.GetEndBracket() );
        return *this;
    }

    sal_Bool GetValue() const                   { return bOn; }
    void SetValue( sal_Bool bFlag )             { bOn = bFlag; }

    sal_Unicode GetStartBracket() const         { return cStartBracket; }
    void SetStartBracket( sal_Unicode c )       { cStartBracket = c; }

    sal_Unicode GetEndBracket() const           { return cEndBracket; }
    void SetEndBracket( sal_Unicode c )         { cEndBracket = c; }
};

#endif

<|endoftext|>


<commit_before>#include <stdio.h>
#include <sstream>
#include <stdexcept>

#include <mtp/usb/Context.h>
#include <mtp/usb/call.h>
#include <mtp/ptp/OperationRequest.h>
#include <mtp/ptp/Container.h>

static void callback(struct libusb_transfer *transfer)
{
	printf("CALLBACK, status: %d\n", transfer->status);
	for(int i = 0; i < transfer->actual_length; ++i)
		printf("%02x ", transfer->buffer[i]);
	printf("\n");
}

int main(int argc, char **argv)
{
	using namespace mtp;
	usb::Context ctx;
	usb::DeviceDescriptorPtr desc;
	for (usb::DeviceDescriptorPtr dd : ctx.GetDevices())
	{
		if (dd->GetVendorId() == 0x18d1)
		{
			desc = dd;
			break;
		}
	}
	if (!desc)
		throw std::runtime_error("no mtp device found");

	usb::DevicePtr device = desc->Open();
	int confs = desc->GetConfigurationsCount();
	printf("configurations: %d\n", confs);

	int mtp_configuration = -1;
	int mtp_interface = -1;

	usb::ConfigurationPtr		configuration;
	usb::InterfacePtr			interface;

	for(int i = 0; i < confs; ++i)
	{
		usb::ConfigurationPtr conf = desc->GetConfiguration(i);
		int interfaces = conf->GetInterfaceCount();
		printf("interfaces: %d\n", interfaces);
		for(int j = 0; j < interfaces; ++j)
		{
			usb::InterfacePtr iface = conf->GetInterface(j, 0);
			printf("%d:%d index %u, eps %u\n", i, j, iface->GetIndex(), iface->GetEndpointsCount());
			int name_idx = iface->GetNameIndex();
			if (!name_idx)
				continue;
			std::string name = device->GetString(name_idx);
			if (name == "MTP")
			{
				configuration = conf;
				interface = iface;
				mtp_configuration = i;
				mtp_interface = j;
				i = confs;
				break;
			}
		}
	}

	if (!interface || mtp_interface < 0 || mtp_configuration < 0)
		throw std::runtime_error("no mtp interface found");

	device->SetConfiguration(configuration->GetIndex());
	int epn = interface->GetEndpointsCount();

	usb::EndpointPtr out, in, interrupt;
	printf("endpoints: %d\n", epn);
	for(int i = 0; i < epn; ++i)
	{
		usb::EndpointPtr ep = interface->GetEndpoint(i);
		printf("endpoint: %d: %02x\n", i, ep->GetAddress());
		//check for bulk here
		if (ep->GetDirection() == usb::EndpointDirection::Out)
		{
			if (ep->GetType() == usb::EndpointType::Bulk)
			{
				printf("OUT\n");
				out = ep;
			}
		}
		else
		{
			if (ep->GetType() == usb::EndpointType::Bulk)
			{
				printf("IN\n");
				in = ep;
			}
			else
			{
				printf("INTERRUPT\n");
				interrupt = ep;
			}
		}
	}
	if (!in || !out || !interrupt)
		throw std::runtime_error("invalid endpoint");

	//USB_CALL(libusb_reset_device(device->GetHandle()));

	printf("claiming interface %d...\n", interface->GetIndex());
	USB_CALL(libusb_claim_interface(device->GetHandle(), interface->GetIndex()));
	printf("claimed interface\n");
	USB_CALL(libusb_set_interface_alt_setting(device->GetHandle(), mtp_interface, 0));

	//OperationRequest req(OperationCode::OpenSession, 0, 1);
	OperationRequest req(OperationCode::GetDeviceInfo, 0, 1);
	Container container(req);

	/*
	for(size_t i = 0; i < container.Data.size(); ++i)
		printf("%02x ", container.Data[i]);
	printf("\n");
	*/

	libusb_clear_halt(device->GetHandle(), out->GetAddress());
	libusb_clear_halt(device->GetHandle(), in->GetAddress());

	std::vector<u8> data(in->GetMaxPacketSize());
	//std::vector<u8> data(64);
#if 0
	libusb_transfer *transfer_out = libusb_alloc_transfer(0);
	//transfer_out->flags |= LIBUSB_TRANSFER_ADD_ZERO_PACKET | LIBUSB_TRANSFER_SHORT_NOT_OK;
	printf("data size: %u\n", (unsigned)container.Data.size());
	libusb_fill_bulk_transfer(transfer_out, device->GetHandle(), out->GetAddress(), container.Data.data(), container.Data.size(), &callback, 0, 3000);
	USB_CALL(libusb_submit_transfer(transfer_out));
	{
		ctx.Wait();
		printf("WAIT COMPLETED\n");
	}

	//libusb_free_transfer(transfer_out);
	libusb_transfer *transfer_in = libusb_alloc_transfer(0);
	libusb_fill_bulk_transfer(transfer_in, device->GetHandle(), in->GetAddress(), data.data(), data.size(), &callback, 0, 3000);
	USB_CALL(libusb_submit_transfer(transfer_in));

	{
		ctx.Wait();
		printf("WAIT COMPLETED\n");
	}

#else
	printf("bulk transfer start, endpoint: %02x\n", out->GetAddress());
	int tr = 0;
	int r = libusb_bulk_transfer(device->GetHandle(), out->GetAddress(), container.Data.data(), container.Data.size(), &tr, 1000);
	printf("bulk transfer end %d %d\n", r, tr);
	tr = data.size();
	r = libusb_bulk_transfer(device->GetHandle(), in->GetAddress(), data.data(), data.size(), &tr, 3000);
	//r = libusb_interrupt_transfer(device->GetHandle(), interrupt->GetAddress(), data.data(), data.size(), &tr, 2000);
	printf("bulk transfer end %d %d\n", r, tr);
#endif
	libusb_release_interface(device->GetHandle(), interface->GetIndex());

	return 0;
}
<commit_msg>removed all configuration changes<commit_after>#include <stdio.h>
#include <sstream>
#include <stdexcept>

#include <mtp/usb/Context.h>
#include <mtp/usb/call.h>
#include <mtp/ptp/OperationRequest.h>
#include <mtp/ptp/Container.h>

static void callback(struct libusb_transfer *transfer)
{
	printf("CALLBACK, status: %d\n", transfer->status);
	for(int i = 0; i < transfer->actual_length; ++i)
		printf("%02x ", transfer->buffer[i]);
	printf("\n");
}

int main(int argc, char **argv)
{
	using namespace mtp;
	usb::Context ctx;
	usb::DeviceDescriptorPtr desc;
	for (usb::DeviceDescriptorPtr dd : ctx.GetDevices())
	{
		if (dd->GetVendorId() == 0x18d1)
		{
			desc = dd;
			break;
		}
	}
	if (!desc)
		throw std::runtime_error("no mtp device found");

	usb::DevicePtr device = desc->Open();
	int confs = desc->GetConfigurationsCount();
	printf("configurations: %d\n", confs);

	int mtp_configuration = -1;
	int mtp_interface = -1;

	usb::ConfigurationPtr		configuration;
	usb::InterfacePtr			interface;

	for(int i = 0; i < confs; ++i)
	{
		usb::ConfigurationPtr conf = desc->GetConfiguration(i);
		int interfaces = conf->GetInterfaceCount();
		printf("interfaces: %d\n", interfaces);
		for(int j = 0; j < interfaces; ++j)
		{
			usb::InterfacePtr iface = conf->GetInterface(j, 0);
			printf("%d:%d index %u, eps %u\n", i, j, iface->GetIndex(), iface->GetEndpointsCount());
			int name_idx = iface->GetNameIndex();
			if (!name_idx)
				continue;
			std::string name = device->GetString(name_idx);
			if (name == "MTP")
			{
				configuration = conf;
				interface = iface;
				mtp_configuration = i;
				mtp_interface = j;
				i = confs;
				break;
			}
		}
	}

	if (!interface || mtp_interface < 0 || mtp_configuration < 0)
		throw std::runtime_error("no mtp interface found");

	//device->SetConfiguration(configuration->GetIndex());
	int epn = interface->GetEndpointsCount();

	usb::EndpointPtr out, in, interrupt;
	printf("endpoints: %d\n", epn);
	for(int i = 0; i < epn; ++i)
	{
		usb::EndpointPtr ep = interface->GetEndpoint(i);
		printf("endpoint: %d: %02x\n", i, ep->GetAddress());
		//check for bulk here
		if (ep->GetDirection() == usb::EndpointDirection::Out)
		{
			if (ep->GetType() == usb::EndpointType::Bulk)
			{
				printf("OUT\n");
				out = ep;
			}
		}
		else
		{
			if (ep->GetType() == usb::EndpointType::Bulk)
			{
				printf("IN\n");
				in = ep;
			}
			else
			{
				printf("INTERRUPT\n");
				interrupt = ep;
			}
		}
	}
	if (!in || !out || !interrupt)
		throw std::runtime_error("invalid endpoint");

	//USB_CALL(libusb_reset_device(device->GetHandle()));

	printf("claiming interface %d...\n", interface->GetIndex());
	//USB_CALL(libusb_claim_interface(device->GetHandle(), interface->GetIndex()));
	printf("claimed interface\n");
	//USB_CALL(libusb_set_interface_alt_setting(device->GetHandle(), mtp_interface, 0));

	//OperationRequest req(OperationCode::OpenSession, 0, 1);
	OperationRequest req(OperationCode::GetDeviceInfo, 0, 0);
	Container container(req);

	/*
	for(size_t i = 0; i < container.Data.size(); ++i)
		printf("%02x ", container.Data[i]);
	printf("\n");
	*/

	libusb_clear_halt(device->GetHandle(), out->GetAddress());
	libusb_clear_halt(device->GetHandle(), in->GetAddress());

	std::vector<u8> data(in->GetMaxPacketSize());
	//std::vector<u8> data(64);
#if 0
	libusb_transfer *transfer_out = libusb_alloc_transfer(0);
	//transfer_out->flags |= LIBUSB_TRANSFER_ADD_ZERO_PACKET | LIBUSB_TRANSFER_SHORT_NOT_OK;
	printf("data size: %u\n", (unsigned)container.Data.size());
	libusb_fill_bulk_transfer(transfer_out, device->GetHandle(), out->GetAddress(), container.Data.data(), container.Data.size(), &callback, 0, 3000);
	USB_CALL(libusb_submit_transfer(transfer_out));
	{
		ctx.Wait();
		printf("WAIT COMPLETED\n");
	}

	//libusb_free_transfer(transfer_out);
	libusb_transfer *transfer_in = libusb_alloc_transfer(0);
	libusb_fill_bulk_transfer(transfer_in, device->GetHandle(), in->GetAddress(), data.data(), data.size(), &callback, 0, 3000);
	USB_CALL(libusb_submit_transfer(transfer_in));

	{
		ctx.Wait();
		printf("WAIT COMPLETED\n");
	}

#else
	printf("bulk transfer start, endpoint: %02x\n", out->GetAddress());
	int tr = 0;
	int r = libusb_bulk_transfer(device->GetHandle(), out->GetAddress(), container.Data.data(), container.Data.size(), &tr, 1000);
	printf("bulk transfer end %d %d\n", r, tr);
	tr = data.size();
	r = libusb_bulk_transfer(device->GetHandle(), in->GetAddress(), data.data(), data.size(), &tr, 3000);
	//r = libusb_interrupt_transfer(device->GetHandle(), interrupt->GetAddress(), data.data(), data.size(), &tr, 2000);
	printf("bulk transfer end %d %d\n", r, tr);
#endif
	libusb_release_interface(device->GetHandle(), interface->GetIndex());

	return 0;
}
<|endoftext|>


<commit_before>/*
  Copyright (c) Mario Garcia, under MIT license. Like anyone is going to use this shit anyway...
*/
#ifndef __VIKR_MATRIX_H
#define __VIKR_MATRIX_H

#include <vikr/platform/vikr_api.hpp>
#include <vikr/math/alg/vect.hpp>

namespace vikr {
namespace math {

template<typename _Value = float>
class Matrix2 {
public:
private:
  _Value mat[2][2];
};

template<typename _Value = float >
class Matrix3 {
public:
  Matrix3();
private:
  _Value mat[3][3];
};

template<typename _Value = float>
class Matrix4 {
  VIKR_DISALLOW_COPY_AND_ASSIGN(Matrix4<_Value>);
public:
  VIKR_DEFAULT_MOVE_AND_ASSIGN(Matrix4<_Value>);

  Matrix4(
    Vector4<_Value> &row1,
    Vector4<_Value> &row2,
    Vector4<_Value> &row3,
    Vector4<_Value> &row4)
  {
    mat[0][0] = row1.x; mat[1][0] = row1.y; mat[2][0] = row1.z; mat[3][0] = row1.w;
    mat[0][1] = row2.x; mat[1][1] = row2.y; mat[2][1] = row2.z; mat[3][1] = row2.w;
    mat[0][2] = row3.x; mat[1][2] = row3.y; mat[2][2] = row3.z; mat[3][2] = row3.w;
    mat[0][3] = row4.x; mat[1][3] = row4.y; mat[2][3] = row4.z; mat[3][3] = row4.w;
  }

  /**
    Initialize Column-Major format.
  */
  Matrix4(
    _Value a00, _Value a01, _Value a02, _Value a03,
    _Value a10, _Value a11, _Value a12, _Value a13,
    _Value a20, _Value a21, _Value a22, _Value a23,
    _Value a30, _Value a31, _Value a32, _Value a33)
  {
    mat[0][0] = a00; mat[1][0] = a10; mat[2][0] = a20; mat[3][0] = a30;
    mat[0][1] = a01; mat[1][1] = a11; mat[2][1] = a21; mat[3][1] = a31;
    mat[0][2] = a02; mat[1][2] = a12; mat[2][2] = a22; mat[3][2] = a32;
    mat[0][3] = a03; mat[1][3] = a13; mat[2][3] = a23; mat[3][3] = a33;
  }

  Matrix4 operator+(Matrix4 &mat1) {
    // Matrix Addition without the need of loop sequence.
    Matrix4 mat_sol;
    mat_sol[0][0] = mat[0][0] + mat1[0][0];
    mat_sol[0][1] = mat[0][1] + mat1[0][1];
    mat_sol[0][2] = mat[0][2] + mat1[0][2];
    mat_sol[0][3] = mat[0][3] + mat1[0][3];

    mat_sol[1][0] = mat[1][0] + mat1[1][0];
    mat_sol[1][1] = mat[1][1] + mat1[1][1];
    mat_sol[1][2] = mat[1][2] + mat1[1][2];
    mat_sol[1][3] = mat[1][3] + mat1[1][3];

    mat_sol[2][0] = mat[2][0] + mat1[2][0];
    mat_sol[2][1] = mat[2][1] + mat1[2][1];
    mat_sol[2][2] = mat[2][2] + mat1[2][2];
    mat_sol[2][3] = mat[2][3] + mat1[2][3];

    mat_sol[3][0] = mat[3][0] + mat1[3][0];
    mat_sol[3][1] = mat[3][1] + mat1[3][1];
    mat_sol[3][2] = mat[3][2] + mat1[3][2];
    mat_sol[3][3] = mat[3][3] + mat1[3][3];
    return mat_sol;
  }

  Matrix4 operator-(Matrix4 &mat1) {
    Matrix4 mat_ans;
    mat_ans[0][0] = mat[0][0] - mat1[0][0];
    mat_ans[0][1] = mat[0][1] - mat1[0][1];
    mat_ans[0][2] = mat[0][2] - mat1[0][2];
    mat_ans[0][3] = mat[0][3] - mat1[0][3];

    mat_ans[1][0] = mat[1][0] - mat1[1][0];
    mat_ans[1][1] = mat[1][1] - mat1[1][1];
    mat_ans[1][2] = mat[1][2] - mat1[1][2];
    mat_ans[1][3] = mat[1][3] - mat1[1][3];

    mat_ans[2][0] = mat[2][0] - mat1[2][0];
    mat_ans[2][1] = mat[2][1] - mat1[2][1];
    mat_ans[2][2] = mat[2][2] - mat1[2][2];
    mat_ans[2][3] = mat[2][3] - mat1[2][3];

    mat_ans[3][0] = mat[3][0] - mat1[3][0];
    mat_ans[3][1] = mat[3][1] - mat1[3][1];
    mat_ans[3][2] = mat[3][1] - mat1[3][2];
    mat_ans[3][3] = mat[3][1] - mat1[3][3];
    return mat_ans;
  }

  Matrix4& operator*(Matrix4& matrix) {

  }

  _Value& operator[](unsigned int index) {
    return mat[index];
  }

private:

  // Col-Major matrix.
  // mat[col][row]
  //
  //  example.
  //       0   1   2   3
  //  0  | 1   5   9  13 |     mat[0][0] = 1   mat[1][0] = 5   mat[2][0] = 9    mat[3][0] = 13
  //  1  | 2   6  10  14 |     mat[0][1] = 2   mat[1][1] = 6   mat[2][1] = 10   mat[3][1] = 14
  //  2  | 3   7  11  15 |     mat[0][2] = 3   mat[1][2] = 7   mat[2][2] = 11   mat[3][2] = 15
  //  3  | 4   8  12  16 |     mat[0][3] = 4   mat[1][3] = 8   mat[2][3] = 12   mat[3][3] = 16
  _Value mat[4][4];
};
} // math
} // vikr
#endif // __VIKR_MATRIX_H<commit_msg>shift params for matrix4<commit_after>/*
  Copyright (c) Mario Garcia, under MIT license. Like anyone is going to use this shit anyway...
*/
#ifndef __VIKR_MATRIX_H
#define __VIKR_MATRIX_H

#include <vikr/platform/vikr_api.hpp>
#include <vikr/math/alg/vect.hpp>

namespace vikr {
namespace math {

template<typename _Value = float>
class Matrix2 {
public:
private:
  _Value mat[2][2];
};

template<typename _Value = float >
class Matrix3 {
public:
  Matrix3();
private:
  _Value mat[3][3];
};

template<typename _Value = float>
class Matrix4 {
  VIKR_DISALLOW_COPY_AND_ASSIGN(Matrix4<_Value>);
public:
  VIKR_DEFAULT_MOVE_AND_ASSIGN(Matrix4<_Value>);

  Matrix4(
    Vector4<_Value> &row1,
    Vector4<_Value> &row2,
    Vector4<_Value> &row3,
    Vector4<_Value> &row4)
  {
    mat[0][0] = row1.x; mat[1][0] = row1.y; mat[2][0] = row1.z; mat[3][0] = row1.w;
    mat[0][1] = row2.x; mat[1][1] = row2.y; mat[2][1] = row2.z; mat[3][1] = row2.w;
    mat[0][2] = row3.x; mat[1][2] = row3.y; mat[2][2] = row3.z; mat[3][2] = row3.w;
    mat[0][3] = row4.x; mat[1][3] = row4.y; mat[2][3] = row4.z; mat[3][3] = row4.w;
  }

  /**
    Initialize Column-Major format.
  */
  Matrix4(
    _Value a00, _Value a10, _Value a20, _Value a30,
    _Value a01, _Value a11, _Value a21, _Value a31,
    _Value a02, _Value a12, _Value a22, _Value a32,
    _Value a03, _Value a13, _Value a23, _Value a33)
  {
    mat[0][0] = a00; mat[1][0] = a10; mat[2][0] = a20; mat[3][0] = a30;
    mat[0][1] = a01; mat[1][1] = a11; mat[2][1] = a21; mat[3][1] = a31;
    mat[0][2] = a02; mat[1][2] = a12; mat[2][2] = a22; mat[3][2] = a32;
    mat[0][3] = a03; mat[1][3] = a13; mat[2][3] = a23; mat[3][3] = a33;
  }

  Matrix4 operator+(Matrix4 &mat1) {
    // Matrix Addition without the need of loop sequence.
    Matrix4 mat_sol;
    mat_sol[0][0] = mat[0][0] + mat1[0][0];
    mat_sol[0][1] = mat[0][1] + mat1[0][1];
    mat_sol[0][2] = mat[0][2] + mat1[0][2];
    mat_sol[0][3] = mat[0][3] + mat1[0][3];

    mat_sol[1][0] = mat[1][0] + mat1[1][0];
    mat_sol[1][1] = mat[1][1] + mat1[1][1];
    mat_sol[1][2] = mat[1][2] + mat1[1][2];
    mat_sol[1][3] = mat[1][3] + mat1[1][3];

    mat_sol[2][0] = mat[2][0] + mat1[2][0];
    mat_sol[2][1] = mat[2][1] + mat1[2][1];
    mat_sol[2][2] = mat[2][2] + mat1[2][2];
    mat_sol[2][3] = mat[2][3] + mat1[2][3];

    mat_sol[3][0] = mat[3][0] + mat1[3][0];
    mat_sol[3][1] = mat[3][1] + mat1[3][1];
    mat_sol[3][2] = mat[3][2] + mat1[3][2];
    mat_sol[3][3] = mat[3][3] + mat1[3][3];
    return mat_sol;
  }

  Matrix4 operator-(Matrix4 &mat1) {
    Matrix4 mat_ans;
    mat_ans[0][0] = mat[0][0] - mat1[0][0];
    mat_ans[0][1] = mat[0][1] - mat1[0][1];
    mat_ans[0][2] = mat[0][2] - mat1[0][2];
    mat_ans[0][3] = mat[0][3] - mat1[0][3];

    mat_ans[1][0] = mat[1][0] - mat1[1][0];
    mat_ans[1][1] = mat[1][1] - mat1[1][1];
    mat_ans[1][2] = mat[1][2] - mat1[1][2];
    mat_ans[1][3] = mat[1][3] - mat1[1][3];

    mat_ans[2][0] = mat[2][0] - mat1[2][0];
    mat_ans[2][1] = mat[2][1] - mat1[2][1];
    mat_ans[2][2] = mat[2][2] - mat1[2][2];
    mat_ans[2][3] = mat[2][3] - mat1[2][3];

    mat_ans[3][0] = mat[3][0] - mat1[3][0];
    mat_ans[3][1] = mat[3][1] - mat1[3][1];
    mat_ans[3][2] = mat[3][1] - mat1[3][2];
    mat_ans[3][3] = mat[3][1] - mat1[3][3];
    return mat_ans;
  }

  Matrix4& operator*(Matrix4& matrix) {

  }

  _Value& operator[](unsigned int index) {
    return mat[index];
  }

private:

  // Col-Major matrix.
  // mat[col][row]
  //
  //  example.
  //       0   1   2   3
  //  0  | 1   5   9  13 |     mat[0][0] = 1   mat[1][0] = 5   mat[2][0] = 9    mat[3][0] = 13
  //  1  | 2   6  10  14 |     mat[0][1] = 2   mat[1][1] = 6   mat[2][1] = 10   mat[3][1] = 14
  //  2  | 3   7  11  15 |     mat[0][2] = 3   mat[1][2] = 7   mat[2][2] = 11   mat[3][2] = 15
  //  3  | 4   8  12  16 |     mat[0][3] = 4   mat[1][3] = 8   mat[2][3] = 12   mat[3][3] = 16
  _Value mat[4][4];
};
} // math
} // vikr
#endif // __VIKR_MATRIX_H<|endoftext|>


<commit_before>/*************************************************************************/
/*  fbx_skeleton.cpp                                                     */
/*************************************************************************/
/*                       This file is part of:                           */
/*                           GODOT ENGINE                                */
/*                      https://godotengine.org                          */
/*************************************************************************/
/* Copyright (c) 2007-2021 Juan Linietsky, Ariel Manzur.                 */
/* Copyright (c) 2014-2021 Godot Engine contributors (cf. AUTHORS.md).   */
/*                                                                       */
/* Permission is hereby granted, free of charge, to any person obtaining */
/* a copy of this software and associated documentation files (the       */
/* "Software"), to deal in the Software without restriction, including   */
/* without limitation the rights to use, copy, modify, merge, publish,   */
/* distribute, sublicense, and/or sell copies of the Software, and to    */
/* permit persons to whom the Software is furnished to do so, subject to */
/* the following conditions:                                             */
/*                                                                       */
/* The above copyright notice and this permission notice shall be        */
/* included in all copies or substantial portions of the Software.       */
/*                                                                       */
/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       */
/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    */
/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY  */
/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,  */
/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE     */
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                */
/*************************************************************************/

#include "fbx_skeleton.h"

#include "import_state.h"

#include "tools/import_utils.h"

void FBXSkeleton::init_skeleton(const ImportState &state) {
	int skeleton_bone_count = skeleton_bones.size();

	if (skeleton == nullptr && skeleton_bone_count > 0) {
		skeleton = memnew(Skeleton3D);

		if (fbx_node.is_valid()) {
			// cache skeleton attachment for later during node creation
			// can't be done until after node hierarchy is built
			if (fbx_node->godot_node != state.root) {
				fbx_node->skeleton_node = Ref<FBXSkeleton>(this);
				print_verbose("cached armature skeleton attachment for node " + fbx_node->node_name);
			} else {
				// root node must never be a skeleton to prevent cyclic skeletons from being allowed (skeleton in a skeleton)
				fbx_node->godot_node->add_child(skeleton);
				skeleton->set_owner(state.root_owner);
				skeleton->set_name("Skeleton3D");
				print_verbose("created armature skeleton for root");
			}
		} else {
			memfree(skeleton);
			skeleton = nullptr;
			print_error("[doc] skeleton has no valid node to parent nodes to - erasing");
			skeleton_bones.clear();
			return;
		}
	}

	// Make the bone name uniques.
	for (int x = 0; x < skeleton_bone_count; x++) {
		Ref<FBXBone> bone = skeleton_bones[x];
		if (bone.is_valid()) {
			// Make sure the bone name is unique.
			const String bone_name = bone->bone_name;
			int same_name_count = 0;
			for (int y = x; y < skeleton_bone_count; y++) {
				Ref<FBXBone> other_bone = skeleton_bones[y];
				if (other_bone.is_valid()) {
					if (other_bone->bone_name == bone_name) {
						same_name_count += 1;
						other_bone->bone_name += "_" + itos(same_name_count);
					}
				}
			}
		}
	}

	Map<int, Ref<FBXBone>> bone_map;
	// implement fbx cluster skin logic here this is where it goes
	int bone_count = 0;
	for (int x = 0; x < skeleton_bone_count; x++) {
		Ref<FBXBone> bone = skeleton_bones[x];
		if (bone.is_valid()) {
			skeleton->add_bone(bone->bone_name);
			bone->godot_bone_id = bone_count;
			bone->fbx_skeleton = Ref<FBXSkeleton>(this);
			bone_map.insert(bone_count, bone);
			print_verbose("added bone " + itos(bone->bone_id) + " " + bone->bone_name);
			bone_count++;
		}
	}

	ERR_FAIL_COND_MSG(skeleton->get_bone_count() != bone_count, "Not all bones got added, is the file corrupted?");

	for (Map<int, Ref<FBXBone>>::Element *bone_element = bone_map.front(); bone_element; bone_element = bone_element->next()) {
		const Ref<FBXBone> bone = bone_element->value();
		int bone_index = bone_element->key();
		print_verbose("working on bone: " + itos(bone_index) + " bone name:" + bone->bone_name);

		skeleton->set_bone_rest(bone->godot_bone_id, get_unscaled_transform(bone->node->pivot_transform->LocalTransform, state.scale));

		// lookup parent ID
		if (bone->valid_parent && state.fbx_bone_map.has(bone->parent_bone_id)) {
			Ref<FBXBone> parent_bone = state.fbx_bone_map[bone->parent_bone_id];
			int bone_id = skeleton->find_bone(parent_bone->bone_name);
			if (bone_id != -1) {
				skeleton->set_bone_parent(bone_index, bone_id);
			} else {
				print_error("invalid bone parent: " + parent_bone->bone_name);
			}
		} else {
			if (bone->godot_bone_id != -1) {
				skeleton->set_bone_parent(bone_index, -1); // no parent for this bone
			}
		}
	}
}
<commit_msg>FBX: Fix first bone getting unnecessary '_1' suffix<commit_after>/*************************************************************************/
/*  fbx_skeleton.cpp                                                     */
/*************************************************************************/
/*                       This file is part of:                           */
/*                           GODOT ENGINE                                */
/*                      https://godotengine.org                          */
/*************************************************************************/
/* Copyright (c) 2007-2021 Juan Linietsky, Ariel Manzur.                 */
/* Copyright (c) 2014-2021 Godot Engine contributors (cf. AUTHORS.md).   */
/*                                                                       */
/* Permission is hereby granted, free of charge, to any person obtaining */
/* a copy of this software and associated documentation files (the       */
/* "Software"), to deal in the Software without restriction, including   */
/* without limitation the rights to use, copy, modify, merge, publish,   */
/* distribute, sublicense, and/or sell copies of the Software, and to    */
/* permit persons to whom the Software is furnished to do so, subject to */
/* the following conditions:                                             */
/*                                                                       */
/* The above copyright notice and this permission notice shall be        */
/* included in all copies or substantial portions of the Software.       */
/*                                                                       */
/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       */
/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    */
/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY  */
/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,  */
/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE     */
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                */
/*************************************************************************/

#include "fbx_skeleton.h"

#include "import_state.h"

#include "tools/import_utils.h"

void FBXSkeleton::init_skeleton(const ImportState &state) {
	int skeleton_bone_count = skeleton_bones.size();

	if (skeleton == nullptr && skeleton_bone_count > 0) {
		skeleton = memnew(Skeleton3D);

		if (fbx_node.is_valid()) {
			// cache skeleton attachment for later during node creation
			// can't be done until after node hierarchy is built
			if (fbx_node->godot_node != state.root) {
				fbx_node->skeleton_node = Ref<FBXSkeleton>(this);
				print_verbose("cached armature skeleton attachment for node " + fbx_node->node_name);
			} else {
				// root node must never be a skeleton to prevent cyclic skeletons from being allowed (skeleton in a skeleton)
				fbx_node->godot_node->add_child(skeleton);
				skeleton->set_owner(state.root_owner);
				skeleton->set_name("Skeleton3D");
				print_verbose("created armature skeleton for root");
			}
		} else {
			memfree(skeleton);
			skeleton = nullptr;
			print_error("[doc] skeleton has no valid node to parent nodes to - erasing");
			skeleton_bones.clear();
			return;
		}
	}

	// Make the bone name uniques.
	for (int x = 0; x < skeleton_bone_count; x++) {
		Ref<FBXBone> bone = skeleton_bones[x];
		if (bone.is_valid()) {
			// Make sure the bone name is unique.
			const String bone_name = bone->bone_name;
			int same_name_count = 0;
			for (int y = x + 1; y < skeleton_bone_count; y++) {
				Ref<FBXBone> other_bone = skeleton_bones[y];
				if (other_bone.is_valid()) {
					if (other_bone->bone_name == bone_name) {
						same_name_count += 1;
						other_bone->bone_name += "_" + itos(same_name_count);
					}
				}
			}
		}
	}

	Map<int, Ref<FBXBone>> bone_map;
	// implement fbx cluster skin logic here this is where it goes
	int bone_count = 0;
	for (int x = 0; x < skeleton_bone_count; x++) {
		Ref<FBXBone> bone = skeleton_bones[x];
		if (bone.is_valid()) {
			skeleton->add_bone(bone->bone_name);
			bone->godot_bone_id = bone_count;
			bone->fbx_skeleton = Ref<FBXSkeleton>(this);
			bone_map.insert(bone_count, bone);
			print_verbose("added bone " + itos(bone->bone_id) + " " + bone->bone_name);
			bone_count++;
		}
	}

	ERR_FAIL_COND_MSG(skeleton->get_bone_count() != bone_count, "Not all bones got added, is the file corrupted?");

	for (Map<int, Ref<FBXBone>>::Element *bone_element = bone_map.front(); bone_element; bone_element = bone_element->next()) {
		const Ref<FBXBone> bone = bone_element->value();
		int bone_index = bone_element->key();
		print_verbose("working on bone: " + itos(bone_index) + " bone name:" + bone->bone_name);

		skeleton->set_bone_rest(bone->godot_bone_id, get_unscaled_transform(bone->node->pivot_transform->LocalTransform, state.scale));

		// lookup parent ID
		if (bone->valid_parent && state.fbx_bone_map.has(bone->parent_bone_id)) {
			Ref<FBXBone> parent_bone = state.fbx_bone_map[bone->parent_bone_id];
			int bone_id = skeleton->find_bone(parent_bone->bone_name);
			if (bone_id != -1) {
				skeleton->set_bone_parent(bone_index, bone_id);
			} else {
				print_error("invalid bone parent: " + parent_bone->bone_name);
			}
		} else {
			if (bone->godot_bone_id != -1) {
				skeleton->set_bone_parent(bone_index, -1); // no parent for this bone
			}
		}
	}
}
<|endoftext|>


<commit_before>#include "test.h"
#include "Constants.h"
#include "Configuration.h"
#include "FilesystemInclude.h"
#include "FstreamInclude.h"

TEST(NoConfigurationFile)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  Configuration config;
  ASSERT(config.companyName == "YourCompany");
  ASSERT(config.regenTag == "GENERATED BY CPP-DEPENDENCIES");
  ASSERT(config.versionUsed == CURRENT_VERSION);
  ASSERT(config.cycleColor == "orange");
  ASSERT(config.publicDepColor == "blue");
  ASSERT(config.privateDepColor == "lightblue");
  ASSERT(config.componentLinkLimit == 30);
  ASSERT(config.componentLocLowerLimit == 200);
  ASSERT(config.componentLocUpperLimit == 20000);
  ASSERT(config.fileLocUpperLimit == 2000);
  ASSERT(config.addLibraryAliases.size() == 1);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addExecutableAliases.size() == 1);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);

  filesystem::current_path(curDir);
}

TEST(ReadConfigurationFile)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  streams::ofstream out(CONFIG_FILE);
  out << "versionUsed: 3\n"
      << "companyName: MyCompany\n"
      << "regenTag: MY_REGEN_TAG\n"
      << "cycleColor: brown\n"
      << "publicDepColor: black\n"
      << "privateDepColor: grey\n"
      << "componentLinkLimit: 2\n"
      << "componentLocLowerLimit: 1\n"
      << "componentLocUpperLimit: 123\n"
      << "fileLocUpperLimit: 567\n";
  out.close();

  Configuration config;
  ASSERT(config.companyName == "MyCompany");
  ASSERT(config.regenTag == "MY_REGEN_TAG");
  ASSERT(config.versionUsed == "3");
  ASSERT(config.cycleColor == "brown");
  ASSERT(config.publicDepColor == "black");
  ASSERT(config.privateDepColor == "grey");
  ASSERT(config.componentLinkLimit == 2);
  ASSERT(config.componentLocLowerLimit == 1);
  ASSERT(config.componentLocUpperLimit == 123);
  ASSERT(config.fileLocUpperLimit == 567);
  ASSERT(config.addLibraryAliases.size() == 1);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addExecutableAliases.size() == 1);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);

  filesystem::current_path(curDir);
}

TEST(ReadConfigurationFile_Aliases)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  streams::ofstream out(CONFIG_FILE);
  out << "addLibraryAlias: add_special_library\n"
      << "addLibraryAlias: add_test_lib\n"
      << "addExecutableAlias: add_special_exe\n"
      << "addExecutableAlias: add_test\n";
  out.close();

  Configuration config;
  ASSERT(config.addLibraryAliases.size() == 3);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addLibraryAliases.count("add_special_library") == 1);
  ASSERT(config.addLibraryAliases.count("add_test_lib") == 1);

  ASSERT(config.addExecutableAliases.size() == 3);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);
  ASSERT(config.addExecutableAliases.count("add_special_exe") == 1);
  ASSERT(config.addExecutableAliases.count("add_test") == 1);

  filesystem::current_path(curDir);
}
<commit_msg>Put writing to out file in separate scope.<commit_after>#include "test.h"
#include "Constants.h"
#include "Configuration.h"
#include "FilesystemInclude.h"
#include "FstreamInclude.h"

TEST(NoConfigurationFile)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  Configuration config;
  ASSERT(config.companyName == "YourCompany");
  ASSERT(config.regenTag == "GENERATED BY CPP-DEPENDENCIES");
  ASSERT(config.versionUsed == CURRENT_VERSION);
  ASSERT(config.cycleColor == "orange");
  ASSERT(config.publicDepColor == "blue");
  ASSERT(config.privateDepColor == "lightblue");
  ASSERT(config.componentLinkLimit == 30);
  ASSERT(config.componentLocLowerLimit == 200);
  ASSERT(config.componentLocUpperLimit == 20000);
  ASSERT(config.fileLocUpperLimit == 2000);
  ASSERT(config.addLibraryAliases.size() == 1);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addExecutableAliases.size() == 1);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);

  filesystem::current_path(curDir);
}

TEST(ReadConfigurationFile)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  {
    streams::ofstream out(CONFIG_FILE);
    out << "versionUsed: 3\n"
        << "companyName: MyCompany\n"
        << "regenTag: MY_REGEN_TAG\n"
        << "cycleColor: brown\n"
        << "publicDepColor: black\n"
        << "privateDepColor: grey\n"
        << "componentLinkLimit: 2\n"
        << "componentLocLowerLimit: 1\n"
        << "componentLocUpperLimit: 123\n"
        << "fileLocUpperLimit: 567\n";
  }

  Configuration config;
  ASSERT(config.companyName == "MyCompany");
  ASSERT(config.regenTag == "MY_REGEN_TAG");
  ASSERT(config.versionUsed == "3");
  ASSERT(config.cycleColor == "brown");
  ASSERT(config.publicDepColor == "black");
  ASSERT(config.privateDepColor == "grey");
  ASSERT(config.componentLinkLimit == 2);
  ASSERT(config.componentLocLowerLimit == 1);
  ASSERT(config.componentLocUpperLimit == 123);
  ASSERT(config.fileLocUpperLimit == 567);
  ASSERT(config.addLibraryAliases.size() == 1);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addExecutableAliases.size() == 1);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);

  filesystem::current_path(curDir);
}

TEST(ReadConfigurationFile_Aliases)
{
  const filesystem::path tempDir = filesystem::unique_path(filesystem::temp_directory_path() / "%%%%%-%%%%%");
  ASSERT(filesystem::create_directories(tempDir));
  const filesystem::path curDir = filesystem::current_path();
  filesystem::current_path(tempDir);

  {
    streams::ofstream out(CONFIG_FILE);
    out << "addLibraryAlias: add_special_library\n"
        << "addLibraryAlias: add_test_lib\n"
        << "addExecutableAlias: add_special_exe\n"
        << "addExecutableAlias: add_test\n";
  }

  Configuration config;
  ASSERT(config.addLibraryAliases.size() == 3);
  ASSERT(config.addLibraryAliases.count("add_library") == 1);
  ASSERT(config.addLibraryAliases.count("add_special_library") == 1);
  ASSERT(config.addLibraryAliases.count("add_test_lib") == 1);

  ASSERT(config.addExecutableAliases.size() == 3);
  ASSERT(config.addExecutableAliases.count("add_executable") == 1);
  ASSERT(config.addExecutableAliases.count("add_special_exe") == 1);
  ASSERT(config.addExecutableAliases.count("add_test") == 1);

  filesystem::current_path(curDir);
}
<|endoftext|>


<commit_before>/*
 * Copyright 2014 Matthew Harvey
 *
 * 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 "reporting_command.hpp"
#include "command.hpp"
#include "config.hpp"
#include "csv_list_report_writer.hpp"
#include "csv_summary_report_writer.hpp"
#include "help_line.hpp"
#include "human_list_report_writer.hpp"
#include "human_summary_report_writer.hpp"
#include "list_report_writer.hpp"
#include "placeholder.hpp"
#include "string_utilities.hpp"
#include "summary_report_writer.hpp"
#include "time_log.hpp"
#include <iostream>
#include <memory>
#include <ostream>
#include <string>
#include <vector>

using std::endl;
using std::ostream;
using std::string;
using std::unique_ptr;
using std::vector;

namespace swx
{

ReportingCommand::ReportingCommand
(   string const& p_command_word,
    vector<string> const& p_aliases,
    string const& p_usage_summary,
    vector<HelpLine> const& p_help_line,
    TimeLog& p_time_log
):
    Command(p_command_word, p_aliases, p_usage_summary, p_help_line),
    m_time_log(p_time_log)
{
    add_option
    (   'r',
        "Treat ACTIVITY as a (POSIX extended) regular expression, and include "
            "all activities that match it",
        &m_use_regex
    );
    add_option
    (   'l',
        "Instead of printing a summary, print a date-ordered list of "
            "individual activity stints during the relevant period",
        &m_show_stints
    );
    add_option
    (   'b',
        "In addition to any other information, output the earliest time at "
            "which each activity was conducted during the relevant period (ignored "
            "in list mode)",
        &m_show_beginning
    );
    add_option
    (   'e',
        "Output in a column to the right of any other info, the latest time at "
            "which each activity was conducted during the relevant period (ignored "
            "in list mode)",
        &m_show_end
    );
    add_option
    (   'c',
        "Output in CSV format",
        &m_produce_csv
    );
    add_option
    (   'v',
        "Instead of printing the summary in \"tree\" form, print the full name of "\
            "each activity (ignored in list mode or succinct mode)",
        &m_be_verbose
    );
    add_option
    (   's',
        "Succinct output: show grand total only (ignored in list mode)",
        &m_be_succinct
    );
}

ReportingCommand::~ReportingCommand() = default;

ostream&
ReportingCommand::print_report
(   ostream& p_os,
    Config const& p_config,
    vector<string> const& p_activity_components,
    TimePoint const* p_begin,
    TimePoint const* p_end
)
{
    unique_ptr<string> activity_ptr;
    if (!p_activity_components.empty())
    {
        auto const expanded = expand_placeholders(p_activity_components, m_time_log);
        activity_ptr.reset(new string(squish(expanded.begin(), expanded.end())));
    }
    auto const stints =
        m_time_log.get_stints(activity_ptr.get(), p_begin, p_end, m_use_regex);
    ReportWriter::Options const options
    (   p_config.output_rounding_numerator(),
        p_config.output_rounding_denominator(),
        p_config.output_precision(),
        p_config.output_width(),
        p_config.formatted_buf_len(),
        p_config.time_format()
    );
    unique_ptr<ReportWriter> report_writer;
    if (m_show_stints)
    {
        if (m_produce_csv)
        {
            report_writer.reset(new CsvListReportWriter(stints, options));
        }
        else
        {
            report_writer.reset(new HumanListReportWriter(stints, options));
        }
    }
    else
    {
        if (m_produce_csv)
        {
            report_writer.reset
            (   new CsvSummaryReportWriter
                (   stints,
                    options,
                    m_show_beginning,
                    m_show_end,
                    m_be_succinct
                )
            );
        }
        else
        {
            report_writer.reset
            (   new HumanSummaryReportWriter
                (   stints,
                    options,
                    m_show_beginning,
                    m_show_end,
                    !m_be_verbose,
                    m_be_succinct
                )
            );
        }
    }
    report_writer->write(p_os);
    return p_os;
}

bool
ReportingCommand::does_support_placeholders() const
{
    return true;
}

}  // namespace swx
<commit_msg>Fix behaviour of -v option to reporting commands.<commit_after>/*
 * Copyright 2014 Matthew Harvey
 *
 * 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 "reporting_command.hpp"
#include "command.hpp"
#include "config.hpp"
#include "csv_list_report_writer.hpp"
#include "csv_summary_report_writer.hpp"
#include "help_line.hpp"
#include "human_list_report_writer.hpp"
#include "human_summary_report_writer.hpp"
#include "list_report_writer.hpp"
#include "placeholder.hpp"
#include "string_utilities.hpp"
#include "summary_report_writer.hpp"
#include "time_log.hpp"
#include <iostream>
#include <memory>
#include <ostream>
#include <string>
#include <vector>

using std::endl;
using std::ostream;
using std::string;
using std::unique_ptr;
using std::vector;

namespace swx
{

ReportingCommand::ReportingCommand
(   string const& p_command_word,
    vector<string> const& p_aliases,
    string const& p_usage_summary,
    vector<HelpLine> const& p_help_line,
    TimeLog& p_time_log
):
    Command(p_command_word, p_aliases, p_usage_summary, p_help_line),
    m_time_log(p_time_log)
{
    add_option
    (   'r',
        "Treat ACTIVITY as a (POSIX extended) regular expression, and include "
            "all activities that match it",
        &m_use_regex
    );
    add_option
    (   'l',
        "Instead of printing a summary, print a date-ordered list of "
            "individual activity stints during the relevant period",
        &m_show_stints
    );
    add_option
    (   'b',
        "In addition to any other information, output the earliest time at "
            "which each activity was conducted during the relevant period (ignored "
            "in list mode)",
        &m_show_beginning
    );
    add_option
    (   'e',
        "Output in a column to the right of any other info, the latest time at "
            "which each activity was conducted during the relevant period (ignored "
            "in list mode)",
        &m_show_end
    );
    add_option
    (   'c',
        "Output in CSV format",
        &m_produce_csv
    );
    add_option
    (   'v',
        "Instead of printing the summary in \"tree\" form, print the full name of "\
            "each activity (ignored in list mode or succinct mode)",
        &m_be_verbose
    );
    add_option
    (   's',
        "Succinct output: show grand total only (ignored in list mode)",
        &m_be_succinct
    );
}

ReportingCommand::~ReportingCommand() = default;

ostream&
ReportingCommand::print_report
(   ostream& p_os,
    Config const& p_config,
    vector<string> const& p_activity_components,
    TimePoint const* p_begin,
    TimePoint const* p_end
)
{
    unique_ptr<string> activity_ptr;
    if (!p_activity_components.empty())
    {
        auto const expanded = expand_placeholders(p_activity_components, m_time_log);
        activity_ptr.reset(new string(squish(expanded.begin(), expanded.end())));
    }
    auto const stints =
        m_time_log.get_stints(activity_ptr.get(), p_begin, p_end, m_use_regex);
    ReportWriter::Options const options
    (   p_config.output_rounding_numerator(),
        p_config.output_rounding_denominator(),
        p_config.output_precision(),
        p_config.output_width(),
        p_config.formatted_buf_len(),
        p_config.time_format()
    );
    unique_ptr<ReportWriter> report_writer;
    if (m_show_stints)
    {
        if (m_produce_csv)
        {
            report_writer.reset(new CsvListReportWriter(stints, options));
        }
        else
        {
            report_writer.reset(new HumanListReportWriter(stints, options));
        }
    }
    else
    {
        if (m_produce_csv)
        {
            report_writer.reset
            (   new CsvSummaryReportWriter
                (   stints,
                    options,
                    m_show_beginning,
                    m_show_end,
                    m_be_succinct
                )
            );
        }
        else
        {
            report_writer.reset
            (   new HumanSummaryReportWriter
                (   stints,
                    options,
                    m_show_beginning,
                    m_show_end,
                    m_be_verbose,
                    m_be_succinct
                )
            );
        }
    }
    report_writer->write(p_os);
    return p_os;
}

bool
ReportingCommand::does_support_placeholders() const
{
    return true;
}

}  // namespace swx
<|endoftext|>