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

#include "native_client/src/shared/ppapi_proxy/browser_ppp_input_event.h"

#include "native_client/src/include/nacl_scoped_ptr.h"
#include "native_client/src/include/portability.h"
#include "native_client/src/shared/ppapi_proxy/browser_globals.h"
#include "native_client/src/shared/ppapi_proxy/input_event_data.h"
#include "native_client/src/shared/ppapi_proxy/object_serialize.h"
#include "native_client/src/shared/ppapi_proxy/browser_ppp.h"
#include "native_client/src/shared/ppapi_proxy/trusted/srpcgen/ppp_rpc.h"
#include "native_client/src/shared/ppapi_proxy/utility.h"
#include "ppapi/c/pp_resource.h"
#include "ppapi/c/ppp_input_event.h"

namespace ppapi_proxy {

namespace {

PP_Bool HandleInputEvent(PP_Instance instance, PP_Resource input_event) {
  DebugPrintf("PPP_InputEvent::HandleInputEvent: instance=%"NACL_PRIu32", "
              "input_event = %"NACL_PRIu32"\n",
              instance, input_event);

  PP_Var character_text = PP_MakeUndefined();
  InputEventData data;
  data.event_type = PPBInputEventInterface()->GetType(input_event);
  data.event_time_stamp = PPBInputEventInterface()->GetTimeStamp(input_event);
  data.event_modifiers = PPBInputEventInterface()->GetModifiers(input_event);

  switch (data.event_type) {
    // These events all use the PPB_MouseInputEvent interface.
    case PP_INPUTEVENT_TYPE_MOUSEDOWN:
    case PP_INPUTEVENT_TYPE_MOUSEUP:
    case PP_INPUTEVENT_TYPE_MOUSEENTER:
    case PP_INPUTEVENT_TYPE_MOUSELEAVE:
    case PP_INPUTEVENT_TYPE_MOUSEMOVE:
    case PP_INPUTEVENT_TYPE_CONTEXTMENU:
      data.mouse_button =
          PPBMouseInputEventInterface()->GetButton(input_event);
      data.mouse_position =
          PPBMouseInputEventInterface()->GetPosition(input_event);
      data.mouse_click_count =
          PPBMouseInputEventInterface()->GetClickCount(input_event);
      data.mouse_movement =
          PPBMouseInputEventInterface()->GetMovement(input_event);
      break;
    // This event uses the PPB_WheelInputEvent interface.
    case PP_INPUTEVENT_TYPE_WHEEL:
      data.wheel_delta =
          PPBWheelInputEventInterface()->GetDelta(input_event);
      data.wheel_ticks =
          PPBWheelInputEventInterface()->GetTicks(input_event);
      data.wheel_scroll_by_page =
          PPBWheelInputEventInterface()->GetScrollByPage(input_event);
      break;
    // These events all use the PPB_KeyInputEvent interface.
    case PP_INPUTEVENT_TYPE_RAWKEYDOWN:
    case PP_INPUTEVENT_TYPE_KEYDOWN:
    case PP_INPUTEVENT_TYPE_KEYUP:
    case PP_INPUTEVENT_TYPE_CHAR:
      data.key_code =
          PPBKeyboardInputEventInterface()->GetKeyCode(input_event);
      character_text =
          PPBKeyboardInputEventInterface()->GetCharacterText(input_event);
      break;
    case PP_INPUTEVENT_TYPE_UNDEFINED:
      return PP_FALSE;
    // No default case; if any new types are added we should get a compile
    // warning.
  }
  // Now data and character_text have all the data we want to send to the
  // untrusted side.

  // character_text should either be undefined or a string type.
  DCHECK((character_text.type == PP_VARTYPE_UNDEFINED) ||
         (character_text.type == PP_VARTYPE_STRING));
  // Serialize the character_text Var.
  uint32_t text_size = kMaxVarSize;
  nacl::scoped_array<char> text_bytes(Serialize(&character_text, 1,
                                                &text_size));
  int32_t handled;
  NaClSrpcError srpc_result =
      PppInputEventRpcClient::PPP_InputEvent_HandleInputEvent(
          GetMainSrpcChannel(instance),
          instance,
          input_event,
          sizeof(data),
          reinterpret_cast<char*>(&data),
          text_size,
          text_bytes.get(),
          &handled);
  DebugPrintf("PPP_Instance::HandleInputEvent: %s\n",
              NaClSrpcErrorString(srpc_result));
  if (srpc_result != NACL_SRPC_RESULT_OK) {
    return PP_FALSE;
  }
  // The 'handled' int should only ever have a value matching one of PP_FALSE
  // or PP_TRUE. Otherwise, there's an error in the proxy.
  DCHECK((handled == static_cast<int32_t>(PP_FALSE) ||
         (handled == static_cast<int32_t>(PP_TRUE))));
  PP_Bool handled_bool = static_cast<PP_Bool>(handled);
  return handled_bool;
}

}  // namespace

const PPP_InputEvent* BrowserInputEvent::GetInterface() {
  static const PPP_InputEvent input_event_interface = {
    HandleInputEvent
  };
  return &input_event_interface;
}

}  // namespace ppapi_proxy
<commit_msg>Add new input event enums for deps roll BUG= none TEST= existing test suites Review URL: http://codereview.chromium.org/7925019<commit_after>// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "native_client/src/shared/ppapi_proxy/browser_ppp_input_event.h"

#include "native_client/src/include/nacl_scoped_ptr.h"
#include "native_client/src/include/portability.h"
#include "native_client/src/shared/ppapi_proxy/browser_globals.h"
#include "native_client/src/shared/ppapi_proxy/input_event_data.h"
#include "native_client/src/shared/ppapi_proxy/object_serialize.h"
#include "native_client/src/shared/ppapi_proxy/browser_ppp.h"
#include "native_client/src/shared/ppapi_proxy/trusted/srpcgen/ppp_rpc.h"
#include "native_client/src/shared/ppapi_proxy/utility.h"
#include "ppapi/c/pp_resource.h"
#include "ppapi/c/ppp_input_event.h"

namespace ppapi_proxy {

namespace {

PP_Bool HandleInputEvent(PP_Instance instance, PP_Resource input_event) {
  DebugPrintf("PPP_InputEvent::HandleInputEvent: instance=%"NACL_PRIu32", "
              "input_event = %"NACL_PRIu32"\n",
              instance, input_event);

  PP_Var character_text = PP_MakeUndefined();
  InputEventData data;
  data.event_type = PPBInputEventInterface()->GetType(input_event);
  data.event_time_stamp = PPBInputEventInterface()->GetTimeStamp(input_event);
  data.event_modifiers = PPBInputEventInterface()->GetModifiers(input_event);

  switch (data.event_type) {
    // These events all use the PPB_MouseInputEvent interface.
    case PP_INPUTEVENT_TYPE_MOUSEDOWN:
    case PP_INPUTEVENT_TYPE_MOUSEUP:
    case PP_INPUTEVENT_TYPE_MOUSEENTER:
    case PP_INPUTEVENT_TYPE_MOUSELEAVE:
    case PP_INPUTEVENT_TYPE_MOUSEMOVE:
    case PP_INPUTEVENT_TYPE_CONTEXTMENU:
      data.mouse_button =
          PPBMouseInputEventInterface()->GetButton(input_event);
      data.mouse_position =
          PPBMouseInputEventInterface()->GetPosition(input_event);
      data.mouse_click_count =
          PPBMouseInputEventInterface()->GetClickCount(input_event);
      data.mouse_movement =
          PPBMouseInputEventInterface()->GetMovement(input_event);
      break;
    // This event uses the PPB_WheelInputEvent interface.
    case PP_INPUTEVENT_TYPE_WHEEL:
      data.wheel_delta =
          PPBWheelInputEventInterface()->GetDelta(input_event);
      data.wheel_ticks =
          PPBWheelInputEventInterface()->GetTicks(input_event);
      data.wheel_scroll_by_page =
          PPBWheelInputEventInterface()->GetScrollByPage(input_event);
      break;
    // These events all use the PPB_KeyInputEvent interface.
    case PP_INPUTEVENT_TYPE_RAWKEYDOWN:
    case PP_INPUTEVENT_TYPE_KEYDOWN:
    case PP_INPUTEVENT_TYPE_KEYUP:
    case PP_INPUTEVENT_TYPE_CHAR:
      data.key_code =
          PPBKeyboardInputEventInterface()->GetKeyCode(input_event);
      character_text =
          PPBKeyboardInputEventInterface()->GetCharacterText(input_event);
      break;
    case PP_INPUTEVENT_TYPE_UNDEFINED:
      return PP_FALSE;
    // TODO(nfullagar): Implement support for event types below.
    case PP_INPUTEVENT_TYPE_COMPOSITION_START:
    case PP_INPUTEVENT_TYPE_COMPOSITION_UPDATE:
    case PP_INPUTEVENT_TYPE_COMPOSITION_END:
    case PP_INPUTEVENT_TYPE_IME_TEXT:
      DebugPrintf("   No implementation for event type %d\n",
          data.event_type);
      return PP_FALSE;
    // No default case; if any new types are added we should get a compile
    // warning.
  }
  // Now data and character_text have all the data we want to send to the
  // untrusted side.

  // character_text should either be undefined or a string type.
  DCHECK((character_text.type == PP_VARTYPE_UNDEFINED) ||
         (character_text.type == PP_VARTYPE_STRING));
  // Serialize the character_text Var.
  uint32_t text_size = kMaxVarSize;
  nacl::scoped_array<char> text_bytes(Serialize(&character_text, 1,
                                                &text_size));
  int32_t handled;
  NaClSrpcError srpc_result =
      PppInputEventRpcClient::PPP_InputEvent_HandleInputEvent(
          GetMainSrpcChannel(instance),
          instance,
          input_event,
          sizeof(data),
          reinterpret_cast<char*>(&data),
          text_size,
          text_bytes.get(),
          &handled);
  DebugPrintf("PPP_Instance::HandleInputEvent: %s\n",
              NaClSrpcErrorString(srpc_result));
  if (srpc_result != NACL_SRPC_RESULT_OK) {
    return PP_FALSE;
  }
  // The 'handled' int should only ever have a value matching one of PP_FALSE
  // or PP_TRUE. Otherwise, there's an error in the proxy.
  DCHECK((handled == static_cast<int32_t>(PP_FALSE) ||
         (handled == static_cast<int32_t>(PP_TRUE))));
  PP_Bool handled_bool = static_cast<PP_Bool>(handled);
  return handled_bool;
}

}  // namespace

const PPP_InputEvent* BrowserInputEvent::GetInterface() {
  static const PPP_InputEvent input_event_interface = {
    HandleInputEvent
  };
  return &input_event_interface;
}

}  // namespace ppapi_proxy
<|endoftext|>


<commit_before>/*
 * Copyright 2014 National ICT Australia Limited (NICTA)
 *
 * 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 <madopt/ipopt_model.hpp>
//#include <madopt/bonmin_model.hpp>
#include <vector>
using namespace std;

int main(){
    int N = pow(10, 4);

    //create IpoptModel
    MadOpt::IpoptModel m;

    //create BonminModel
    //MadOpt::BonminModel m;

    // Options
    //
    //
    //m.setIntegerOption("print_level", 5);
    //m.setStringOption("print_timing_statistics", "yes");
    //m.setStringOption("hessian_approximation", "limited-memory");

    // shortcut flags
    // set flag if solver output should be printed
    m.show_solver = true;
    // timelimit, a negative value disables the time limit
    m.timelimit = 12;

    // Variables
    //
    //
    // create continuous variable x
    // lower bound = -1.5
    // upper bound = 0
    // initial value = -0.5
    // MadOpt::Var x = m.addVar(-1.5, 0, -0.5, "x");

    // to set a bound to infinity use MadOpt::INF
    // MadOpt::Var v = m.addVar(MadOpt::INF, 0, -0.5, "v");

    // create integer variable y
    // lower bound = 1
    // upper bound = 10
    // initial value = 4
    // MadOpt::Var y = m.addIVar(1, 10, 4, "y");

    // create binary variable z
    // initial value = 1
    // MadOpt::Var z = m.addBVar(1, "z");

    vector<MadOpt::Var> x(N);
    for (int i=0; i<N; i++){
        x[i] = m.addVar(-1.5, 0, -0.5, "x" + to_string(i));
    }

    // Parameters
    //
    //
    // create Parameter
    // value = 1
    // name = p
    // MadOpt::Param p = m.addParam(1, "p");
    vector<MadOpt::Param> p(N-2);
    for (int i=0; i<N-2; i++){
        double a = double(i+2)/(double)N;
        p[i] = m.addParam(a, "p"+to_string(i));
    }

    // Constraints
    //
    //
    // expr = expression build from constants, variables MadOpt::Var, parameters MadOpt::Param
    // lb = lower bound, double
    // ub = upper bound, double
    //
    // add constraint of type:
    //
    // lb <= expr <= ub
    // m.addConstr(lb, expr, ub);
    //
    // lb <= expr <= INF
    // m.addConstr(lb, expr);
    //
    // INF <= expr <= ub
    // m.addConstr(expr, ub);
    //
    // expr == eq
    // m.addEqConstr(expr, eq);

    vector<MadOpt::Constraint> c(N-2);
    for (int i=0; i<N-2; i++){
        c[i] = m.addEqConstr((MadOpt::pow(x[i+1], 2) + 1.5*x[i+1] - p[i])*MadOpt::cos(x[i+2]) - x[i], 0);
    }

    // Objective
    //
    //
    MadOpt::Expr obj(0);
    for (int i=0; i<N; i++)
        obj += MadOpt::pow(x[i] - 1, 2);

    // set objective
    m.setObj(obj);

    // calling the solver
    //
    //
    m.solve();

    // check if a solution exists, or in other words if the solver succeeded
    //
    //
    if (m.hasSolution()){

        // access objective value
        cout<<"Objective:"<<m.objValue()<<endl;

        // access solver status == Ipopt status values
        cout<<"Solver status:"<<m.status()<<endl;

        //print solution value of first variable
        cout<<"Solution value for x0:"<<x[0].x()<<endl;

        //print lambda value of constraint, only available for IpoptModel
        cout<<"Lambda value of constraint 0:"<<c[0].lam()<<endl;
    }

    //changing the model
    //
    //
    // Variables
    //change variable bounds and initial value
    x[1].lb(-12);
    x[1].ub(1);
    x[1].init(0);
    //access bounds and initial values
    cout<<"Variable values: lb="<<x[1].lb()<<" ub="<<x[1].ub()<<" init="<<x[1].init()<<endl;

    //Constraints
    //change constraint bounds
    c[0].lb(-1);
    c[0].ub(2);
    //access bounds
    cout<<"Constraint bounds: lb="<<c[0].lb()<<" ub="<<c[0].ub()<<endl;

    //Parameter
    // change value
    p[0].value(12);
    // access value
    cout<<"Parameter value:"<<p[0].value()<<endl;

    // resolve
    //
    //
    // set solution as initial values
    m.solAsInit();

    m.show_solver = false;
    m.solve();
    if (not m.hasSolution())
        cout<<"no solution"<<endl;
    // test for specific solver status
    if (m.status()==MadOpt::Solution::LOCAL_INFEASIBILITY)
        cout<<"Infeasible"<<endl;

    return 0;
}
<commit_msg>fixed bug in example<commit_after>/*
 * Copyright 2014 National ICT Australia Limited (NICTA)
 *
 * 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 <madopt/ipopt_model.hpp>
//#include <madopt/bonmin_model.hpp>
#include <vector>
#include <math.h>
using namespace std;

int main(){
    int N = pow(10, 4);

    //create IpoptModel
    MadOpt::IpoptModel m;

    //create BonminModel
    //MadOpt::BonminModel m;

    // Options
    //
    //
    //m.setIntegerOption("print_level", 5);
    //m.setStringOption("print_timing_statistics", "yes");
    //m.setStringOption("hessian_approximation", "limited-memory");

    // shortcut flags
    // set flag if solver output should be printed
    m.show_solver = true;
    // timelimit, a negative value disables the time limit
    m.timelimit = 12;

    // Variables
    //
    //
    // create continuous variable x
    // lower bound = -1.5
    // upper bound = 0
    // initial value = -0.5
    // MadOpt::Var x = m.addVar(-1.5, 0, -0.5, "x");

    // to set a bound to infinity use MadOpt::INF
    // MadOpt::Var v = m.addVar(MadOpt::INF, 0, -0.5, "v");

    // create integer variable y
    // lower bound = 1
    // upper bound = 10
    // initial value = 4
    // MadOpt::Var y = m.addIVar(1, 10, 4, "y");

    // create binary variable z
    // initial value = 1
    // MadOpt::Var z = m.addBVar(1, "z");

    vector<MadOpt::Var> x(N);
    for (int i=0; i<N; i++){
        x[i] = m.addVar(-1.5, 0, -0.5, "x" + to_string(i));
    }

    // Parameters
    //
    //
    // create Parameter
    // value = 1
    // name = p
    // MadOpt::Param p = m.addParam(1, "p");
    vector<MadOpt::Param> p(N-2);
    for (int i=0; i<N-2; i++){
        double a = double(i+2)/(double)N;
        p[i] = m.addParam(a, "p"+to_string(i));
    }

    // Constraints
    //
    //
    // expr = expression build from constants, variables MadOpt::Var, parameters MadOpt::Param
    // lb = lower bound, double
    // ub = upper bound, double
    //
    // add constraint of type:
    //
    // lb <= expr <= ub
    // m.addConstr(lb, expr, ub);
    //
    // lb <= expr <= INF
    // m.addConstr(lb, expr);
    //
    // INF <= expr <= ub
    // m.addConstr(expr, ub);
    //
    // expr == eq
    // m.addEqConstr(expr, eq);

    vector<MadOpt::Constraint> c(N-2);
    for (int i=0; i<N-2; i++){
        c[i] = m.addEqConstr((MadOpt::pow(x[i+1], 2) + 1.5*x[i+1] - p[i])*MadOpt::cos(x[i+2]) - x[i], 0);
    }

    // Objective
    //
    //
    MadOpt::Expr obj(0);
    for (int i=0; i<N; i++)
        obj += MadOpt::pow(x[i] - 1, 2);

    // set objective
    m.setObj(obj);

    // calling the solver
    //
    //
    m.solve();

    // check if a solution exists, or in other words if the solver succeeded
    //
    //
    if (m.hasSolution()){

        // access objective value
        cout<<"Objective:"<<m.objValue()<<endl;

        // access solver status == Ipopt status values
        cout<<"Solver status:"<<m.status()<<endl;

        //print solution value of first variable
        cout<<"Solution value for x0:"<<x[0].x()<<endl;

        //print lambda value of constraint, only available for IpoptModel
        cout<<"Lambda value of constraint 0:"<<c[0].lam()<<endl;
    }

    //changing the model
    //
    //
    // Variables
    //change variable bounds and initial value
    x[1].lb(-12);
    x[1].ub(1);
    x[1].init(0);
    //access bounds and initial values
    cout<<"Variable values: lb="<<x[1].lb()<<" ub="<<x[1].ub()<<" init="<<x[1].init()<<endl;

    //Constraints
    //change constraint bounds
    c[0].lb(-1);
    c[0].ub(2);
    //access bounds
    cout<<"Constraint bounds: lb="<<c[0].lb()<<" ub="<<c[0].ub()<<endl;

    //Parameter
    // change value
    p[0].value(12);
    // access value
    cout<<"Parameter value:"<<p[0].value()<<endl;

    // resolve
    //
    //
    // set solution as initial values
    m.solAsInit();

    m.show_solver = false;
    m.solve();
    if (not m.hasSolution())
        cout<<"no solution"<<endl;
    // test for specific solver status
    if (m.status()==MadOpt::Solution::LOCAL_INFEASIBILITY)
        cout<<"Infeasible"<<endl;

    return 0;
}
<|endoftext|>


<commit_before>//
// Name:	 canvas.cpp
// Purpose:	 Implements the canvas class for a wxWindows application.
//
// Copyright (c) 2001 Virtual Terrain Project
// Free for all uses, see license.txt for details.
//

// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"

#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif

// Header for the vtlib library
#include "vtlib/vtlib.h"

#include "canvas.h"
#include "frame.h"
#include "app.h"

DECLARE_APP(vtApp);

/*
 * vtGLCanvas implementation
 */
BEGIN_EVENT_TABLE(vtGLCanvas, wxGLCanvas)
EVT_SIZE(vtGLCanvas::OnSize)
EVT_PAINT(vtGLCanvas::OnPaint)
EVT_CHAR(vtGLCanvas::OnChar)
EVT_MOUSE_EVENTS(vtGLCanvas::OnMouseEvent)
EVT_ERASE_BACKGROUND(vtGLCanvas::OnEraseBackground)
END_EVENT_TABLE()

vtGLCanvas::vtGLCanvas(wxWindow *parent, wxWindowID id,
	const wxPoint& pos, const wxSize& size, long style, const wxString& name, int* gl_attrib):
wxGLCanvas(parent, id, pos, size, style, name, gl_attrib)
{
	parent->Show(TRUE);
	SetCurrent();

	m_bPainting = false;
	m_bRunning = true;
	QueueRefresh(FALSE);
}

vtGLCanvas::~vtGLCanvas(void)
{
}

void vtGLCanvas::QueueRefresh(bool eraseBackground)
	// A Refresh routine we can call from inside OnPaint.
	//   (queues the events rather than dispatching them immediately).
{
#if !WIN32
	// With wxGTK, you can't do a Refresh() in OnPaint because it doesn't
	//   queue (post) a Refresh event for later.  Rather it dispatches
	//   (processes) the underlying events immediately via ProcessEvent
	//   (read, recursive call).  See the wxPostEvent docs and Refresh code
	//   for more details.
	if ( eraseBackground )
	{
		wxEraseEvent eevent( GetId() );
		eevent.SetEventObject( this );
		wxPostEvent( GetEventHandler(), eevent );
	}

	wxPaintEvent event( GetId() );
	event.SetEventObject( this );
	wxPostEvent( GetEventHandler(), event );
#endif
}

void vtGLCanvas::OnPaint( wxPaintEvent& event )
{
	// Prevent this function from ever being called nested, it is not re-entrant
	static bool bInside = false;
	if (bInside)
		return;
	bInside = true;

	vtScene *pScene = vtGetScene();

	if (!pScene->HasWinInfo())
	{
#ifdef WIN32
		HWND handle = (HWND) GetHandle();
		pScene->SetWinInfo(handle, m_glContext);
#else
		pScene->SetWinInfo(NULL, NULL);
#endif
	}
	// place the dc inside a scope, to delete it before the end of function
	if (1)
	{
		// This is a dummy, to avoid an endless succession of paint messages.
		// OnPaint handlers must always create a wxPaintDC.
		wxPaintDC dc(this);
#ifdef __WXMSW__
		if (!GetContext()) return;
#endif

		if (m_bPainting || !m_bRunning) return;

#if !VTLIB_PSM
		m_bPainting = true;

		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

		// Render the SSG scene
		vtGetScene()->DoUpdate();

		SwapBuffers();

#ifdef WIN32
		// Call Refresh again for continuous rendering,
		if (m_bRunning)
			Refresh(FALSE);
#else
		// Queue another refresh for continuous rendering.
		//   (Yield first so we don't starve out keyboard & mouse events.)
		//
		// FIXME: We may want to use a frame timer instead of immediate-
		//   redraw so we don't eat so much CPU on machines that can
		//   easily handle the frame rate.
		wxYield();
		QueueRefresh(FALSE);
#endif

		m_bPainting = false;
#endif // VTLIB_PSM
	}

	// Must allow some idle processing to occur - or the toolbars will not
	// update, and the close box will not respond!
	wxGetApp().ProcessIdle();

	bInside = false;
}

static void Reshape(int width, int height)
{
	printf("Reshape: %d, %d\n", width, height);
	glViewport(0, 0, (GLint)width, (GLint)height);
}

void vtGLCanvas::OnSize(wxSizeEvent& event)
{
	// Presumably this is a wxMSWism.
	// For wxGTK & wxMotif, all canvas resize events occur before the context
	//   is set.  So ignore this context check and grab the window width/height
	//   when we get it so it (and derived values such as aspect ratio and
	//   viewport parms) are computed correctly.
#ifdef __WXMSW__
	if (!GetContext()) return;
#endif

	SetCurrent();
	int width, height;
	GetClientSize(& width, & height);
	Reshape(width, height);

	vtGetScene()->SetWindowSize(width, height);
}

void vtGLCanvas::OnChar(wxKeyEvent& event)
{
	long key = event.KeyCode();

	if ( key == WXK_ESCAPE || key == 'q' || key == 'Q' )
		wxGetApp().GetTopWindow()->Close();

	// pass the char to the vtlib Scene
	vtGetScene()->OnKey(key, 0);
}

void vtGLCanvas::OnMouseEvent(wxMouseEvent& event1)
{
	// turn WX mouse event into a VT mouse event
	vtMouseEvent event;
	wxEventType type = event1.GetEventType();

	if ( type == wxEVT_LEFT_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_LEFT;
	}
	else if ( type == wxEVT_LEFT_UP )
	{
		event.type = VT_UP;
		event.button = VT_LEFT;
	}
	else if ( type == wxEVT_MIDDLE_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_MIDDLE;
	}
	else if ( type == wxEVT_MIDDLE_UP )
	{
		event.type = VT_UP;
		event.button = VT_MIDDLE;
	}
	else if ( type == wxEVT_RIGHT_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_RIGHT;
	}
	else if ( type == wxEVT_RIGHT_UP )
	{
		event.type = VT_UP;
		event.button = VT_RIGHT;
	}
	else if ( type == wxEVT_MOTION )
	{
		event.type = VT_MOVE;
		event.button = VT_NONE;
	}
	else
	{
		// ignore other mouse events, such as wxEVT_LEAVE_WINDOW
		return;
	}

	event.flags = 0;
	wxCoord xpos, ypos;
	event1.GetPosition(&xpos, &ypos);
	event.pos.Set(xpos, ypos);

	if (event1.ControlDown())
		event.flags |= VT_CONTROL;

	if (event1.ShiftDown())
		event.flags |= VT_SHIFT;

	vtGetScene()->OnMouse(event);
}

void vtGLCanvas::OnEraseBackground(wxEraseEvent& event)
{
	// Do nothing, to avoid flashing.
}
<commit_msg>added vtlib/core/Event.h<commit_after>//
// Name:	 canvas.cpp
// Purpose:	 Implements the canvas class for a wxWindows application.
//
// Copyright (c) 2001 Virtual Terrain Project
// Free for all uses, see license.txt for details.
//

// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"

#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif

// Header for the vtlib library
#include "vtlib/vtlib.h"
#include "vtlib/core/Event.h"

#include "canvas.h"
#include "frame.h"
#include "app.h"

DECLARE_APP(vtApp);

/*
 * vtGLCanvas implementation
 */
BEGIN_EVENT_TABLE(vtGLCanvas, wxGLCanvas)
EVT_SIZE(vtGLCanvas::OnSize)
EVT_PAINT(vtGLCanvas::OnPaint)
EVT_CHAR(vtGLCanvas::OnChar)
EVT_MOUSE_EVENTS(vtGLCanvas::OnMouseEvent)
EVT_ERASE_BACKGROUND(vtGLCanvas::OnEraseBackground)
END_EVENT_TABLE()

vtGLCanvas::vtGLCanvas(wxWindow *parent, wxWindowID id,
	const wxPoint& pos, const wxSize& size, long style, const wxString& name, int* gl_attrib):
wxGLCanvas(parent, id, pos, size, style, name, gl_attrib)
{
	parent->Show(TRUE);
	SetCurrent();

	m_bPainting = false;
	m_bRunning = true;
	QueueRefresh(FALSE);
}

vtGLCanvas::~vtGLCanvas(void)
{
}

void vtGLCanvas::QueueRefresh(bool eraseBackground)
	// A Refresh routine we can call from inside OnPaint.
	//   (queues the events rather than dispatching them immediately).
{
#if !WIN32
	// With wxGTK, you can't do a Refresh() in OnPaint because it doesn't
	//   queue (post) a Refresh event for later.  Rather it dispatches
	//   (processes) the underlying events immediately via ProcessEvent
	//   (read, recursive call).  See the wxPostEvent docs and Refresh code
	//   for more details.
	if ( eraseBackground )
	{
		wxEraseEvent eevent( GetId() );
		eevent.SetEventObject( this );
		wxPostEvent( GetEventHandler(), eevent );
	}

	wxPaintEvent event( GetId() );
	event.SetEventObject( this );
	wxPostEvent( GetEventHandler(), event );
#endif
}

void vtGLCanvas::OnPaint( wxPaintEvent& event )
{
	// Prevent this function from ever being called nested, it is not re-entrant
	static bool bInside = false;
	if (bInside)
		return;
	bInside = true;

	vtScene *pScene = vtGetScene();

	if (!pScene->HasWinInfo())
	{
#ifdef WIN32
		HWND handle = (HWND) GetHandle();
		pScene->SetWinInfo(handle, m_glContext);
#else
		pScene->SetWinInfo(NULL, NULL);
#endif
	}
	// place the dc inside a scope, to delete it before the end of function
	if (1)
	{
		// This is a dummy, to avoid an endless succession of paint messages.
		// OnPaint handlers must always create a wxPaintDC.
		wxPaintDC dc(this);
#ifdef __WXMSW__
		if (!GetContext()) return;
#endif

		if (m_bPainting || !m_bRunning) return;

#if !VTLIB_PSM
		m_bPainting = true;

		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

		// Render the SSG scene
		vtGetScene()->DoUpdate();

		SwapBuffers();

#ifdef WIN32
		// Call Refresh again for continuous rendering,
		if (m_bRunning)
			Refresh(FALSE);
#else
		// Queue another refresh for continuous rendering.
		//   (Yield first so we don't starve out keyboard & mouse events.)
		//
		// FIXME: We may want to use a frame timer instead of immediate-
		//   redraw so we don't eat so much CPU on machines that can
		//   easily handle the frame rate.
		wxYield();
		QueueRefresh(FALSE);
#endif

		m_bPainting = false;
#endif // VTLIB_PSM
	}

	// Must allow some idle processing to occur - or the toolbars will not
	// update, and the close box will not respond!
	wxGetApp().ProcessIdle();

	bInside = false;
}

static void Reshape(int width, int height)
{
	printf("Reshape: %d, %d\n", width, height);
	glViewport(0, 0, (GLint)width, (GLint)height);
}

void vtGLCanvas::OnSize(wxSizeEvent& event)
{
	// Presumably this is a wxMSWism.
	// For wxGTK & wxMotif, all canvas resize events occur before the context
	//   is set.  So ignore this context check and grab the window width/height
	//   when we get it so it (and derived values such as aspect ratio and
	//   viewport parms) are computed correctly.
#ifdef __WXMSW__
	if (!GetContext()) return;
#endif

	SetCurrent();
	int width, height;
	GetClientSize(& width, & height);
	Reshape(width, height);

	vtGetScene()->SetWindowSize(width, height);
}

void vtGLCanvas::OnChar(wxKeyEvent& event)
{
	long key = event.KeyCode();

	if ( key == WXK_ESCAPE || key == 'q' || key == 'Q' )
		wxGetApp().GetTopWindow()->Close();

	// pass the char to the vtlib Scene
	vtGetScene()->OnKey(key, 0);
}

void vtGLCanvas::OnMouseEvent(wxMouseEvent& event1)
{
	// turn WX mouse event into a VT mouse event
	vtMouseEvent event;
	wxEventType type = event1.GetEventType();

	if ( type == wxEVT_LEFT_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_LEFT;
	}
	else if ( type == wxEVT_LEFT_UP )
	{
		event.type = VT_UP;
		event.button = VT_LEFT;
	}
	else if ( type == wxEVT_MIDDLE_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_MIDDLE;
	}
	else if ( type == wxEVT_MIDDLE_UP )
	{
		event.type = VT_UP;
		event.button = VT_MIDDLE;
	}
	else if ( type == wxEVT_RIGHT_DOWN )
	{
		event.type = VT_DOWN;
		event.button = VT_RIGHT;
	}
	else if ( type == wxEVT_RIGHT_UP )
	{
		event.type = VT_UP;
		event.button = VT_RIGHT;
	}
	else if ( type == wxEVT_MOTION )
	{
		event.type = VT_MOVE;
		event.button = VT_NONE;
	}
	else
	{
		// ignore other mouse events, such as wxEVT_LEAVE_WINDOW
		return;
	}

	event.flags = 0;
	wxCoord xpos, ypos;
	event1.GetPosition(&xpos, &ypos);
	event.pos.Set(xpos, ypos);

	if (event1.ControlDown())
		event.flags |= VT_CONTROL;

	if (event1.ShiftDown())
		event.flags |= VT_SHIFT;

	vtGetScene()->OnMouse(event);
}

void vtGLCanvas::OnEraseBackground(wxEraseEvent& event)
{
	// Do nothing, to avoid flashing.
}
<|endoftext|>


<commit_before>#include "MaximumProductSubarray.hpp"

#include <algorithm>

using namespace std;

int MaximumProductSubarray::maxProduct(vector<int> &nums) {
    int n = nums.size();

    if (n == 0)
        return 0;

    vector<int> a(n, 0);
    vector<int> b(n, 0);
    a[0] = b[0] = nums[0];

    for (int i = 1; i < n; i++) {
        int v1 = nums[i];
        int v2 = a[i - 1] * nums[i];
        int v3 = b[i - 1] * nums[i];
        a[i] = max(v1, max(v2, v3));
        b[i] = min(v1, min(v2, v3));
    }

    int ret = a[0];

    for (int i = 1; i < n; i++)
        ret = max(ret, a[i]);

    return ret;
}
<commit_msg>Refine Problem 152. Maximum Product Subarray<commit_after>#include "MaximumProductSubarray.hpp"

#include <algorithm>

using namespace std;

int MaximumProductSubarray::maxProduct(vector<int> &nums) {
    if (nums.empty()) return 0;

    vector<int> a(nums.begin(), nums.end());
    vector<int> b(nums.begin(), nums.end());
    int ret = a[0];

    for (int i = 1; i < nums.size(); i++) {
        int v1 = a[i - 1] * nums[i];
        int v2 = b[i - 1] * nums[i];
        a[i] = max(a[i], max(v1, v2));
        b[i] = min(b[i], min(v1, v2));
        ret = max(ret, a[i]);
    }

    return ret;
}
<|endoftext|>


<commit_before>#include <Spirit_Defines.h>
#include <engine/Method_EMA.hpp>
#include <engine/Vectormath.hpp>
#include <data/Spin_System.hpp>
#include <io/IO.hpp>
#include <utility/Logging.hpp>
#include <fmt/format.h>
#include <Eigen/Dense>

#include <iostream>
#include <fstream>
#include <thread>
#include <chrono>

using namespace Utility;

namespace Engine
{
    Method_EMA::Method_EMA(std::shared_ptr<Data::Spin_System> system, int idx_img, int idx_chain) :
        Method(system->ema_parameters, idx_img, idx_chain)
    {
        // Currently we only support a single image being iterated at once:
        this->systems = std::vector<std::shared_ptr<Data::Spin_System>>(1, system);
        this->SenderName = Utility::Log_Sender::EMA;

        this->noi = this->systems.size();
        this->nos = this->systems[0]->nos;

        this->parameters_ema = system->ema_parameters;

        this->spins_initial = *this->systems[0]->spins;
        this->axis = vectorfield(this->nos);
        this->mode = vectorfield(this->nos, Vector3{1,0,0});

        this->steps_per_period = 50;
        this->timestep = 1./this->steps_per_period;
        this->counter = 0;
        this->amplitude = 0.2;

        // Find the axes of rotation
        for (int idx=0; idx<nos; idx++)
            this->axis[idx] = spins_initial[idx].cross(this->mode[idx]).normalized();
    }

    void Method_EMA::Iteration()
    {
        int nos = this->systems[0]->spins->size();

        auto& image = *this->systems[0]->spins;

        // Calculate n for that iteration based on the initial n displacement vector
        scalar angle = this->amplitude * std::cos(2*M_PI*this->counter*this->timestep);

        // Rotate the spins
        for (int idx=0; idx<nos; idx++)
            Vectormath::rotate( this->spins_initial[idx], this->axis[idx], angle, image[idx] );

        // normalize all spins
        Vectormath::normalize_vectors( *this->systems[0]->spins );
    }

    bool Method_EMA::Converged()
    {
        //// TODO: Needs proper implementation
        return false;
    }

    void Method_EMA::Save_Current(std::string starttime, int iteration, bool initial, bool final)
    {
    }

    void Method_EMA::Hook_Pre_Iteration()
    {
    }

    void Method_EMA::Hook_Post_Iteration()
    {
        ++this->counter;
        std::this_thread::sleep_for(std::chrono::milliseconds(50));
    }

    void Method_EMA::Initialize()
    {
    }

    void Method_EMA::Finalize()
    {
    }

    void Method_EMA::Message_Start()
    {
        using namespace Utility;

        //---- Log messages
        Log.SendBlock(Log_Level::All, this->SenderName,
        {
            "------------  Started  " + this->Name() + " Calculation  ------------",
            "    Going to iterate " + fmt::format("{}", this->n_log) + " steps",
            "                with " + fmt::format("{}", this->n_iterations_log) + " iterations per step",
            "     Number of modes " + fmt::format("{}", this->parameters_ema->n_modes ),
            "-----------------------------------------------------"
        }, this->idx_image, this->idx_chain);
    }

    void Method_EMA::Message_Step()
    {
    }

    void Method_EMA::Message_End()
    {
    }

    // Method name as string
    std::string Method_EMA::Name() { return "EMA"; }
}<commit_msg>Core: added eigenmode calculation to Method_EMA.<commit_after>#include <Spirit_Defines.h>
#include <engine/Method_EMA.hpp>
#include <engine/Vectormath.hpp>
#include <data/Spin_System.hpp>
#include <io/IO.hpp>
#include <utility/Logging.hpp>

#include <fmt/format.h>
#include <Eigen/Dense>
#include <Eigen/Eigenvalues>
#include <GenEigsSolver.h>  // Also includes <MatOp/DenseGenMatProd.h>
#include <GenEigsRealShiftSolver.h>

#include <iostream>
#include <fstream>
#include <thread>
#include <chrono>

using namespace Utility;

namespace Engine
{
    Method_EMA::Method_EMA(std::shared_ptr<Data::Spin_System> system, int idx_img, int idx_chain) :
        Method(system->ema_parameters, idx_img, idx_chain)
    {
        // Currently we only support a single image being iterated at once:
        this->systems = std::vector<std::shared_ptr<Data::Spin_System>>(1, system);
        this->SenderName = Utility::Log_Sender::EMA;

        this->noi = this->systems.size();
        this->nos = this->systems[0]->nos;

        this->parameters_ema = system->ema_parameters;

        this->steps_per_period = 50;
        this->timestep = 1./this->steps_per_period;
        this->counter = 0;
        this->amplitude = 0.2;

        this->spins_initial = *this->systems[0]->spins;
        this->axis = vectorfield(this->nos);

        // Calculate the Eigenmodes
        int n_modes = 10;
        int selected_mode = 0;

        vectorfield gradient(this->nos);
        MatrixX hessian(3*this->nos, 3*this->nos);

        // The gradient (unprojected)
        system->hamiltonian->Gradient(spins_initial, gradient);
        Vectormath::set_c_a(1, gradient, gradient, this->parameters->pinning->mask_unpinned);

        // The Hessian (unprojected)
        system->hamiltonian->Hessian(spins_initial, hessian);

        // Calculate the final Hessian to use for the minimum mode
        MatrixX hessian_final = MatrixX::Zero(2*this->nos, 2*this->nos);
        Manifoldmath::hessian_bordered(spins_initial, gradient, hessian, hessian_final);

        Spectra::DenseGenMatProd<scalar> op(hessian_final);
        Spectra::GenEigsSolver< scalar, Spectra::SMALLEST_REAL, Spectra::DenseGenMatProd<scalar> > hessian_spectrum(&op, n_modes, 2*this->nos);
        hessian_spectrum.init();
        // Compute the specified spectrum
        int nconv = hessian_spectrum.compute(1000, 1e-10, int(Spectra::SMALLEST_REAL));

        this->mode = vectorfield(this->nos, Vector3{1, 0, 0});
        if (hessian_spectrum.info() == Spectra::SUCCESSFUL)
        {
            // Retrieve the eigenvalues
            // VectorX evalues = hessian_spectrum.eigenvalues().real();

            // Retrieve the eigenmode
            VectorX evec_2N = hessian_spectrum.eigenvectors().real().col(selected_mode);

            // Extract the minimum mode (transform evec_lowest_2N back to 3N)
            MatrixX basis_3Nx2N = MatrixX::Zero(3*nos, 2*nos);
            Manifoldmath::tangent_basis_spherical(spins_initial, basis_3Nx2N); // Important to choose the right matrix here! It should especially be consistent with the matrix chosen in the Hessian calculation!
            VectorX evec_3N = basis_3Nx2N * evec_2N;

            // Set the mode
            for (int n=0; n<this->nos; ++n)
                this->mode[n] = {evec_3N[3*n], evec_3N[3*n+1], evec_3N[3*n+2]};
        }

        // Find the axes of rotation
        for (int idx=0; idx<nos; idx++)
            this->axis[idx] = spins_initial[idx].cross(this->mode[idx]).normalized();
    }

    void Method_EMA::Iteration()
    {
        int nos = this->systems[0]->spins->size();

        auto& image = *this->systems[0]->spins;

        // Calculate n for that iteration based on the initial n displacement vector
        scalar angle = this->amplitude * std::cos(2*M_PI*this->counter*this->timestep);

        // Rotate the spins
        for (int idx=0; idx<nos; idx++)
            Vectormath::rotate( this->spins_initial[idx], this->axis[idx], angle, image[idx] );

        // normalize all spins
        Vectormath::normalize_vectors( *this->systems[0]->spins );
    }

    bool Method_EMA::Converged()
    {
        //// TODO: Needs proper implementation
        return false;
    }

    void Method_EMA::Save_Current(std::string starttime, int iteration, bool initial, bool final)
    {
    }

    void Method_EMA::Hook_Pre_Iteration()
    {
    }

    void Method_EMA::Hook_Post_Iteration()
    {
        ++this->counter;
        std::this_thread::sleep_for(std::chrono::milliseconds(50));
    }

    void Method_EMA::Initialize()
    {
    }

    void Method_EMA::Finalize()
    {
    }

    void Method_EMA::Message_Start()
    {
        using namespace Utility;

        //---- Log messages
        Log.SendBlock(Log_Level::All, this->SenderName,
        {
            "------------  Started  " + this->Name() + " Calculation  ------------",
            "    Going to iterate " + fmt::format("{}", this->n_log) + " steps",
            "                with " + fmt::format("{}", this->n_iterations_log) + " iterations per step",
            "     Number of modes " + fmt::format("{}", this->parameters_ema->n_modes ),
            "-----------------------------------------------------"
        }, this->idx_image, this->idx_chain);
    }

    void Method_EMA::Message_Step()
    {
    }

    void Method_EMA::Message_End()
    {
    }

    // Method name as string
    std::string Method_EMA::Name() { return "EMA"; }
}<|endoftext|>


<commit_before>/**
 * Clever programming language
 * Copyright (c) Clever Team
 *
 * This file is distributed under the MIT license. See LICENSE for details.
 */

#include "core/clever.h"
#include "modules/std/core/function.h"
#include "modules/std/reflection/reflect.h"
#include "modules/std/core/array.h"
#include "modules/std/core/map.h"

namespace clever { namespace packages { namespace std { namespace reflection {

void* ReflectType::allocData(CLEVER_TYPE_CTOR_ARGS) const
{
	ReflectObject* obj = new ReflectObject;

	obj->setData(args->at(0));

	return obj;
}

// Reflect::Reflect(object)
// Returns an instance of Reflect object
CLEVER_METHOD(ReflectType::ctor)
{
	if (!clever_check_args(".")) {
		return;
	}

	result->setObj(this, allocData(&args));
}

// Reflect::getType()
// Returns the type name of the object
CLEVER_METHOD(ReflectType::getType)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	if (intern->getData()->getType()) {
		result->setStr(intern->getData()->getType()->getName());
	}
}

// Reflect::isFunction()
// Check if the object is of function type
CLEVER_METHOD(ReflectType::isFunction)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isFunction());
}

// Reflect::isBool()
// Check if the object is of bool type
CLEVER_METHOD(ReflectType::isBool)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isBool());
}

// Reflect::isString()
// Check if the object is of string type
CLEVER_METHOD(ReflectType::isString)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isStr());
}

// Reflect::isInt()
// Check if the object is of int type
CLEVER_METHOD(ReflectType::isInt)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isInt());
}

// Reflect::isDouble()
// Check if the object is of double type
CLEVER_METHOD(ReflectType::isDouble)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isDouble());
}

// Reflect::isArray()
// Check if the object is of double type
CLEVER_METHOD(ReflectType::isArray)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isArray());
}

// Reflect::isMap()
// Check if the object is of map type
CLEVER_METHOD(ReflectType::isMap)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isMap());
}

// Reflect::isThread()
// Check if the object is of thread type
CLEVER_METHOD(ReflectType::isThread)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isThread());
}

// Reflect::getName()
// Returns the name of the type or function
CLEVER_METHOD(ReflectType::getName)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setStr(CSTRING(func->getName()));
}

// Reflect::isStatic()
// Check if the object is an static function
CLEVER_METHOD(ReflectType::isStatic)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isStatic());
}

// Reflect::isVariadic()
// Check if the object is a variadic function
CLEVER_METHOD(ReflectType::isVariadic)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isVariadic());
}

// Reflect::isUserDefined()
// Check if the object is an user-defined function
CLEVER_METHOD(ReflectType::isUserDefined)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isUserDefined());
}

// Reflect::isInternal()
// Check if the object is an internal function
CLEVER_METHOD(ReflectType::isInternal)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isInternal());
}

// Reflect::getNumArgs()
// Returns the number of arguments (variadic is not in the count)
CLEVER_METHOD(ReflectType::getNumArgs)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setInt(func->getNumArgs());
}

// Reflect::getNumRegArgs()
// Returns the number of required arguments (variadic is not in the count)
CLEVER_METHOD(ReflectType::getNumReqArgs)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setInt(func->getNumRequiredArgs());
}

// Reflect::getMethods()
// Returns an array with the type methods
CLEVER_METHOD(ReflectType::getMethods)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const MethodMap& methods = intern->getData()->getType()->getMethods();
	MethodMap::const_iterator it(methods.begin()), end(methods.end());

	ArrayObject* arr = new ArrayObject;

	while (it != end) {
		Value* val = new Value;
		val->setStr(CSTRING(it->second->getName()));
		arr->getData().push_back(val);
		++it;
	}

	result->setObj(CLEVER_ARRAY_TYPE, arr);
}

// Reflect::getProperties()
// Returns the type properties
CLEVER_METHOD(ReflectType::getProperties)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const PropertyMap& props = intern->getData()->getType()->getProperties();
	PropertyMap::const_iterator it(props.begin()), end(props.end());

	MapObject* map = new MapObject;

	while (it != end) {
		map->getData().insert(MapObjectPair(*it->first, it->second));
		it->second->addRef();
		++it;
	}

	result->setObj(CLEVER_MAP_TYPE, map);
}

// Reflect type initialization
CLEVER_TYPE_INIT(ReflectType::init)
{
	Function* ctor = new Function("Reflect", (MethodPtr) &ReflectType::ctor);

	setConstructor(ctor);
	addMethod(ctor);
	addMethod(new Function("getType",    (MethodPtr) &ReflectType::getType));

	// Type checking
	addMethod(new Function("isFunction", (MethodPtr) &ReflectType::isFunction));
	addMethod(new Function("isBool",     (MethodPtr) &ReflectType::isBool));
	addMethod(new Function("isString",   (MethodPtr) &ReflectType::isString));
	addMethod(new Function("isInt",      (MethodPtr) &ReflectType::isInt));
	addMethod(new Function("isDouble",   (MethodPtr) &ReflectType::isDouble));
	addMethod(new Function("isArray",    (MethodPtr) &ReflectType::isArray));
	addMethod(new Function("isMap",      (MethodPtr) &ReflectType::isMap));
	addMethod(new Function("isThread",   (MethodPtr) &ReflectType::isThread));

	// Function specific methods
	addMethod(new Function("getName",       (MethodPtr) &ReflectType::getName));
	addMethod(new Function("isStatic",      (MethodPtr) &ReflectType::isStatic));
	addMethod(new Function("isVariadic",    (MethodPtr) &ReflectType::isVariadic));
	addMethod(new Function("isUserDefined", (MethodPtr) &ReflectType::isUserDefined));
	addMethod(new Function("isInternal",    (MethodPtr) &ReflectType::isInternal));
	addMethod(new Function("getNumArgs",    (MethodPtr) &ReflectType::getNumArgs));
	addMethod(new Function("getNumReqArgs", (MethodPtr) &ReflectType::getNumReqArgs));

	// Type specific methods
	addMethod(new Function("getMethods",    (MethodPtr) &ReflectType::getMethods));
	addMethod(new Function("getProperties", (MethodPtr) &ReflectType::getProperties));
}

}}}} // clever::packages::std::reflection
<commit_msg>- Fix comments<commit_after>/**
 * Clever programming language
 * Copyright (c) Clever Team
 *
 * This file is distributed under the MIT license. See LICENSE for details.
 */

#include "core/clever.h"
#include "modules/std/core/function.h"
#include "modules/std/reflection/reflect.h"
#include "modules/std/core/array.h"
#include "modules/std/core/map.h"

namespace clever { namespace packages { namespace std { namespace reflection {

void* ReflectType::allocData(CLEVER_TYPE_CTOR_ARGS) const
{
	ReflectObject* obj = new ReflectObject;

	obj->setData(args->at(0));

	return obj;
}

// Reflect::Reflect(object)
// Returns an instance of Reflect object
CLEVER_METHOD(ReflectType::ctor)
{
	if (!clever_check_args(".")) {
		return;
	}

	result->setObj(this, allocData(&args));
}

// Reflect::getType()
// Returns the type name of the object
CLEVER_METHOD(ReflectType::getType)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	if (intern->getData()->getType()) {
		result->setStr(intern->getData()->getType()->getName());
	}
}

// Reflect::isFunction()
// Check if the object is of function type
CLEVER_METHOD(ReflectType::isFunction)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isFunction());
}

// Reflect::isBool()
// Check if the object is of bool type
CLEVER_METHOD(ReflectType::isBool)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isBool());
}

// Reflect::isString()
// Check if the object is of string type
CLEVER_METHOD(ReflectType::isString)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isStr());
}

// Reflect::isInt()
// Check if the object is of int type
CLEVER_METHOD(ReflectType::isInt)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isInt());
}

// Reflect::isDouble()
// Check if the object is of double type
CLEVER_METHOD(ReflectType::isDouble)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isDouble());
}

// Reflect::isArray()
// Check if the object is of double type
CLEVER_METHOD(ReflectType::isArray)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isArray());
}

// Reflect::isMap()
// Check if the object is of map type
CLEVER_METHOD(ReflectType::isMap)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isMap());
}

// Reflect::isThread()
// Check if the object is of thread type
CLEVER_METHOD(ReflectType::isThread)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());

	result->setBool(intern->getData()->isThread());
}

// Reflect::getName()
// Returns the name of the type or function
CLEVER_METHOD(ReflectType::getName)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setStr(CSTRING(func->getName()));
}

// Reflect::isStatic()
// Check if the object is an static function
CLEVER_METHOD(ReflectType::isStatic)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isStatic());
}

// Reflect::isVariadic()
// Check if the object is a variadic function
CLEVER_METHOD(ReflectType::isVariadic)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isVariadic());
}

// Reflect::isUserDefined()
// Check if the object is an user-defined function
CLEVER_METHOD(ReflectType::isUserDefined)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isUserDefined());
}

// Reflect::isInternal()
// Check if the object is an internal function
CLEVER_METHOD(ReflectType::isInternal)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setBool(func->isInternal());
}

// Reflect::getNumArgs()
// Returns the number of arguments (variadic is not in the count)
CLEVER_METHOD(ReflectType::getNumArgs)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setInt(func->getNumArgs());
}

// Reflect::getNumRegArgs()
// Returns the number of required arguments (variadic is not in the count)
CLEVER_METHOD(ReflectType::getNumReqArgs)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const Value* data = intern->getData();

	if (!data->isFunction()) {
		return;
	}

	const Function* func = static_cast<Function*>(data->getObj());

	result->setInt(func->getNumRequiredArgs());
}

// Reflect::getMethods()
// Returns an array containing the type methods
CLEVER_METHOD(ReflectType::getMethods)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const MethodMap& methods = intern->getData()->getType()->getMethods();
	MethodMap::const_iterator it(methods.begin()), end(methods.end());

	ArrayObject* arr = new ArrayObject;

	while (it != end) {
		Value* val = new Value;
		val->setStr(CSTRING(it->second->getName()));
		arr->getData().push_back(val);
		++it;
	}

	result->setObj(CLEVER_ARRAY_TYPE, arr);
}

// Reflect::getProperties()
// Returns a map containing the type properties
CLEVER_METHOD(ReflectType::getProperties)
{
	if (!clever_check_no_args()) {
		return;
	}

	const ReflectObject* intern = CLEVER_GET_OBJECT(ReflectObject*, CLEVER_THIS());
	const PropertyMap& props = intern->getData()->getType()->getProperties();
	PropertyMap::const_iterator it(props.begin()), end(props.end());

	MapObject* map = new MapObject;

	while (it != end) {
		map->getData().insert(MapObjectPair(*it->first, it->second));
		it->second->addRef();
		++it;
	}

	result->setObj(CLEVER_MAP_TYPE, map);
}

// Reflect type initialization
CLEVER_TYPE_INIT(ReflectType::init)
{
	Function* ctor = new Function("Reflect", (MethodPtr) &ReflectType::ctor);

	setConstructor(ctor);
	addMethod(ctor);
	addMethod(new Function("getType",    (MethodPtr) &ReflectType::getType));

	// Type checking
	addMethod(new Function("isFunction", (MethodPtr) &ReflectType::isFunction));
	addMethod(new Function("isBool",     (MethodPtr) &ReflectType::isBool));
	addMethod(new Function("isString",   (MethodPtr) &ReflectType::isString));
	addMethod(new Function("isInt",      (MethodPtr) &ReflectType::isInt));
	addMethod(new Function("isDouble",   (MethodPtr) &ReflectType::isDouble));
	addMethod(new Function("isArray",    (MethodPtr) &ReflectType::isArray));
	addMethod(new Function("isMap",      (MethodPtr) &ReflectType::isMap));
	addMethod(new Function("isThread",   (MethodPtr) &ReflectType::isThread));

	// Function specific methods
	addMethod(new Function("getName",       (MethodPtr) &ReflectType::getName));
	addMethod(new Function("isStatic",      (MethodPtr) &ReflectType::isStatic));
	addMethod(new Function("isVariadic",    (MethodPtr) &ReflectType::isVariadic));
	addMethod(new Function("isUserDefined", (MethodPtr) &ReflectType::isUserDefined));
	addMethod(new Function("isInternal",    (MethodPtr) &ReflectType::isInternal));
	addMethod(new Function("getNumArgs",    (MethodPtr) &ReflectType::getNumArgs));
	addMethod(new Function("getNumReqArgs", (MethodPtr) &ReflectType::getNumReqArgs));

	// Type specific methods
	addMethod(new Function("getMethods",    (MethodPtr) &ReflectType::getMethods));
	addMethod(new Function("getProperties", (MethodPtr) &ReflectType::getProperties));
}

}}}} // clever::packages::std::reflection
<|endoftext|>


<commit_before><commit_msg>[Part] AppPartPy.cpp Python 3.9 Unicode warning fixes.<commit_after><|endoftext|>


<commit_before>/*
 * superviseddescent: A C++11 implementation of the supervised descent
 *                    optimisation method
 * File: examples/rcr/helpers.hpp
 *
 * Copyright 2015 Patrik Huber
 *
 * 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.
 */
#pragma once

#ifndef HELPERS_HPP_
#define HELPERS_HPP_

#include "eos_core_landmark.hpp"

#include <vector>

namespace rcr {

// for float-type landmarks
// returns a row in the form [x0, y0, ..., xn, yn]
// type of returned Mat is CV_32FC1
// we could write this more generic if needed
//template<class LandmarkType>
cv::Mat toRow(eos::core::LandmarkCollection<cv::Vec2f> landmarks)
{
	auto numLandmarks = landmarks.size();
	cv::Mat row(1, numLandmarks * 2, CV_32FC1);
	for (std::size_t i = 0; i < numLandmarks; ++i) {
		row.at<float>(i) = landmarks[i].coordinates[0];
		row.at<float>(i + numLandmarks) = landmarks[i].coordinates[1];
	}
	return row;
}

// document how they're gonna be taken/expected from/int he Mat
eos::core::LandmarkCollection<cv::Vec2f> toLandmarkCollection(cv::Mat modelInstance, std::vector<std::string> modelLandmarksList)
{
	eos::core::LandmarkCollection<cv::Vec2f> collection;
	auto numLandmarks = modelInstance.cols / 2;
	assert(numLandmarks == modelLandmarksList.size()); // shouldn't be an assert, not a programming/internal error.
	for (int i = 0; i < numLandmarks; ++i) {
		collection.emplace_back(eos::core::Landmark<cv::Vec2f>{ modelLandmarksList[i], cv::Vec2f{ modelInstance.at<float>(i), modelInstance.at<float>(i + numLandmarks) } });
	}
	return collection;
}

/**
 * Draws the given landmarks into the image.
 *
 * @param[in] image An image to draw into.
 * @param[in] landmarks The landmarks to draw.
 * @param[in] color Color of the landmarks to be drawn.
 */
void drawLandmarks(cv::Mat image, cv::Mat landmarks, cv::Scalar color = cv::Scalar(0.0, 255.0, 0.0))
{
	auto numLandmarks = std::max(landmarks.cols, landmarks.rows) / 2;
	for (int i = 0; i < numLandmarks; ++i) {
		cv::circle(image, cv::Point2f(landmarks.at<float>(i), landmarks.at<float>(i + numLandmarks)), 2, color);
	}
}

// checks overlap...
// Possible better names: checkEqual, checkIsTruePositive, overlap...
bool checkFace(std::vector<cv::Rect> detectedFaces, eos::core::LandmarkCollection<cv::Vec2f> groundtruthLandmarks)
{
	// If no face is detected, return immediately:
	if (detectedFaces.empty()) {
		return false;
	}

	bool isTruePositive = true;
	// for now, if the ground-truth landmarks 37 (reye_oc), 46 (leye_oc) and 58 (mouth_ll_c) are inside the face-box
	// (should add: _and_ the face-box is not bigger than IED*2 or something)
	//assert(groundtruthLandmarks.size() == 68); // only works with ibug-68 so far...
	// for now: user should make sure we have 37, 46, 58.

	for (const auto& lm : groundtruthLandmarks) {
		if (lm.name == "37" || lm.name == "46" || lm.name == "58") {
			if (!detectedFaces[0].contains(cv::Point(lm.coordinates))) {
				isTruePositive = false;
				break; // if any LM is not inside, skip this training image
				// Note: improvement: if the first face-box doesn't work, try the other ones
			}
		}
	}

	return isTruePositive;
}

// Calculate the IED from one or several identifiers.
// Several is necessary because sometimes (e.g. ibug) doesn't define the eye center.
// throws if any of given ids not present in lms. => Todo: Think about if we should throw or use optional<>.
double getIed(eos::core::LandmarkCollection<cv::Vec2f> lms, std::vector<std::string> rightEyeIdentifiers, std::vector<std::string> leftEyeIdentifiers)
{
	// Calculate the inter-eye distance. Which landmarks to take for that is specified in the config, it
	// might be one or two, and we calculate the average of them (per eye). For example, it might be the outer eye-corners.
	cv::Vec2f rightEyeCenter(0.0f, 0.0f);
	for (const auto& rightEyeIdentifyer : rightEyeIdentifiers) {
		eos::core::LandmarkCollection<cv::Vec2f>::const_iterator element;
		if ((element = std::find_if(begin(lms), end(lms), [&rightEyeIdentifyer](const eos::core::Landmark<cv::Vec2f>& landmark) { return landmark.name == rightEyeIdentifyer; })) == end(lms)) {
			throw std::runtime_error("one of given rightEyeIdentifiers ids not present in lms");
		}
		rightEyeCenter += element->coordinates;
	}
	rightEyeCenter /= static_cast<float>(rightEyeIdentifiers.size());
	cv::Vec2f leftEyeCenter(0.0f, 0.0f);
	for (const auto& leftEyeIdentifyer : leftEyeIdentifiers) {
		eos::core::LandmarkCollection<cv::Vec2f>::const_iterator element;
		if ((element = std::find_if(begin(lms), end(lms), [&leftEyeIdentifyer](const eos::core::Landmark<cv::Vec2f>& landmark) { return landmark.name == leftEyeIdentifyer; })) == end(lms)) {
			throw std::runtime_error("one of given leftEyeIdentifiers ids not present in lms");
		}
		leftEyeCenter += element->coordinates;
	}
	leftEyeCenter /= static_cast<float>(leftEyeIdentifiers.size());
	cv::Scalar interEyeDistance = cv::norm(rightEyeCenter, leftEyeCenter, cv::NORM_L2);
	return interEyeDistance[0];
};

} /* namespace rcr */

#endif /* HELPERS_HPP_ */
<commit_msg>Fixed type conversion warning in toRow<commit_after>/*
 * superviseddescent: A C++11 implementation of the supervised descent
 *                    optimisation method
 * File: examples/rcr/helpers.hpp
 *
 * Copyright 2015 Patrik Huber
 *
 * 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.
 */
#pragma once

#ifndef HELPERS_HPP_
#define HELPERS_HPP_

#include "eos_core_landmark.hpp"

#include "opencv2/core/core.hpp"

#include <vector>

namespace rcr {

// for float-type landmarks
// returns a row in the form [x0, y0, ..., xn, yn]
// type of returned Mat is CV_32FC1
// we could write this more generic if needed
//template<class LandmarkType>
cv::Mat toRow(eos::core::LandmarkCollection<cv::Vec2f> landmarks)
{
	// landmarks.size() must be <= max_int
	auto numLandmarks = static_cast<int>(landmarks.size());
	cv::Mat row(1, numLandmarks * 2, CV_32FC1);
	for (int i = 0; i < numLandmarks; ++i) {
		row.at<float>(i) = landmarks[i].coordinates[0];
		row.at<float>(i + numLandmarks) = landmarks[i].coordinates[1];
	}
	return row;
}

// document how they're gonna be taken/expected from/int he Mat
eos::core::LandmarkCollection<cv::Vec2f> toLandmarkCollection(cv::Mat modelInstance, std::vector<std::string> modelLandmarksList)
{
	eos::core::LandmarkCollection<cv::Vec2f> collection;
	auto numLandmarks = modelInstance.cols / 2;
	assert(numLandmarks == modelLandmarksList.size()); // shouldn't be an assert, not a programming/internal error.
	for (int i = 0; i < numLandmarks; ++i) {
		collection.emplace_back(eos::core::Landmark<cv::Vec2f>{ modelLandmarksList[i], cv::Vec2f{ modelInstance.at<float>(i), modelInstance.at<float>(i + numLandmarks) } });
	}
	return collection;
}

/**
 * Draws the given landmarks into the image.
 *
 * @param[in] image An image to draw into.
 * @param[in] landmarks The landmarks to draw.
 * @param[in] color Color of the landmarks to be drawn.
 */
void drawLandmarks(cv::Mat image, cv::Mat landmarks, cv::Scalar color = cv::Scalar(0.0, 255.0, 0.0))
{
	auto numLandmarks = std::max(landmarks.cols, landmarks.rows) / 2;
	for (int i = 0; i < numLandmarks; ++i) {
		cv::circle(image, cv::Point2f(landmarks.at<float>(i), landmarks.at<float>(i + numLandmarks)), 2, color);
	}
}

// checks overlap...
// Possible better names: checkEqual, checkIsTruePositive, overlap...
bool checkFace(std::vector<cv::Rect> detectedFaces, eos::core::LandmarkCollection<cv::Vec2f> groundtruthLandmarks)
{
	// If no face is detected, return immediately:
	if (detectedFaces.empty()) {
		return false;
	}

	bool isTruePositive = true;
	// for now, if the ground-truth landmarks 37 (reye_oc), 46 (leye_oc) and 58 (mouth_ll_c) are inside the face-box
	// (should add: _and_ the face-box is not bigger than IED*2 or something)
	//assert(groundtruthLandmarks.size() == 68); // only works with ibug-68 so far...
	// for now: user should make sure we have 37, 46, 58.

	for (const auto& lm : groundtruthLandmarks) {
		if (lm.name == "37" || lm.name == "46" || lm.name == "58") {
			if (!detectedFaces[0].contains(cv::Point(lm.coordinates))) {
				isTruePositive = false;
				break; // if any LM is not inside, skip this training image
				// Note: improvement: if the first face-box doesn't work, try the other ones
			}
		}
	}

	return isTruePositive;
}

// Calculate the IED from one or several identifiers.
// Several is necessary because sometimes (e.g. ibug) doesn't define the eye center.
// throws if any of given ids not present in lms. => Todo: Think about if we should throw or use optional<>.
double getIed(eos::core::LandmarkCollection<cv::Vec2f> lms, std::vector<std::string> rightEyeIdentifiers, std::vector<std::string> leftEyeIdentifiers)
{
	// Calculate the inter-eye distance. Which landmarks to take for that is specified in the config, it
	// might be one or two, and we calculate the average of them (per eye). For example, it might be the outer eye-corners.
	cv::Vec2f rightEyeCenter(0.0f, 0.0f);
	for (const auto& rightEyeIdentifyer : rightEyeIdentifiers) {
		eos::core::LandmarkCollection<cv::Vec2f>::const_iterator element;
		if ((element = std::find_if(begin(lms), end(lms), [&rightEyeIdentifyer](const eos::core::Landmark<cv::Vec2f>& landmark) { return landmark.name == rightEyeIdentifyer; })) == end(lms)) {
			throw std::runtime_error("one of given rightEyeIdentifiers ids not present in lms");
		}
		rightEyeCenter += element->coordinates;
	}
	rightEyeCenter /= static_cast<float>(rightEyeIdentifiers.size());
	cv::Vec2f leftEyeCenter(0.0f, 0.0f);
	for (const auto& leftEyeIdentifyer : leftEyeIdentifiers) {
		eos::core::LandmarkCollection<cv::Vec2f>::const_iterator element;
		if ((element = std::find_if(begin(lms), end(lms), [&leftEyeIdentifyer](const eos::core::Landmark<cv::Vec2f>& landmark) { return landmark.name == leftEyeIdentifyer; })) == end(lms)) {
			throw std::runtime_error("one of given leftEyeIdentifiers ids not present in lms");
		}
		leftEyeCenter += element->coordinates;
	}
	leftEyeCenter /= static_cast<float>(leftEyeIdentifiers.size());
	cv::Scalar interEyeDistance = cv::norm(rightEyeCenter, leftEyeCenter, cv::NORM_L2);
	return interEyeDistance[0];
};

} /* namespace rcr */

#endif /* HELPERS_HPP_ */
<|endoftext|>


<commit_before>/**
 * This file is part of the "libfnord" project
 *   Copyright (c) 2015 Paul Asmuth
 *
 * FnordMetric is free software: you can redistribute it and/or modify it under
 * the terms of the GNU General Public License v3.0. You should have received a
 * copy of the GNU General Public License along with this program. If not, see
 * <http://www.gnu.org/licenses/>.
 */
#include <stx/stdtypes.h>
#include <stx/logging.h>
#include <stx/io/fileutil.h>
#include <stx/io/mmappedfile.h>
#include <stx/protobuf/msg.h>
#include <stx/wallclock.h>
#include <zbase/core/CSTableIndex.h>
#include <zbase/core/CSTableIndexBuildState.pb.h>
#include <zbase/core/RecordSet.h>
#include <zbase/core/LogPartitionReader.h>
#include <stx/protobuf/MessageDecoder.h>
#include <cstable/RecordShredder.h>
#include <cstable/CSTableWriter.h>

using namespace stx;

namespace zbase {

CSTableIndex::CSTableIndex(
    PartitionMap* pmap,
    size_t nthreads) :
    nthreads_(nthreads),
    queue_([] (
        const Pair<uint64_t, RefPtr<Partition>>& a,
        const Pair<uint64_t, RefPtr<Partition>>& b) {
      return a.first < b.first;
    }),
    running_(false) {
  pmap->subscribeToPartitionChanges([this] (
      RefPtr<zbase::PartitionChangeNotification> change) {
    enqueuePartition(change->partition);
  });

  start();
}

CSTableIndex::~CSTableIndex() {
  stop();
}

bool CSTableIndex::needsUpdate(
    RefPtr<PartitionSnapshot> snap) const {
  String tbl_uuid((char*) snap->uuid().data(), snap->uuid().size());

  auto metapath = FileUtil::joinPaths(snap->base_path, "_cstable_state");

  if (FileUtil::exists(metapath)) {
    auto metadata = msg::decode<CSTableIndexBuildState>(
        FileUtil::read(metapath));

    if (metadata.uuid() == tbl_uuid &&
        metadata.offset() >= snap->nrecs) {
      return false;
    }
  }

  return true;
}

void CSTableIndex::buildCSTable(RefPtr<Partition> partition) {
  auto table = partition->getTable();
  if (table->storage() != zbase::TBL_STORAGE_LOG) {
    return;
  }

  auto t0 = WallClock::unixMicros();
  auto snap = partition->getSnapshot();

  if (!needsUpdate(snap)) {
    return;
  }

  logDebug(
      "tsdb",
      "Building CSTable index for partition $0/$1/$2",
      snap->state.tsdb_namespace(),
      table->name(),
      snap->key.toString());

  auto filepath = FileUtil::joinPaths(snap->base_path, "_cstable");
  auto filepath_tmp = filepath + "." + Random::singleton()->hex128();
  auto schema = table->schema();

  {
    auto cstable = cstable::CSTableWriter::createFile(
        filepath_tmp,
        cstable::BinaryFormatVersion::v0_1_0,
        cstable::TableSchema::fromProtobuf(*schema));

    cstable::RecordShredder shredder(cstable.get());

    auto reader_ptr = partition->getReader();
    auto& reader = dynamic_cast<LogPartitionReader&>(*reader_ptr);

    reader.fetchRecords([&schema, &shredder] (const Buffer& record) {
      msg::MessageObject obj;
      msg::MessageDecoder::decode(record.data(), record.size(), *schema, &obj);
      shredder.addRecordFromProtobuf(obj, *schema);
    });

    cstable->commit();
  }

  auto metapath = FileUtil::joinPaths(snap->base_path, "_cstable_state");
  auto metapath_tmp = metapath + "." + Random::singleton()->hex128();
  {
    auto metafile = File::openFile(
        metapath_tmp,
        File::O_CREATE | File::O_WRITE);

    CSTableIndexBuildState metadata;
    metadata.set_offset(snap->nrecs);
    metadata.set_uuid(snap->uuid().data(), snap->uuid().size());

    auto buf = msg::encode(metadata);
    metafile.write(buf->data(), buf->size());
  }

  FileUtil::mv(filepath_tmp, filepath);
  FileUtil::mv(metapath_tmp, metapath);

  auto t1 = WallClock::unixMicros();
  logDebug(
      "tsdb",
      "Commiting CSTable index for partition $0/$1/$2, building took $3s",
      snap->state.tsdb_namespace(),
      table->name(),
      snap->key.toString(),
      (double) (t1 - t0) / 1000000.0f);
}

void CSTableIndex::enqueuePartition(RefPtr<Partition> partition) {
  std::unique_lock<std::mutex> lk(mutex_);
  enqueuePartitionWithLock(partition);
}

void CSTableIndex::enqueuePartitionWithLock(RefPtr<Partition> partition) {
  auto interval = partition->getTable()->cstableBuildInterval();

  auto uuid = partition->uuid();
  if (waitset_.count(uuid) > 0) {
    return;
  }

  queue_.emplace(
      WallClock::unixMicros() + interval.microseconds(),
      partition);

  waitset_.emplace(uuid);
  cv_.notify_all();
}

void CSTableIndex::start() {
  running_ = true;

  for (int i = 0; i < nthreads_; ++i) {
    threads_.emplace_back(std::bind(&CSTableIndex::work, this));
  }
}

void CSTableIndex::stop() {
  if (!running_) {
    return;
  }

  running_ = false;
  cv_.notify_all();

  for (auto& t : threads_) {
    t.join();
  }
}

void CSTableIndex::work() {
  std::unique_lock<std::mutex> lk(mutex_);

  while (running_) {
    if (queue_.size() == 0) {
      cv_.wait(lk);
    }

    if (queue_.size() == 0) {
      continue;
    }

    auto now = WallClock::unixMicros();
    if (now < queue_.begin()->first) {
      cv_.wait_for(
          lk,
          std::chrono::microseconds(queue_.begin()->first - now));

      continue;
    }

    auto partition = queue_.begin()->second;
    queue_.erase(queue_.begin());

    bool success = true;
    {
      lk.unlock();

      try {
        buildCSTable(partition);
      } catch (const StandardException& e) {
        logError("tsdb", e, "CSTableIndex error");
        success = false;
      }

      lk.lock();
    }

    if (success) {
      waitset_.erase(partition->uuid());

      if (needsUpdate(partition->getSnapshot())) {
        enqueuePartitionWithLock(partition);
      }
    } else {
      auto delay = 30 * kMicrosPerSecond; // FIXPAUL increasing delay..
      queue_.emplace(now + delay, partition);
    }
  }
}

} // namespace zbase
<commit_msg>abort if cstable is too large<commit_after>/**
 * This file is part of the "libfnord" project
 *   Copyright (c) 2015 Paul Asmuth
 *
 * FnordMetric is free software: you can redistribute it and/or modify it under
 * the terms of the GNU General Public License v3.0. You should have received a
 * copy of the GNU General Public License along with this program. If not, see
 * <http://www.gnu.org/licenses/>.
 */
#include <stx/stdtypes.h>
#include <stx/logging.h>
#include <stx/io/fileutil.h>
#include <stx/io/mmappedfile.h>
#include <stx/protobuf/msg.h>
#include <stx/wallclock.h>
#include <zbase/core/CSTableIndex.h>
#include <zbase/core/CSTableIndexBuildState.pb.h>
#include <zbase/core/RecordSet.h>
#include <zbase/core/LogPartitionReader.h>
#include <stx/protobuf/MessageDecoder.h>
#include <cstable/RecordShredder.h>
#include <cstable/CSTableWriter.h>

using namespace stx;

namespace zbase {

CSTableIndex::CSTableIndex(
    PartitionMap* pmap,
    size_t nthreads) :
    nthreads_(nthreads),
    queue_([] (
        const Pair<uint64_t, RefPtr<Partition>>& a,
        const Pair<uint64_t, RefPtr<Partition>>& b) {
      return a.first < b.first;
    }),
    running_(false) {
  pmap->subscribeToPartitionChanges([this] (
      RefPtr<zbase::PartitionChangeNotification> change) {
    enqueuePartition(change->partition);
  });

  start();
}

CSTableIndex::~CSTableIndex() {
  stop();
}

bool CSTableIndex::needsUpdate(
    RefPtr<PartitionSnapshot> snap) const {
  String tbl_uuid((char*) snap->uuid().data(), snap->uuid().size());

  auto metapath = FileUtil::joinPaths(snap->base_path, "_cstable_state");

  if (FileUtil::exists(metapath)) {
    auto metadata = msg::decode<CSTableIndexBuildState>(
        FileUtil::read(metapath));

    if (metadata.uuid() == tbl_uuid &&
        metadata.offset() >= snap->nrecs) {
      return false;
    }
  }

  return true;
}

void CSTableIndex::buildCSTable(RefPtr<Partition> partition) {
  auto table = partition->getTable();
  if (table->storage() != zbase::TBL_STORAGE_LOG) {
    return;
  }

  auto t0 = WallClock::unixMicros();
  auto snap = partition->getSnapshot();

  if (!needsUpdate(snap)) {
    return;
  }

  logDebug(
      "tsdb",
      "Building CSTable index for partition $0/$1/$2",
      snap->state.tsdb_namespace(),
      table->name(),
      snap->key.toString());

  auto filepath = FileUtil::joinPaths(snap->base_path, "_cstable");
  auto filepath_tmp = filepath + "." + Random::singleton()->hex128();
  auto schema = table->schema();

  {
    auto cstable = cstable::CSTableWriter::createFile(
        filepath_tmp,
        cstable::BinaryFormatVersion::v0_1_0,
        cstable::TableSchema::fromProtobuf(*schema));

    cstable::RecordShredder shredder(cstable.get());

    auto reader_ptr = partition->getReader();
    auto& reader = dynamic_cast<LogPartitionReader&>(*reader_ptr);

    size_t total_size = 0;
    reader.fetchRecords([&schema, &shredder, &total_size, &snap, &table] (const Buffer& record) {
      msg::MessageObject obj;
      msg::MessageDecoder::decode(record.data(), record.size(), *schema, &obj);
      shredder.addRecordFromProtobuf(obj, *schema);

      total_size += record.size();
      static const size_t kMaxTableSize = 1024 * 1024 * 1024 * 4;
      if (total_size > kMaxTableSize) {
        RAISEF(
            kRuntimeError,
            "CSTable is too large $0/$1/$2",
            snap->state.tsdb_namespace(),
            table->name(),
            snap->key.toString());
      }
    });

    cstable->commit();
  }

  auto metapath = FileUtil::joinPaths(snap->base_path, "_cstable_state");
  auto metapath_tmp = metapath + "." + Random::singleton()->hex128();
  {
    auto metafile = File::openFile(
        metapath_tmp,
        File::O_CREATE | File::O_WRITE);

    CSTableIndexBuildState metadata;
    metadata.set_offset(snap->nrecs);
    metadata.set_uuid(snap->uuid().data(), snap->uuid().size());

    auto buf = msg::encode(metadata);
    metafile.write(buf->data(), buf->size());
  }

  FileUtil::mv(filepath_tmp, filepath);
  FileUtil::mv(metapath_tmp, metapath);

  auto t1 = WallClock::unixMicros();
  logDebug(
      "tsdb",
      "Commiting CSTable index for partition $0/$1/$2, building took $3s",
      snap->state.tsdb_namespace(),
      table->name(),
      snap->key.toString(),
      (double) (t1 - t0) / 1000000.0f);
}

void CSTableIndex::enqueuePartition(RefPtr<Partition> partition) {
  std::unique_lock<std::mutex> lk(mutex_);
  enqueuePartitionWithLock(partition);
}

void CSTableIndex::enqueuePartitionWithLock(RefPtr<Partition> partition) {
  auto interval = partition->getTable()->cstableBuildInterval();

  auto uuid = partition->uuid();
  if (waitset_.count(uuid) > 0) {
    return;
  }

  queue_.emplace(
      WallClock::unixMicros() + interval.microseconds(),
      partition);

  waitset_.emplace(uuid);
  cv_.notify_all();
}

void CSTableIndex::start() {
  running_ = true;

  for (int i = 0; i < nthreads_; ++i) {
    threads_.emplace_back(std::bind(&CSTableIndex::work, this));
  }
}

void CSTableIndex::stop() {
  if (!running_) {
    return;
  }

  running_ = false;
  cv_.notify_all();

  for (auto& t : threads_) {
    t.join();
  }
}

void CSTableIndex::work() {
  std::unique_lock<std::mutex> lk(mutex_);

  while (running_) {
    if (queue_.size() == 0) {
      cv_.wait(lk);
    }

    if (queue_.size() == 0) {
      continue;
    }

    auto now = WallClock::unixMicros();
    if (now < queue_.begin()->first) {
      cv_.wait_for(
          lk,
          std::chrono::microseconds(queue_.begin()->first - now));

      continue;
    }

    auto partition = queue_.begin()->second;
    queue_.erase(queue_.begin());

    bool success = true;
    {
      lk.unlock();

      try {
        buildCSTable(partition);
      } catch (const StandardException& e) {
        logError("tsdb", e, "CSTableIndex error");
        success = false;
      }

      lk.lock();
    }

    if (success) {
      waitset_.erase(partition->uuid());

      if (needsUpdate(partition->getSnapshot())) {
        enqueuePartitionWithLock(partition);
      }
    } else {
      auto delay = 30 * kMicrosPerSecond; // FIXPAUL increasing delay..
      queue_.emplace(now + delay, partition);
    }
  }
}

} // namespace zbase
<|endoftext|>


<commit_before>/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
   Copyright 2022 The StableHLO Authors.

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 "stablehlo/dialect/Register.h"

#include "stablehlo/dialect/ChloOps.h"
#include "stablehlo/dialect/StablehloOps.h"

namespace mlir {
namespace stablehlo {

void registerAllDialects(mlir::DialectRegistry &registry) {
  // clang-format off
  registry.insert<mlir::chlo::ChloDialect,
                  mlir::stablehlo::StablehloDialect>();
  // clang-format on
}

}  // namespace stablehlo
}  // namespace mlir
<commit_msg>Add SparseTensorDialect to  registration (#483)<commit_after>/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
   Copyright 2022 The StableHLO Authors.

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 "stablehlo/dialect/Register.h"

#include "mlir/Dialect/SparseTensor/IR/SparseTensor.h"
#include "stablehlo/dialect/ChloOps.h"
#include "stablehlo/dialect/StablehloOps.h"

namespace mlir {
namespace stablehlo {

void registerAllDialects(mlir::DialectRegistry &registry) {
  // clang-format off
  registry.insert<mlir::sparse_tensor::SparseTensorDialect>();
  registry.insert<mlir::chlo::ChloDialect,
                  mlir::stablehlo::StablehloDialect>();
  // clang-format on
}

}  // namespace stablehlo
}  // namespace mlir
<|endoftext|>


<commit_before>// ------------------------------------------------------------------
// pion-net: a C++ framework for building lightweight HTTP interfaces
// ------------------------------------------------------------------
// Copyright (C) 2007-2008 Atomic Labs, Inc.  (http://www.atomiclabs.com)
//
// Distributed under the Boost Software License, Version 1.0.
// See http://www.boost.org/LICENSE_1_0.txt
//

#ifndef __PION_HTTPTYPES_HEADER__
#define __PION_HTTPTYPES_HEADER__

#include <string>
#include <cctype>
#include <pion/PionConfig.hpp>
#include <pion/PionHashMap.hpp>

namespace pion {	// begin namespace pion
namespace net {		// begin namespace net (Pion Network Library)

///
/// HTTPTypes: common data types used by HTTP
///
struct PION_NET_API HTTPTypes
{
	/// virtual destructor
	virtual ~HTTPTypes() {}

	// generic strings used by HTTP
	static const std::string	STRING_EMPTY;
	static const std::string	STRING_CRLF;
	static const std::string	STRING_HTTP_VERSION;
	static const std::string	HEADER_NAME_VALUE_DELIMITER;

	// common HTTP header names
	static const std::string	HEADER_HOST;
	static const std::string	HEADER_COOKIE;
	static const std::string	HEADER_SET_COOKIE;
	static const std::string	HEADER_CONNECTION;
	static const std::string	HEADER_CONTENT_TYPE;
	static const std::string	HEADER_CONTENT_LENGTH;
	static const std::string	HEADER_CONTENT_LOCATION;
	static const std::string	HEADER_LAST_MODIFIED;
	static const std::string	HEADER_IF_MODIFIED_SINCE;
	static const std::string	HEADER_TRANSFER_ENCODING;
	static const std::string	HEADER_LOCATION;

	// common HTTP content types
	static const std::string	CONTENT_TYPE_HTML;
	static const std::string	CONTENT_TYPE_TEXT;
	static const std::string	CONTENT_TYPE_XML;
	static const std::string	CONTENT_TYPE_URLENCODED;

	// common HTTP request methods
	static const std::string	REQUEST_METHOD_HEAD;
	static const std::string	REQUEST_METHOD_GET;
	static const std::string	REQUEST_METHOD_PUT;
	static const std::string	REQUEST_METHOD_POST;
	static const std::string	REQUEST_METHOD_DELETE;

	// common HTTP response messages
	static const std::string	RESPONSE_MESSAGE_OK;
	static const std::string	RESPONSE_MESSAGE_CREATED;
	static const std::string	RESPONSE_MESSAGE_NO_CONTENT;
	static const std::string	RESPONSE_MESSAGE_FORBIDDEN;
	static const std::string	RESPONSE_MESSAGE_NOT_FOUND;
	static const std::string	RESPONSE_MESSAGE_METHOD_NOT_ALLOWED;
	static const std::string	RESPONSE_MESSAGE_NOT_MODIFIED;
	static const std::string	RESPONSE_MESSAGE_BAD_REQUEST;
	static const std::string	RESPONSE_MESSAGE_SERVER_ERROR;
	static const std::string	RESPONSE_MESSAGE_NOT_IMPLEMENTED;

	// common HTTP response codes
	static const unsigned int	RESPONSE_CODE_OK;
	static const unsigned int	RESPONSE_CODE_CREATED;
	static const unsigned int	RESPONSE_CODE_NO_CONTENT;
	static const unsigned int	RESPONSE_CODE_FORBIDDEN;
	static const unsigned int	RESPONSE_CODE_NOT_FOUND;
	static const unsigned int	RESPONSE_CODE_METHOD_NOT_ALLOWED;
	static const unsigned int	RESPONSE_CODE_NOT_MODIFIED;
	static const unsigned int	RESPONSE_CODE_BAD_REQUEST;
	static const unsigned int	RESPONSE_CODE_SERVER_ERROR;
	static const unsigned int	RESPONSE_CODE_NOT_IMPLEMENTED;

	/// returns true if two strings are equal (ignoring case)
	struct CaseInsensitiveEqual {
		inline bool operator()(const std::string& str1, const std::string& str2) const {
			if (str1.size() != str2.size())
				return false;
			std::string::const_iterator it1 = str1.begin();
			std::string::const_iterator it2 = str2.begin();
			while ( (it1!=str1.end()) && (it2!=str2.end()) ) {
				if (tolower(*it1) != tolower(*it2))
					return false;
				++it1;
				++it2;
			}
			return true;
		}
	};

	/// case insensitive hash function for std::string
	struct CaseInsensitiveHash {
		inline unsigned long operator()(const std::string& str) const {
			unsigned long value = 0;
			for (std::string::const_iterator i = str.begin(); i!= str.end(); ++i)
				value = static_cast<unsigned char>(tolower(*i)) + (value << 6) + (value << 16) - value;
			return value;
		}
	};

	/// returns true if str1 < str2 (ignoring case)
	struct CaseInsensitiveLess {
		inline bool operator()(const std::string& str1, const std::string& str2) const {
			std::string::const_iterator it1 = str1.begin();
			std::string::const_iterator it2 = str2.begin();
			while ( (it1 != str1.end()) && (it2 != str2.end()) ) {
				if (tolower(*it1) != tolower(*it2))
					return (tolower(*it1) < tolower(*it2));
				++it1;
				++it2;
			}
			return (str1.size() < str2.size());
		}
	};

	/// case insensitive extension of stdext::hash_compare for std::string
	struct CaseInsensitiveHashCompare : public stdext::hash_compare<std::string, CaseInsensitiveLess> {
		// makes operator() with two arguments visible, otherwise it would be hidden by the operator() defined here
		using stdext::hash_compare<std::string, CaseInsensitiveLess>::operator();

		inline size_t operator()(const std::string& str) const {
			return CaseInsensitiveHash()(str);
		}
	};

	/// use case-insensitive comparisons for HTTP header names
#ifdef _MSC_VER
	typedef PION_HASH_MULTIMAP<std::string, std::string, CaseInsensitiveHashCompare>	Headers;
#else
	typedef PION_HASH_MULTIMAP<std::string, std::string, CaseInsensitiveHash, CaseInsensitiveEqual >	Headers;
#endif

	/// data type for a dictionary of strings (used for HTTP headers)
	typedef PION_HASH_MULTIMAP<std::string, std::string, PION_HASH_STRING >	StringDictionary;

	/// data type for HTTP query parameters
	typedef StringDictionary	QueryParams;

	/// data type for HTTP cookie parameters
	typedef StringDictionary	CookieParams;

	/// escapes URL-encoded strings (a%20value+with%20spaces)
	static std::string url_decode(const std::string& str);

	/// encodes strings so that they are safe for URLs (with%20spaces)
	static std::string url_encode(const std::string& str);

	/// converts time_t format into an HTTP-date string
	static std::string get_date_string(const time_t t);

	/// builds an HTTP query string from a collection of query parameters
	static std::string make_query_string(const QueryParams& query_params);

	/**
	 * creates a "Set-Cookie" header
	 *
	 * @param name the name of the cookie
	 * @param value the value of the cookie
	 * @param path the path of the cookie
	 * @param has_max_age true if the max_age value should be set
	 * @param max_age the life of the cookie, in seconds (0 = discard)
	 *
	 * @return the new "Set-Cookie" header
	 */
	static std::string make_set_cookie_header(const std::string& name,
											  const std::string& value,
											  const std::string& path,
											  const bool has_max_age = false,
											  const unsigned long max_age = 0);
};

}	// end namespace net
}	// end namespace pion

#endif
<commit_msg>Made some MSVC specific code conditionally compiled.<commit_after>// ------------------------------------------------------------------
// pion-net: a C++ framework for building lightweight HTTP interfaces
// ------------------------------------------------------------------
// Copyright (C) 2007-2008 Atomic Labs, Inc.  (http://www.atomiclabs.com)
//
// Distributed under the Boost Software License, Version 1.0.
// See http://www.boost.org/LICENSE_1_0.txt
//

#ifndef __PION_HTTPTYPES_HEADER__
#define __PION_HTTPTYPES_HEADER__

#include <string>
#include <cctype>
#include <pion/PionConfig.hpp>
#include <pion/PionHashMap.hpp>

namespace pion {	// begin namespace pion
namespace net {		// begin namespace net (Pion Network Library)

///
/// HTTPTypes: common data types used by HTTP
///
struct PION_NET_API HTTPTypes
{
	/// virtual destructor
	virtual ~HTTPTypes() {}

	// generic strings used by HTTP
	static const std::string	STRING_EMPTY;
	static const std::string	STRING_CRLF;
	static const std::string	STRING_HTTP_VERSION;
	static const std::string	HEADER_NAME_VALUE_DELIMITER;

	// common HTTP header names
	static const std::string	HEADER_HOST;
	static const std::string	HEADER_COOKIE;
	static const std::string	HEADER_SET_COOKIE;
	static const std::string	HEADER_CONNECTION;
	static const std::string	HEADER_CONTENT_TYPE;
	static const std::string	HEADER_CONTENT_LENGTH;
	static const std::string	HEADER_CONTENT_LOCATION;
	static const std::string	HEADER_LAST_MODIFIED;
	static const std::string	HEADER_IF_MODIFIED_SINCE;
	static const std::string	HEADER_TRANSFER_ENCODING;
	static const std::string	HEADER_LOCATION;

	// common HTTP content types
	static const std::string	CONTENT_TYPE_HTML;
	static const std::string	CONTENT_TYPE_TEXT;
	static const std::string	CONTENT_TYPE_XML;
	static const std::string	CONTENT_TYPE_URLENCODED;

	// common HTTP request methods
	static const std::string	REQUEST_METHOD_HEAD;
	static const std::string	REQUEST_METHOD_GET;
	static const std::string	REQUEST_METHOD_PUT;
	static const std::string	REQUEST_METHOD_POST;
	static const std::string	REQUEST_METHOD_DELETE;

	// common HTTP response messages
	static const std::string	RESPONSE_MESSAGE_OK;
	static const std::string	RESPONSE_MESSAGE_CREATED;
	static const std::string	RESPONSE_MESSAGE_NO_CONTENT;
	static const std::string	RESPONSE_MESSAGE_FORBIDDEN;
	static const std::string	RESPONSE_MESSAGE_NOT_FOUND;
	static const std::string	RESPONSE_MESSAGE_METHOD_NOT_ALLOWED;
	static const std::string	RESPONSE_MESSAGE_NOT_MODIFIED;
	static const std::string	RESPONSE_MESSAGE_BAD_REQUEST;
	static const std::string	RESPONSE_MESSAGE_SERVER_ERROR;
	static const std::string	RESPONSE_MESSAGE_NOT_IMPLEMENTED;

	// common HTTP response codes
	static const unsigned int	RESPONSE_CODE_OK;
	static const unsigned int	RESPONSE_CODE_CREATED;
	static const unsigned int	RESPONSE_CODE_NO_CONTENT;
	static const unsigned int	RESPONSE_CODE_FORBIDDEN;
	static const unsigned int	RESPONSE_CODE_NOT_FOUND;
	static const unsigned int	RESPONSE_CODE_METHOD_NOT_ALLOWED;
	static const unsigned int	RESPONSE_CODE_NOT_MODIFIED;
	static const unsigned int	RESPONSE_CODE_BAD_REQUEST;
	static const unsigned int	RESPONSE_CODE_SERVER_ERROR;
	static const unsigned int	RESPONSE_CODE_NOT_IMPLEMENTED;

	/// returns true if two strings are equal (ignoring case)
	struct CaseInsensitiveEqual {
		inline bool operator()(const std::string& str1, const std::string& str2) const {
			if (str1.size() != str2.size())
				return false;
			std::string::const_iterator it1 = str1.begin();
			std::string::const_iterator it2 = str2.begin();
			while ( (it1!=str1.end()) && (it2!=str2.end()) ) {
				if (tolower(*it1) != tolower(*it2))
					return false;
				++it1;
				++it2;
			}
			return true;
		}
	};

	/// case insensitive hash function for std::string
	struct CaseInsensitiveHash {
		inline unsigned long operator()(const std::string& str) const {
			unsigned long value = 0;
			for (std::string::const_iterator i = str.begin(); i!= str.end(); ++i)
				value = static_cast<unsigned char>(tolower(*i)) + (value << 6) + (value << 16) - value;
			return value;
		}
	};

	/// returns true if str1 < str2 (ignoring case)
	struct CaseInsensitiveLess {
		inline bool operator()(const std::string& str1, const std::string& str2) const {
			std::string::const_iterator it1 = str1.begin();
			std::string::const_iterator it2 = str2.begin();
			while ( (it1 != str1.end()) && (it2 != str2.end()) ) {
				if (tolower(*it1) != tolower(*it2))
					return (tolower(*it1) < tolower(*it2));
				++it1;
				++it2;
			}
			return (str1.size() < str2.size());
		}
	};

#ifdef _MSC_VER
	/// case insensitive extension of stdext::hash_compare for std::string
	struct CaseInsensitiveHashCompare : public stdext::hash_compare<std::string, CaseInsensitiveLess> {
		// makes operator() with two arguments visible, otherwise it would be hidden by the operator() defined here
		using stdext::hash_compare<std::string, CaseInsensitiveLess>::operator();

		inline size_t operator()(const std::string& str) const {
			return CaseInsensitiveHash()(str);
		}
	};
#endif

	/// use case-insensitive comparisons for HTTP header names
#ifdef _MSC_VER
	typedef PION_HASH_MULTIMAP<std::string, std::string, CaseInsensitiveHashCompare>	Headers;
#else
	typedef PION_HASH_MULTIMAP<std::string, std::string, CaseInsensitiveHash, CaseInsensitiveEqual >	Headers;
#endif

	/// data type for a dictionary of strings (used for HTTP headers)
	typedef PION_HASH_MULTIMAP<std::string, std::string, PION_HASH_STRING >	StringDictionary;

	/// data type for HTTP query parameters
	typedef StringDictionary	QueryParams;

	/// data type for HTTP cookie parameters
	typedef StringDictionary	CookieParams;

	/// escapes URL-encoded strings (a%20value+with%20spaces)
	static std::string url_decode(const std::string& str);

	/// encodes strings so that they are safe for URLs (with%20spaces)
	static std::string url_encode(const std::string& str);

	/// converts time_t format into an HTTP-date string
	static std::string get_date_string(const time_t t);

	/// builds an HTTP query string from a collection of query parameters
	static std::string make_query_string(const QueryParams& query_params);

	/**
	 * creates a "Set-Cookie" header
	 *
	 * @param name the name of the cookie
	 * @param value the value of the cookie
	 * @param path the path of the cookie
	 * @param has_max_age true if the max_age value should be set
	 * @param max_age the life of the cookie, in seconds (0 = discard)
	 *
	 * @return the new "Set-Cookie" header
	 */
	static std::string make_set_cookie_header(const std::string& name,
											  const std::string& value,
											  const std::string& path,
											  const bool has_max_age = false,
											  const unsigned long max_age = 0);
};

}	// end namespace net
}	// end namespace pion

#endif
<|endoftext|>