<commit_before>// $Id: LogStream_test.C,v 1.6 2000/05/29 23:45:27 amoll Exp $
#include <BALL/CONCEPT/classTest.h>

///////////////////////////
#include <BALL/COMMON/logStream.h>
#include <sys/time.h>
#include <BALL/MATHS/common.h>
///////////////////////////

START_TEST(class_name, "$Id: LogStream_test.C,v 1.6 2000/05/29 23:45:27 amoll Exp $")

/////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////

using namespace BALL;
using namespace std;
String filename;

LogStream* l1;
LogStream* l2;

CHECK(LogStream(bool associate_stdio = false))
	l1 = new LogStream();
	l2 = new LogStream(true);
	TEST_NOT_EQUAL(l1, 0)
	TEST_NOT_EQUAL(l2, 0)
RESULT

CHECK(~LogStream())
	delete l1;
	delete l2;
RESULT

CHECK(LogStream(LogStreamBuf* buf))
	LogStream* l1;
	LogStreamBuf* lb1;
	l1 = new LogStream(lb1);
	TEST_NOT_EQUAL(l1, 0)
RESULT

CHECK(rdbuf())
	LogStream l1;
	TEST_NOT_EQUAL(l1.rdbuf(), 0)
RESULT

CHECK(operator -> ())
	LogStream l1;
	l1->sync();
RESULT

CHECK(setLevel(int level))
	LogStream l1;
	l1 << "TEST1" <<endl;
	l1.setLevel(99);
	l1 << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(0), 0)
	TEST_EQUAL(l1.getLineLevel(1), 99)
RESULT

CHECK(l1.getLevel())
	LogStream l1;
	TEST_EQUAL(l1.getLevel(), 0)
	l1.setLevel(99);
	TEST_EQUAL(l1.getLevel(), 99)
RESULT

CHECK(level(int n))
	LogStream l1;
	l1.level(99) << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), 99)
RESULT

CHECK(info(int n = 0))
	LogStream l1;
	l1.info() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::INFORMATION)
	l1.info(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::INFORMATION + 1)
RESULT

CHECK(error(int n = 0))
	LogStream l1;
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::ERROR)
	l1.error(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::ERROR + 1)
RESULT

CHECK(warn(int n = 0))
	LogStream l1;
	l1.warn() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::WARNING)
	l1.warn(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::WARNING + 1)
RESULT

CHECK(insert(std::ostream& s, int min_level = INT_MIN, int max_level = INT_MAX))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 99, 99);
	l1.level(98) << "X" << endl;
	l1.level(99) << "1" << endl;
	l1.info(99)  << "2" << endl;
	l1.level(100)<< "X" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 4)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(remove(std::ostream& s))
	LogStream l1;
	ofstream s;
	l1.insert(s);
	l1.remove(s);
RESULT

CHECK(insertNotification(const std::ostream& s, const Target& target))
// BAUSTELLE
RESULT

CHECK(removeNotification(const std::ostream& s))
// BAUSTELLE
RESULT

CHECK(setMinLevel(const std::ostream& s, int min_level))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 0);
	l1.setMinLevel(s, 98);
	l1.info(97) << "X" << endl;
	l1.info(98) << "1" << endl;
	l1.info(99) << "2" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 3)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(setMaxLevel(const std::ostream& s, int max_level))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 0);
	l1.setMaxLevel(s, 98);
	l1.info(97) << "1" << endl;
	l1.info(98) << "2" << endl;
	l1.info(99) << "X" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 3)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(setPrefix(const std::ostream& s, const string& prefix))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);;
	l1.insert(s, 0);
	l1.setPrefix(s, "%l"); //loglevel
	l1.info(1) << "  1." << endl;
	l1.setPrefix(s, "%y"); //message type ("Error", "Warning", "Information", "-")
	l1.info(2) << "  2." << endl;
	l1.setPrefix(s, "%T"); //time (HH:MM:SS)
	l1.info(3) << "  3." << endl;
	l1.setPrefix(s, "%t"); //time in short format (HH:MM)
	l1.info(4) << "  4." << endl;
	l1.setPrefix(s, "%D"); //date (DD.MM.YYYY)
	l1.info(5) << "  5." << endl;
	l1.setPrefix(s, "%d"); // date in short format (DD.MM.)
	l1.info(6) << "  6." << endl;
	l1.setPrefix(s, "%S"); //time and date (DD.MM.YYYY, HH:MM:SS)
	l1.info(7) << "  7." << endl;
	l1.setPrefix(s, "%s"); //time and date in short format (DD.MM., HH:MM)
	l1.info(8) << "  8." << endl;
	l1.setPrefix(s, "%%"); //percent sign (escape sequence)
	l1.info(9) << "  9." << endl;
	l1.setPrefix(s, ""); //no prefix
	l1.info(10) << " 10." << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 10)
	TEST_FILE(filename.c_str(), "data/LogStream_test_setPrefix.txt", true)
RESULT

CHECK(clear())
	LogStream l1;
	l1.error() << "TEST" <<endl;
	l1.clear();
	TEST_EQUAL(l1.getNumberOfLines(), 0)
RESULT

CHECK(getNumberOfLines(int min_level = INT_MIN, int max_level = INT_MAX))
	LogStream l1;
	TEST_EQUAL(l1.getNumberOfLines(), 0)
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
RESULT

CHECK(getLineText(Index index))
	LogStream l1;
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getLineText(0), "TEST")
RESULT

CHECK(getLineTime(Index index))
	LogStream l1;
	time_t timer;
  timer = time(NULL);
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(timer, l1.getLineTime(0))
	TEST_EQUAL(Maths::isNear(timer, l1.getLineTime(0), (long)1), true)
RESULT

CHECK(getLineLevel(Index index))
	LogStream l1;
	l1.level(99) << "TEST" <<endl;
	TEST_EQUAL(l1.getLineLevel(0), 99)
RESULT

CHECK(filterLines(const int min_level = INT_MIN, const int max_level = INT_MAX,
									const time_t earliest = 0, const time_t latest = LONG_MAX, const string& s = ""))
	LogStream l1;
  using std::list;
	list<int>	liste;

	l1.level(0) << "TEST1" << endl;
	l1.level(1) << "TEST2" << endl;
	l1.level(2) << "XXXXX" << endl;
	time_t timer = time(NULL);
	time_t x = timer;
	while (x == timer)
	{
		x = time(NULL);
	}
	timer = time(NULL);
	l1.level(3) << "XXXXX" << endl;
	l1.level(4) << "TEST4" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 5)

	liste = l1.filterLines(1, 2, 0, LONG_MAX, "" );
	TEST_EQUAL(liste.size(), 2)
	TEST_EQUAL(liste.front(), 1)
	liste.pop_front();
	TEST_EQUAL(liste.front(), 2)
	liste.clear();

	liste = l1.filterLines(1, 2, 0, LONG_MAX, "XXXXX" );
	TEST_EQUAL(liste.size(), 1)
	TEST_EQUAL(liste.front(), 2)
	liste.clear();

	liste = l1.filterLines(3, 3, timer, LONG_MAX, "XXXXX");
	TEST_EQUAL(liste.size(), 1)
	TEST_EQUAL(liste.front(), 3)
	liste.clear();
RESULT
/////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////
END_TEST
<commit_msg>fixed: incorrect/incomplete test for constructor<commit_after>// $Id: LogStream_test.C,v 1.7 2000/06/07 09:35:07 oliver Exp $
#include <BALL/CONCEPT/classTest.h>

///////////////////////////
#include <BALL/COMMON/logStream.h>
#include <sys/time.h>
#include <BALL/MATHS/common.h>
///////////////////////////

START_TEST(class_name, "$Id: LogStream_test.C,v 1.7 2000/06/07 09:35:07 oliver Exp $")

/////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////

using namespace BALL;
using namespace std;
String filename;

LogStream* l1;
LogStream* l2;

CHECK(LogStream(bool associate_stdio = false))
	l1 = new LogStream();
	l2 = new LogStream(true);
	TEST_NOT_EQUAL(l1, 0)
	TEST_NOT_EQUAL(l2, 0)
RESULT

CHECK(~LogStream())
	delete l1;
	delete l2;
RESULT

CHECK(LogStream(LogStreamBuf* buf))
	LogStream* l1;
	l1 = new LogStream((LogStreamBuf*)0);
	TEST_NOT_EQUAL(l1, 0)
	delete l1;

	LogStream* l2;
	LogStreamBuf* lb2 = new LogStreamBuf;
	l2 = new LogStream(lb2);
	TEST_NOT_EQUAL(l2, 0)
	delete l2;
RESULT

CHECK(rdbuf())
	LogStream l1;
	TEST_NOT_EQUAL(l1.rdbuf(), 0)
RESULT

CHECK(operator -> ())
	LogStream l1;
	l1->sync();
RESULT

CHECK(setLevel(int level))
	LogStream l1;
	l1 << "TEST1" <<endl;
	l1.setLevel(99);
	l1 << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(0), 0)
	TEST_EQUAL(l1.getLineLevel(1), 99)
RESULT

CHECK(l1.getLevel())
	LogStream l1;
	TEST_EQUAL(l1.getLevel(), 0)
	l1.setLevel(99);
	TEST_EQUAL(l1.getLevel(), 99)
RESULT

CHECK(level(int n))
	LogStream l1;
	l1.level(99) << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), 99)
RESULT

CHECK(info(int n = 0))
	LogStream l1;
	l1.info() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::INFORMATION)
	l1.info(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::INFORMATION + 1)
RESULT

CHECK(error(int n = 0))
	LogStream l1;
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::ERROR)
	l1.error(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::ERROR + 1)
RESULT

CHECK(warn(int n = 0))
	LogStream l1;
	l1.warn() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
	TEST_EQUAL(l1.getLineText(0), "TEST")
	TEST_EQUAL(l1.getLineLevel(0), LogStream::WARNING)
	l1.warn(1) << "TEST2" <<endl;
	TEST_EQUAL(l1.getLineLevel(1), LogStream::WARNING + 1)
RESULT

CHECK(insert(std::ostream& s, int min_level = INT_MIN, int max_level = INT_MAX))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 99, 99);
	l1.level(98) << "X" << endl;
	l1.level(99) << "1" << endl;
	l1.info(99)  << "2" << endl;
	l1.level(100)<< "X" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 4)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(remove(std::ostream& s))
	LogStream l1;
	ofstream s;
	l1.insert(s);
	l1.remove(s);
RESULT

CHECK(insertNotification(const std::ostream& s, const Target& target))
// BAUSTELLE
RESULT

CHECK(removeNotification(const std::ostream& s))
// BAUSTELLE
RESULT

CHECK(setMinLevel(const std::ostream& s, int min_level))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 0);
	l1.setMinLevel(s, 98);
	l1.info(97) << "X" << endl;
	l1.info(98) << "1" << endl;
	l1.info(99) << "2" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 3)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(setMaxLevel(const std::ostream& s, int max_level))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);
	l1.insert(s, 0);
	l1.setMaxLevel(s, 98);
	l1.info(97) << "1" << endl;
	l1.info(98) << "2" << endl;
	l1.info(99) << "X" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 3)
	TEST_FILE(filename.c_str(), "data/LogStream_test_general.txt", false)
RESULT

CHECK(setPrefix(const std::ostream& s, const string& prefix))
	NEW_TMP_FILE(filename)
	LogStream l1;
	ofstream s(filename.c_str(), std::ios::out);;
	l1.insert(s, 0);
	l1.setPrefix(s, "%l"); //loglevel
	l1.info(1) << "  1." << endl;
	l1.setPrefix(s, "%y"); //message type ("Error", "Warning", "Information", "-")
	l1.info(2) << "  2." << endl;
	l1.setPrefix(s, "%T"); //time (HH:MM:SS)
	l1.info(3) << "  3." << endl;
	l1.setPrefix(s, "%t"); //time in short format (HH:MM)
	l1.info(4) << "  4." << endl;
	l1.setPrefix(s, "%D"); //date (DD.MM.YYYY)
	l1.info(5) << "  5." << endl;
	l1.setPrefix(s, "%d"); // date in short format (DD.MM.)
	l1.info(6) << "  6." << endl;
	l1.setPrefix(s, "%S"); //time and date (DD.MM.YYYY, HH:MM:SS)
	l1.info(7) << "  7." << endl;
	l1.setPrefix(s, "%s"); //time and date in short format (DD.MM., HH:MM)
	l1.info(8) << "  8." << endl;
	l1.setPrefix(s, "%%"); //percent sign (escape sequence)
	l1.info(9) << "  9." << endl;
	l1.setPrefix(s, ""); //no prefix
	l1.info(10) << " 10." << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 10)
	TEST_FILE(filename.c_str(), "data/LogStream_test_setPrefix.txt", true)
RESULT

CHECK(clear())
	LogStream l1;
	l1.error() << "TEST" <<endl;
	l1.clear();
	TEST_EQUAL(l1.getNumberOfLines(), 0)
RESULT

CHECK(getNumberOfLines(int min_level = INT_MIN, int max_level = INT_MAX))
	LogStream l1;
	TEST_EQUAL(l1.getNumberOfLines(), 0)
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getNumberOfLines(), 1)
RESULT

CHECK(getLineText(Index index))
	LogStream l1;
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(l1.getLineText(0), "TEST")
RESULT

CHECK(getLineTime(Index index))
	LogStream l1;
	time_t timer;
  timer = time(NULL);
	l1.error() << "TEST" <<endl;
	TEST_EQUAL(timer, l1.getLineTime(0))
	TEST_EQUAL(Maths::isNear(timer, l1.getLineTime(0), (long)1), true)
RESULT

CHECK(getLineLevel(Index index))
	LogStream l1;
	l1.level(99) << "TEST" <<endl;
	TEST_EQUAL(l1.getLineLevel(0), 99)
RESULT

CHECK(filterLines(const int min_level = INT_MIN, const int max_level = INT_MAX,
									const time_t earliest = 0, const time_t latest = LONG_MAX, const string& s = ""))
	LogStream l1;
  using std::list;
	list<int>	liste;

	l1.level(0) << "TEST1" << endl;
	l1.level(1) << "TEST2" << endl;
	l1.level(2) << "XXXXX" << endl;
	time_t timer = time(NULL);
	time_t x = timer;
	while (x == timer)
	{
		x = time(NULL);
	}
	timer = time(NULL);
	l1.level(3) << "XXXXX" << endl;
	l1.level(4) << "TEST4" << endl;
	TEST_EQUAL(l1.getNumberOfLines(), 5)

	liste = l1.filterLines(1, 2, 0, LONG_MAX, "" );
	TEST_EQUAL(liste.size(), 2)
	TEST_EQUAL(liste.front(), 1)
	liste.pop_front();
	TEST_EQUAL(liste.front(), 2)
	liste.clear();

	liste = l1.filterLines(1, 2, 0, LONG_MAX, "XXXXX" );
	TEST_EQUAL(liste.size(), 1)
	TEST_EQUAL(liste.front(), 2)
	liste.clear();

	liste = l1.filterLines(3, 3, timer, LONG_MAX, "XXXXX");
	TEST_EQUAL(liste.size(), 1)
	TEST_EQUAL(liste.front(), 3)
	liste.clear();
RESULT
/////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////
END_TEST
<|endoftext|>


<commit_before>// Given an array S of n integers, are there elements a, b, c in S such that a +
// b + c = 0? Find all unique triplets in the array which gives the sum of zero.
// Note: The solution set must not contain duplicate triplets.
// For example, given array S = [-1, 0, 1, 2, -1, -4],
// A solution set is:
// [
//   [-1, 0, 1],
//   [-1, -1, 2]
// ]

class Solution {
  public:
    vector<vector<int>> threeSum(vector<int> &nums) {
        sort(nums.begin(), nums.end());
        if (*num.begin() > 0 || *(nums.end() - 1) < 0)
            return vector<vector<int>>();

        set<vector<int>> result;
        if (nums[i] + nums[j] > 0)

            return vector<vector<int>>(result.begin(), result.end());
    }
};<commit_msg>working 015<commit_after>// Given an array S of n integers, are there elements a, b, c in S such that a +
// b + c = 0? Find all unique triplets in the array which gives the sum of zero.
// Note: The solution set must not contain duplicate triplets.
// For example, given array S = [-1, 0, 1, 2, -1, -4],
// A solution set is:
// [
//   [-1, 0, 1],
//   [-1, -1, 2]
// ]

class Solution {
  public:
    vector<vector<int>> threeSum(vector<int> &nums) {
        sort(nums.begin(), nums.end()); // nlog(n)
        vector<vector<int>> result;
        int sz = nums.size();
        // O(n^2)
        for (int i = 0; i < sz - 2; ++i) {
            int j = i + 1, k = sz - 1;
            while (j < k) {
                if (nums[j] + nums[k] < -nums[i])
                    ++j;
                else if (nums[j] + nums[k] > -nums[i])
                    --k;
                else {
                    // acutally i, j, k; just combine j++ and k-- here.
                    result.push_back({nums[i], nums[j++], nums[k--]});
                    // bypassing same elements (j, k)
                    while (j < k && nums[j] == nums[j - 1])
                        ++j;
                    while (j < k && nums[k] == nums[k + 1])
                        --k;
                }
            }
            // bypassing same elements (i)
            while (i < sz - 1 && nums[i + 1] == nums[i])
                ++i;
        }
        return result;
    }
};<|endoftext|>


<commit_before>/**
 * Appcelerator Titanium Mobile
 * Copyright (c) 2011 by Appcelerator, Inc. All Rights Reserved.
 * Licensed under the terms of the Apache Public License
 * Please see the LICENSE included with this distribution for details.
 */
#include <jni.h>
#include <v8.h>

#include "TypeConverter.h"
#include "JNIUtil.h"
#include "JavaObject.h"
#include "ProxyFactory.h"

using namespace titanium;

/****************************** public methods ******************************/
jshort TypeConverter::jsNumberToJavaShort(v8::Handle<v8::Number> jsNumber)
{
	return ((jshort) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaShortToJsNumber(jshort javaShort)
{
	return v8::Number::New((double) javaShort);
}

jint TypeConverter::jsNumberToJavaInt(v8::Handle<v8::Number> jsNumber)
{
	return ((jint) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaIntToJsNumber(jint javaInt)
{
	return v8::Number::New((double) javaInt);
}

jlong TypeConverter::jsNumberToJavaLong(v8::Handle<v8::Number> jsNumber)
{
	return ((jlong) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaLongToJsNumber(jlong javaLong)
{
	return v8::Number::New((double) javaLong);
}

jfloat TypeConverter::jsNumberToJavaFloat(v8::Handle<v8::Number> jsNumber)
{
	return ((jfloat) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaFloatToJsNumber(jfloat javaFloat)
{
	return v8::Number::New((double) javaFloat);
}

jdouble TypeConverter::jsNumberToJavaDouble(v8::Handle<v8::Number> jsNumber)
{
	return ((jdouble) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaDoubleToJsNumber(jdouble javaDouble)
{
	return v8::Number::New(javaDouble);
}

jboolean TypeConverter::jsBooleanToJavaBoolean(v8::Handle<v8::Boolean> jsBoolean)
{
	return (jsBoolean->Value()) == JNI_TRUE;
}

v8::Handle<v8::Boolean> TypeConverter::javaBooleanToJsBoolean(jboolean javaBoolean)
{
	return v8::Boolean::New((bool) javaBoolean);
}

jstring TypeConverter::jsStringToJavaString(v8::Handle<v8::String> jsString)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	v8::String::Value javaString(jsString);
	return env->NewString(*javaString, javaString.length());
}

v8::Handle<v8::String> TypeConverter::javaStringToJsString(jstring javaString)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::String>();
	}

	const char *nativeString = env->GetStringUTFChars(javaString, 0);
	int nativeStringLength = env->GetStringUTFLength(javaString);

	v8::Handle<v8::String> jsString = v8::String::New(nativeString, nativeStringLength);
	env->ReleaseStringUTFChars(javaString, nativeString);

	return jsString;
}

jobject TypeConverter::jsDateToJavaDate(v8::Handle<v8::Date> jsDate)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	return env->NewObject(JNIUtil::dateClass, JNIUtil::dateInitMethod, (jlong) jsDate->NumberValue());
}

jlong TypeConverter::jsDateToJavaLong(v8::Handle<v8::Date> jsDate)
{
	return (jlong) jsDate->NumberValue();
}

v8::Handle<v8::Date> TypeConverter::javaDateToJsDate(jobject javaDate)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Date>();
	}

	jlong epochTime = env->CallLongMethod(javaDate, JNIUtil::dateGetTimeMethod);
	return v8::Handle<v8::Date>::Cast(v8::Date::New((double) epochTime));
}

v8::Handle<v8::Date> TypeConverter::javaLongToJsDate(jlong javaLong)
{
	return v8::Handle<v8::Date>::Cast(v8::Date::New((double) javaLong));
}

jarray TypeConverter::jsArrayToJavaArray(v8::Handle<v8::Array> jsArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	int arrayLength = jsArray->Length();
	jobjectArray javaArray = env->NewObjectArray(arrayLength, JNIUtil::objectClass, NULL);

	for (int i = 0; i < arrayLength; i++) {
		v8::Local<v8::Value> element = jsArray->Get(i);
		jobject javaObject = jsValueToJavaObject(element);
		env->SetObjectArrayElement(javaArray, i, javaObject);
		env->DeleteLocalRef(javaObject);
	}

	return javaArray;
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jbooleanArray javaBooleanArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaBooleanArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	jboolean *arrayElements = env->GetBooleanArrayElements(javaBooleanArray, 0);
	for (int i = 0; i < arrayLength; i++) {
		jsArray->Set((uint32_t) i, v8::Boolean::New(arrayElements[i]));
	}

	return jsArray;
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jshortArray javaShortArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaShortArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jintArray javaIntArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaIntArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jlongArray javaLongArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaLongArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jfloatArray javaFloatArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaFloatArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jdoubleArray javaDoubleArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaDoubleArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jobjectArray javaObjectArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaObjectArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	for (int i = 0; i < arrayLength; i++) {
		jobject javaArrayElement = env->GetObjectArrayElement(javaObjectArray, i);
		v8::Handle<v8::Value> jsArrayElement = TypeConverter::javaObjectToJsValue(javaArrayElement);
		jsArray->Set((uint32_t) i, jsArrayElement);
		env->DeleteLocalRef(javaArrayElement);
	}

	return jsArray;
}

// converts js value to java object and recursively converts sub objects if this
// object is a container type
jobject TypeConverter::jsValueToJavaObject(v8::Local<v8::Value> jsValue)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	if (jsValue->IsNumber()) {
		jdouble javaDouble = TypeConverter::jsNumberToJavaDouble(jsValue->ToNumber());
		return env->NewObject(JNIUtil::doubleClass, JNIUtil::doubleInitMethod, javaDouble);
	} else if (jsValue->IsBoolean()) {
		jboolean javaBoolean = TypeConverter::jsBooleanToJavaBoolean(jsValue->ToBoolean());
		return env->NewObject(JNIUtil::booleanClass, JNIUtil::booleanInitMethod, javaBoolean);
	} else if (jsValue->IsString()) {
		return TypeConverter::jsStringToJavaString(jsValue->ToString());
	} else if (jsValue->IsDate()) {
		jlong javaLong = TypeConverter::jsDateToJavaLong(v8::Handle<v8::Date>::Cast(jsValue));
		return env->NewObject(JNIUtil::longClass, JNIUtil::longInitMethod, javaLong);
	} else if (jsValue->IsArray()) {
		return TypeConverter::jsArrayToJavaArray(v8::Handle<v8::Array>::Cast(jsValue));
	} else if (jsValue->IsObject()) {
		v8::Handle<v8::Object> jsObject = jsValue->ToObject();

		if (JavaObject::isJavaObject(jsObject)) {
			JavaObject *javaObject = JavaObject::Unwrap<JavaObject>(jsObject);
			return javaObject->getJavaObject();
		} else {
			v8::Handle<v8::Array> objectKeys = jsObject->GetOwnPropertyNames();
			int numKeys = objectKeys->Length();

			jobject javaHashMap = env->NewObject(JNIUtil::hashMapClass, JNIUtil::hashMapInitMethod, numKeys);

			for (int i = 0; i < numKeys; i++) {
				v8::Local<v8::Value> jsObjectPropertyKey = objectKeys->Get((uint32_t) i);
				jobject javaObjectPropertyKey = TypeConverter::jsValueToJavaObject(jsObjectPropertyKey);
				v8::Local<v8::Value> jsObjectPropertyValue = jsObject->Get(jsObjectPropertyKey);
				jobject javaObjectPropertyValue = TypeConverter::jsValueToJavaObject(jsObjectPropertyValue);

				env->CallObjectMethod(javaHashMap, JNIUtil::hashMapPutMethod, javaObjectPropertyKey,
					javaObjectPropertyValue);
			}

			return javaHashMap;
		}
	}
	return NULL;
}

// converts java object to js value and recursively converts sub objects if this
// object is a container type
v8::Handle<v8::Value> TypeConverter::javaObjectToJsValue(jobject javaObject)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Value>();
	}

	jclass javaObjectClass = env->GetObjectClass(javaObject);

	if (env->IsInstanceOf(javaObjectClass, JNIUtil::numberClass)) {
		jdouble javaDouble = env->CallDoubleMethod(javaObject, JNIUtil::numberDoubleValueMethod);
		return v8::Number::New((double) javaDouble);
	} else if (env->IsInstanceOf(javaObject, JNIUtil::stringClass)) {
		return v8::String::New(env->GetStringChars((jstring) javaObject, 0));
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::dateClass)) {
		return TypeConverter::javaDateToJsDate(javaObject);
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::hashMapClass)) {
		v8::Handle<v8::Object> jsObject = v8::Object::New();

		jobject hashMapSet = env->CallObjectMethod(javaObject, JNIUtil::hashMapKeySetMethod);

		jobjectArray hashMapKeys = (jobjectArray) env->CallObjectMethod(hashMapSet, JNIUtil::setToArrayMethod);
		env->DeleteLocalRef(hashMapSet);
		int hashMapKeysLength = env->GetArrayLength(hashMapKeys);

		for (int i = 0; i < hashMapKeysLength; i++) {
			jobject javaPairKey = env->GetObjectArrayElement(hashMapKeys, i);
			v8::Handle<v8::Value> jsPairKey = TypeConverter::javaObjectToJsValue(javaPairKey);

			jobject javaPairValue = env->CallObjectMethod(javaObject, JNIUtil::hashMapGetMethod, javaPairKey);
			env->DeleteLocalRef(javaPairKey);
			jsObject->Set(jsPairKey, TypeConverter::javaObjectToJsValue(javaPairValue));
			env->DeleteLocalRef(javaPairValue);
		}

		env->DeleteLocalRef(hashMapKeys);

		return jsObject;
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::krollProxyClass)) {
		jlong v8ObjectPointer = env->CallLongMethod(javaObject, JNIUtil::krollProxyGetV8ObjectPointerMethod);
		if (v8ObjectPointer > 0) {
			v8::Handle<v8::Object> v8ObjectPointerHandle((v8::Object*) v8ObjectPointer);
			return v8ObjectPointerHandle;
		} else {
			ProxyFactory *proxyFactory = ProxyFactory::factoryForClass(javaObjectClass);
			v8::Handle<v8::Object> proxyHandle = proxyFactory->create(javaObject);
			return proxyHandle;
		}
	}
	return v8::Handle<v8::Value>();
}

/****************************** private methods ******************************/

// used mainly by the array conversion methods when converting java numeric types
// arrays to to the generic js number type
v8::Handle<v8::Array> TypeConverter::javaDoubleArrayToJsNumberArray(jdoubleArray javaDoubleArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaDoubleArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	jdouble *arrayElements = env->GetDoubleArrayElements(javaDoubleArray, 0);
	for (int i = 0; i < arrayLength; i++) {
		jsArray->Set((uint32_t) i, v8::Number::New(arrayElements[i]));
	}

	return jsArray;
}

<commit_msg>changes to converter when changing proxy types<commit_after>/**
 * Appcelerator Titanium Mobile
 * Copyright (c) 2011 by Appcelerator, Inc. All Rights Reserved.
 * Licensed under the terms of the Apache Public License
 * Please see the LICENSE included with this distribution for details.
 */
#include <jni.h>
#include <v8.h>

#include "TypeConverter.h"
#include "JNIUtil.h"
#include "JavaObject.h"
#include "ProxyFactory.h"
#include "V8Runtime.h"

using namespace titanium;

/****************************** public methods ******************************/
jshort TypeConverter::jsNumberToJavaShort(v8::Handle<v8::Number> jsNumber)
{
	return ((jshort) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaShortToJsNumber(jshort javaShort)
{
	return v8::Number::New((double) javaShort);
}

jint TypeConverter::jsNumberToJavaInt(v8::Handle<v8::Number> jsNumber)
{
	return ((jint) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaIntToJsNumber(jint javaInt)
{
	return v8::Number::New((double) javaInt);
}

jlong TypeConverter::jsNumberToJavaLong(v8::Handle<v8::Number> jsNumber)
{
	return ((jlong) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaLongToJsNumber(jlong javaLong)
{
	return v8::Number::New((double) javaLong);
}

jfloat TypeConverter::jsNumberToJavaFloat(v8::Handle<v8::Number> jsNumber)
{
	return ((jfloat) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaFloatToJsNumber(jfloat javaFloat)
{
	return v8::Number::New((double) javaFloat);
}

jdouble TypeConverter::jsNumberToJavaDouble(v8::Handle<v8::Number> jsNumber)
{
	return ((jdouble) jsNumber->Value());
}

v8::Handle<v8::Number> TypeConverter::javaDoubleToJsNumber(jdouble javaDouble)
{
	return v8::Number::New(javaDouble);
}

jboolean TypeConverter::jsBooleanToJavaBoolean(v8::Handle<v8::Boolean> jsBoolean)
{
	return (jsBoolean->Value()) == JNI_TRUE;
}

v8::Handle<v8::Boolean> TypeConverter::javaBooleanToJsBoolean(jboolean javaBoolean)
{
	return v8::Boolean::New((bool) javaBoolean);
}

jstring TypeConverter::jsStringToJavaString(v8::Handle<v8::String> jsString)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	v8::String::Value javaString(jsString);
	return env->NewString(*javaString, javaString.length());
}

v8::Handle<v8::String> TypeConverter::javaStringToJsString(jstring javaString)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::String>();
	}

	const char *nativeString = env->GetStringUTFChars(javaString, 0);
	int nativeStringLength = env->GetStringUTFLength(javaString);

	v8::Handle<v8::String> jsString = v8::String::New(nativeString, nativeStringLength);
	env->ReleaseStringUTFChars(javaString, nativeString);

	return jsString;
}

jobject TypeConverter::jsDateToJavaDate(v8::Handle<v8::Date> jsDate)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	return env->NewObject(JNIUtil::dateClass, JNIUtil::dateInitMethod, (jlong) jsDate->NumberValue());
}

jlong TypeConverter::jsDateToJavaLong(v8::Handle<v8::Date> jsDate)
{
	return (jlong) jsDate->NumberValue();
}

v8::Handle<v8::Date> TypeConverter::javaDateToJsDate(jobject javaDate)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Date>();
	}

	jlong epochTime = env->CallLongMethod(javaDate, JNIUtil::dateGetTimeMethod);
	return v8::Handle<v8::Date>::Cast(v8::Date::New((double) epochTime));
}

v8::Handle<v8::Date> TypeConverter::javaLongToJsDate(jlong javaLong)
{
	return v8::Handle<v8::Date>::Cast(v8::Date::New((double) javaLong));
}

jarray TypeConverter::jsArrayToJavaArray(v8::Handle<v8::Array> jsArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	int arrayLength = jsArray->Length();
	jobjectArray javaArray = env->NewObjectArray(arrayLength, JNIUtil::objectClass, NULL);

	for (int i = 0; i < arrayLength; i++) {
		v8::Local<v8::Value> element = jsArray->Get(i);
		jobject javaObject = jsValueToJavaObject(element);
		env->SetObjectArrayElement(javaArray, i, javaObject);
		env->DeleteLocalRef(javaObject);
	}

	return javaArray;
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jbooleanArray javaBooleanArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaBooleanArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	jboolean *arrayElements = env->GetBooleanArrayElements(javaBooleanArray, 0);
	for (int i = 0; i < arrayLength; i++) {
		jsArray->Set((uint32_t) i, v8::Boolean::New(arrayElements[i]));
	}

	return jsArray;
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jshortArray javaShortArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaShortArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jintArray javaIntArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaIntArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jlongArray javaLongArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaLongArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jfloatArray javaFloatArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaFloatArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jdoubleArray javaDoubleArray)
{
	return javaDoubleArrayToJsNumberArray((jdoubleArray) javaDoubleArray);
}

v8::Handle<v8::Array> TypeConverter::javaArrayToJsArray(jobjectArray javaObjectArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaObjectArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	for (int i = 0; i < arrayLength; i++) {
		jobject javaArrayElement = env->GetObjectArrayElement(javaObjectArray, i);
		v8::Handle<v8::Value> jsArrayElement = TypeConverter::javaObjectToJsValue(javaArrayElement);
		jsArray->Set((uint32_t) i, jsArrayElement);
		env->DeleteLocalRef(javaArrayElement);
	}

	return jsArray;
}

// converts js value to java object and recursively converts sub objects if this
// object is a container type
jobject TypeConverter::jsValueToJavaObject(v8::Local<v8::Value> jsValue)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return NULL;
	}

	if (jsValue->IsNumber()) {
		jdouble javaDouble = TypeConverter::jsNumberToJavaDouble(jsValue->ToNumber());
		return env->NewObject(JNIUtil::doubleClass, JNIUtil::doubleInitMethod, javaDouble);
	} else if (jsValue->IsBoolean()) {
		jboolean javaBoolean = TypeConverter::jsBooleanToJavaBoolean(jsValue->ToBoolean());
		return env->NewObject(JNIUtil::booleanClass, JNIUtil::booleanInitMethod, javaBoolean);
	} else if (jsValue->IsString()) {
		return TypeConverter::jsStringToJavaString(jsValue->ToString());
	} else if (jsValue->IsDate()) {
		jlong javaLong = TypeConverter::jsDateToJavaLong(v8::Handle<v8::Date>::Cast(jsValue));
		return env->NewObject(JNIUtil::longClass, JNIUtil::longInitMethod, javaLong);
	} else if (jsValue->IsArray()) {
		return TypeConverter::jsArrayToJavaArray(v8::Handle<v8::Array>::Cast(jsValue));
	} else if (jsValue->IsObject()) {
		v8::Handle<v8::Object> jsObject = jsValue->ToObject();

		if (JavaObject::isJavaObject(jsObject)) {
			JavaObject *javaObject = JavaObject::Unwrap<JavaObject>(jsObject);
			return javaObject->getJavaObject();
		} else {
			v8::Handle<v8::Array> objectKeys = jsObject->GetOwnPropertyNames();
			int numKeys = objectKeys->Length();

			jobject javaHashMap = env->NewObject(JNIUtil::hashMapClass, JNIUtil::hashMapInitMethod, numKeys);

			for (int i = 0; i < numKeys; i++) {
				v8::Local<v8::Value> jsObjectPropertyKey = objectKeys->Get((uint32_t) i);
				jobject javaObjectPropertyKey = TypeConverter::jsValueToJavaObject(jsObjectPropertyKey);
				v8::Local<v8::Value> jsObjectPropertyValue = jsObject->Get(jsObjectPropertyKey);
				jobject javaObjectPropertyValue = TypeConverter::jsValueToJavaObject(jsObjectPropertyValue);

				env->CallObjectMethod(javaHashMap, JNIUtil::hashMapPutMethod, javaObjectPropertyKey,
					javaObjectPropertyValue);
			}

			return javaHashMap;
		}
	}
	return NULL;
}

// converts java object to js value and recursively converts sub objects if this
// object is a container type
v8::Handle<v8::Value> TypeConverter::javaObjectToJsValue(jobject javaObject)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Value>();
	}

	jclass javaObjectClass = env->GetObjectClass(javaObject);

	if (env->IsInstanceOf(javaObjectClass, JNIUtil::numberClass)) {
		jdouble javaDouble = env->CallDoubleMethod(javaObject, JNIUtil::numberDoubleValueMethod);
		return v8::Number::New((double) javaDouble);
	} else if (env->IsInstanceOf(javaObject, JNIUtil::stringClass)) {
		return v8::String::New(env->GetStringChars((jstring) javaObject, 0));
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::dateClass)) {
		return TypeConverter::javaDateToJsDate(javaObject);
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::hashMapClass)) {
		v8::Handle<v8::Object> jsObject = v8::Object::New();

		jobject hashMapSet = env->CallObjectMethod(javaObject, JNIUtil::hashMapKeySetMethod);

		jobjectArray hashMapKeys = (jobjectArray) env->CallObjectMethod(hashMapSet, JNIUtil::setToArrayMethod);
		env->DeleteLocalRef(hashMapSet);
		int hashMapKeysLength = env->GetArrayLength(hashMapKeys);

		for (int i = 0; i < hashMapKeysLength; i++) {
			jobject javaPairKey = env->GetObjectArrayElement(hashMapKeys, i);
			v8::Handle<v8::Value> jsPairKey = TypeConverter::javaObjectToJsValue(javaPairKey);

			jobject javaPairValue = env->CallObjectMethod(javaObject, JNIUtil::hashMapGetMethod, javaPairKey);
			env->DeleteLocalRef(javaPairKey);
			jsObject->Set(jsPairKey, TypeConverter::javaObjectToJsValue(javaPairValue));
			env->DeleteLocalRef(javaPairValue);
		}

		env->DeleteLocalRef(hashMapKeys);

		return jsObject;
	} else if (env->IsInstanceOf(javaObjectClass, JNIUtil::krollProxyClass)) {
		jlong v8ObjectPointer = env->CallLongMethod(javaObject, JNIUtil::krollProxyGetV8ObjectPointerMethod);
		if (v8ObjectPointer > 0) {
			v8::Handle<v8::Object> v8ObjectPointerHandle((v8::Object*) v8ObjectPointer);
			return v8ObjectPointerHandle;
		} else {
			ProxyFactory *proxyFactory = ProxyFactory::factoryForClass(javaObjectClass);
			v8::Handle<v8::Object> proxyHandle = proxyFactory->create(javaObject);

			// set the pointer back on the java proxy
			V8Runtime::newObject(proxyHandle);

			return proxyHandle;
		}
	}

	return v8::Handle<v8::Value>();
}

/****************************** private methods ******************************/

// used mainly by the array conversion methods when converting java numeric types
// arrays to to the generic js number type
v8::Handle<v8::Array> TypeConverter::javaDoubleArrayToJsNumberArray(jdoubleArray javaDoubleArray)
{
	JNIEnv *env = JNIUtil::getJNIEnv();
	if (env == NULL) {
		return v8::Handle<v8::Array>();
	}

	int arrayLength = env->GetArrayLength(javaDoubleArray);
	v8::Handle<v8::Array> jsArray = v8::Array::New(arrayLength);

	jdouble *arrayElements = env->GetDoubleArrayElements(javaDoubleArray, 0);
	for (int i = 0; i < arrayLength; i++) {
		jsArray->Set((uint32_t) i, v8::Number::New(arrayElements[i]));
	}

	return jsArray;
}

<|endoftext|>


<commit_before><commit_msg>lib/core/object/io/writer: support tag values.<commit_after><|endoftext|>


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

#include "OSVRPrivatePCH.h"

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
#include "OSVRInterfaceCollection.h"
#endif

#include "OSVREntryPoint.h"
#include <osvr/ClientKit/ServerAutoStartC.h>

#include "Runtime/Core/Public/Misc/DateTime.h"

DEFINE_LOG_CATEGORY(OSVREntryPointLog);

OSVREntryPoint::OSVREntryPoint()
{
    osvrClientAttemptServerAutoStart();

    osvrClientContext = osvrClientInit("com.osvr.unreal.plugin");

    {
        bool bClientContextOK = false;
        bool bFailure = false;
        auto begin = FDateTime::Now().GetSecond();
        auto end = begin + 3;
        while (FDateTime::Now().GetSecond() < end && !bClientContextOK && !bFailure)
        {
            bClientContextOK = osvrClientCheckStatus(osvrClientContext) == OSVR_RETURN_SUCCESS;
            if (!bClientContextOK)
            {
                bFailure = osvrClientUpdate(osvrClientContext) == OSVR_RETURN_FAILURE;
                if (bFailure)
                {
                    UE_LOG(OSVREntryPointLog, Warning, TEXT("osvrClientUpdate failed during startup. Treating this as \"HMD not connected\""));
                    break;
                }
                FPlatformProcess::Sleep(0.2f);
            }
        }
        if (!bClientContextOK)
        {
            UE_LOG(OSVREntryPointLog, Warning, TEXT("OSVR client context did not initialize correctly. Most likely the server isn't running. Treating this as if the HMD is not connected."));
        }
    }

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
    InterfaceCollection = MakeShareable(new OSVRInterfaceCollection(osvrClientContext));
#endif
}

OSVREntryPoint::~OSVREntryPoint()
{
    FScopeLock lock(this->GetClientContextMutex());

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
    InterfaceCollection = nullptr;
#endif

    osvrClientShutdown(osvrClientContext);
    osvrClientReleaseAutoStartedServer();
}

void OSVREntryPoint::Tick(float DeltaTime)
{
    FScopeLock lock(this->GetClientContextMutex());
    osvrClientUpdate(osvrClientContext);
}

bool OSVREntryPoint::IsOSVRConnected()
{
    return osvrClientContext && osvrClientCheckStatus(osvrClientContext) == OSVR_RETURN_SUCCESS;
}

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
OSVRInterfaceCollection* OSVREntryPoint::GetInterfaceCollection()
{
    return InterfaceCollection.Get();
}
#endif
<commit_msg>Avoid infinite hang BuildCookRun commandlet due to OSVR server connect failure<commit_after>//
// Copyright 2014, 2015 Razer Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//

#include "OSVRPrivatePCH.h"

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
#include "OSVRInterfaceCollection.h"
#endif

#include "OSVREntryPoint.h"
#include <osvr/ClientKit/ServerAutoStartC.h>

#include "Runtime/Core/Public/Misc/DateTime.h"

DEFINE_LOG_CATEGORY(OSVREntryPointLog);

OSVREntryPoint::OSVREntryPoint()
{
    // avoid BuildCookRun hangs
    if (IsRunningCommandlet() || IsRunningDedicatedServer())
    {
        return;
    }

    osvrClientAttemptServerAutoStart();

    osvrClientContext = osvrClientInit("com.osvr.unreal.plugin");

    {
        bool bClientContextOK = false;
        bool bFailure = false;
        auto begin = FDateTime::Now().GetSecond();
        auto end = begin + 3;
        while (FDateTime::Now().GetSecond() < end && !bClientContextOK && !bFailure)
        {
            bClientContextOK = osvrClientCheckStatus(osvrClientContext) == OSVR_RETURN_SUCCESS;
            if (!bClientContextOK)
            {
                bFailure = osvrClientUpdate(osvrClientContext) == OSVR_RETURN_FAILURE;
                if (bFailure)
                {
                    UE_LOG(OSVREntryPointLog, Warning, TEXT("osvrClientUpdate failed during startup. Treating this as \"HMD not connected\""));
                    break;
                }
                FPlatformProcess::Sleep(0.2f);
            }
        }
        if (!bClientContextOK)
        {
            UE_LOG(OSVREntryPointLog, Warning, TEXT("OSVR client context did not initialize correctly. Most likely the server isn't running. Treating this as if the HMD is not connected."));
        }
    }

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
    InterfaceCollection = MakeShareable(new OSVRInterfaceCollection(osvrClientContext));
#endif
}

OSVREntryPoint::~OSVREntryPoint()
{
    FScopeLock lock(this->GetClientContextMutex());

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
    InterfaceCollection = nullptr;
#endif

    osvrClientShutdown(osvrClientContext);
    osvrClientReleaseAutoStartedServer();
}

void OSVREntryPoint::Tick(float DeltaTime)
{
    FScopeLock lock(this->GetClientContextMutex());
    osvrClientUpdate(osvrClientContext);
}

bool OSVREntryPoint::IsOSVRConnected()
{
    return osvrClientContext && osvrClientCheckStatus(osvrClientContext) == OSVR_RETURN_SUCCESS;
}

#if OSVR_DEPRECATED_BLUEPRINT_API_ENABLED
OSVRInterfaceCollection* OSVREntryPoint::GetInterfaceCollection()
{
    return InterfaceCollection.Get();
}
#endif
<|endoftext|>


<commit_before>// Virvo - Virtual Reality Volume Rendering
// Copyright (C) 1999-2003 University of Stuttgart, 2004-2005 Brown University
// Contact: Jurgen P. Schulze, jschulze@ucsd.edu
//
// This file is part of Virvo.
//
// Virvo is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library (see license.txt); if not, write to the
// Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA

#include <GL/glew.h>

#include "vvcanvas.h"

#include <virvo/vvdebugmsg.h>
#include <virvo/vvfileio.h>
#include <virvo/vvgltools.h>

#include <QSettings>
#include <QTimer>

#include <iostream>

using vox::vvObjView;

vvCanvas::vvCanvas(const QGLFormat& format, const QString& filename, QWidget* parent)
  : QGLWidget(format, parent)
  , _vd(NULL)
  , _renderer(NULL)
  , _projectionType(vox::vvObjView::PERSPECTIVE)
  , _doubleBuffering(format.doubleBuffer())
  , _superSamples(format.samples())
{
  vvDebugMsg::msg(1, "vvCanvas::vvCanvas()");

  if (filename != "")
  {
    _vd = new vvVolDesc(filename.toStdString().c_str());
  }
  else
  {
    // load default volume
    _vd = new vvVolDesc;
    _vd->vox[0] = 32;
    _vd->vox[1] = 32;
    _vd->vox[2] = 32;
    _vd->frames = 0;
  }

  // init ui
  setMouseTracking(true);
  setFocusPolicy(Qt::StrongFocus);

  // read persistent settings
  QSettings settings;
  QColor qcolor = settings.value("canvas/bgcolor").value<QColor>();
  _bgColor = vvColor(qcolor.redF(), qcolor.greenF(), qcolor.blueF());

  _animTimer = new QTimer(this);
  connect(_animTimer, SIGNAL(timeout()), this, SLOT(incTimeStep()));
}

vvCanvas::~vvCanvas()
{
  vvDebugMsg::msg(1, "vvCanvas::~vvCanvas()");

  delete _renderer;
  delete _vd;
}

void vvCanvas::setParameter(ParameterType param, const vvParam& value)
{
  vvDebugMsg::msg(3, "vvCanvas::setParameter()");

  switch (param)
  {
  case VV_BG_COLOR:
    _bgColor = value;
    break;
  case VV_DOUBLEBUFFERING:
    _doubleBuffering = value;
    break;
  case VV_SUPERSAMPLES:
    _superSamples = value;
    break;
  default:
    break;
  }
}

void vvCanvas::setVolDesc(vvVolDesc* vd)
{
  vvDebugMsg::msg(3, "vvCanvas::setVolDesc()");

  delete _vd;
  _vd = vd;

  if (_vd != NULL)
  {
    createRenderer();
  }

  foreach (vvPlugin* plugin, _plugins)
  {
    plugin->setVolDesc(_vd);
  }

  emit newVolDesc(_vd);
}

void vvCanvas::setPlugins(const QList<vvPlugin*>& plugins)
{
  vvDebugMsg::msg(3, "vvCanvas::setPlugins()");

  _plugins = plugins;
}

vvVolDesc* vvCanvas::getVolDesc() const
{
  vvDebugMsg::msg(3, "vvCanvas::getVolDesc()");

  return _vd;
}

vvRenderer* vvCanvas::getRenderer() const
{
  vvDebugMsg::msg(3, "vvCanvas::getRenderer()");

  return _renderer;
}

void vvCanvas::loadCamera(const QString& filename)
{
  vvDebugMsg::msg(3, "vvCanvas::loadCamera()");

  QByteArray ba = filename.toLatin1();
  _ov.loadCamera(ba.data());
}

void vvCanvas::saveCamera(const QString& filename)
{
  vvDebugMsg::msg(3, "vvCanvas::saveCamera()");

  QByteArray ba = filename.toLatin1();
  _ov.saveCamera(ba.data());
}

void vvCanvas::initializeGL()
{
  vvDebugMsg::msg(1, "vvCanvas::initializeGL()");

  glewInit();
  init();
}

void vvCanvas::paintGL()
{
  vvDebugMsg::msg(3, "vvCanvas::paintGL()");

  if (_renderer == NULL)
  {
    return;
  }

  if (_doubleBuffering)
  {
    glDrawBuffer(GL_BACK);
  }
  else
  {
    glDrawBuffer(GL_FRONT);
  }

  glClearColor(_bgColor[0], _bgColor[1], _bgColor[2], 0.0f);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

  glMatrixMode(GL_MODELVIEW);
  _ov.setModelviewMatrix(vvObjView::CENTER);

  foreach (vvPlugin* plugin, _plugins)
  {
    if (plugin->isActive())
    {
      plugin->prerender();
    }
  }

  _renderer->renderVolumeGL();

  foreach (vvPlugin* plugin, _plugins)
  {
    if (plugin->isActive())
    {
      plugin->postrender();
    }
  }
}

void vvCanvas::resizeGL(const int w, const int h)
{
  vvDebugMsg::msg(3, "vvCanvas::resizeGL()");

  glViewport(0, 0, w, h);
  if (h > 0)
  {
    _ov.setAspectRatio(static_cast<float>(w) / static_cast<float>(h));
  }
  updateGL();

  emit resized(QSize(w, h));
}

void vvCanvas::mouseMoveEvent(QMouseEvent* event)
{
  vvDebugMsg::msg(3, "vvCanvas::mouseMoveEvent()");

  switch (_mouseButton)
  {
  case Qt::LeftButton:
  {
    _ov._camera.trackballRotation(width(), height(),
      _lastMousePos.x(), _lastMousePos.y(),
      event->pos().x(), event->pos().y());
    break;
  }
  case Qt::MiddleButton:
  {
    const float pixelInWorld = _ov.getViewportWidth() / static_cast<float>(width());
    const float dx = static_cast<float>(event->pos().x() - _lastMousePos.x());
    const float dy = static_cast<float>(event->pos().y() - _lastMousePos.y());
    vvVector2f pan(pixelInWorld * dx, pixelInWorld * dy);
    _ov._camera.translate(pan[0], -pan[1], 0.0f);
    break;
  }
  case Qt::RightButton:
  {
    const float factor = event->pos().y() - _lastMousePos.y();
    _ov._camera.translate(0.0f, 0.0f, factor);
    break;
  }
  default:
    break;
  }
  _lastMousePos = event->pos();
  updateGL();
}

void vvCanvas::mousePressEvent(QMouseEvent* event)
{
  vvDebugMsg::msg(3, "vvCanvas::mousePressEvent()");

  _mouseButton = event->button();
  _lastMousePos = event->pos();
}

void vvCanvas::mouseReleaseEvent(QMouseEvent*)
{
  vvDebugMsg::msg(3, "vvCanvas::mouseReleaseEvent()");

  _mouseButton = Qt::NoButton;
}

void vvCanvas::init()
{
  vvDebugMsg::msg(3, "vvCanvas::init()");

  vvFileIO* fio = new vvFileIO;
  fio->loadVolumeData(_vd, vvFileIO::ALL_DATA);
  delete fio;

  // default transfer function
  if (_vd->tf.isEmpty())
  {
    _vd->tf.setDefaultAlpha(0, _vd->real[0], _vd->real[1]);
    _vd->tf.setDefaultColors((_vd->chan == 1) ? 0 : 3, _vd->real[0], _vd->real[1]);
  }

  // init renderer
  if (_vd != NULL)
  {
    _currentRenderer = "viewport";
    _currentOptions["voxeltype"] = "arb";
    createRenderer();
  }

  updateProjection();

  foreach (vvPlugin* plugin, _plugins)
  {
    plugin->setVolDesc(_vd);
  }

  emit newVolDesc(_vd);
}

void vvCanvas::createRenderer()
{
  vvDebugMsg::msg(3, "vvCanvas::createRenderer()");

  vvRenderState state;
  if (_renderer)
  {
    state = *_renderer;
    delete _renderer;
  }

  vvRendererFactory::Options opt(_currentOptions);
  _renderer = vvRendererFactory::create(_vd, state, _currentRenderer.c_str(), opt);
}

void vvCanvas::updateProjection()
{
  vvDebugMsg::msg(3, "vvCanvas::updateProjection()");

  if (_projectionType == vvObjView::PERSPECTIVE)
  {
    _ov.setProjection(vvObjView::PERSPECTIVE, vvObjView::DEF_FOV, vvObjView::DEF_CLIP_NEAR, vvObjView::DEF_CLIP_FAR);
  }
  else if (_projectionType == vvObjView::ORTHO)
  {
    _ov.setProjection(vvObjView::ORTHO, vvObjView::DEF_VIEWPORT_WIDTH, vvObjView::DEF_CLIP_NEAR, vvObjView::DEF_CLIP_FAR);
  }
}

void vvCanvas::setCurrentFrame(const int frame)
{
  vvDebugMsg::msg(3, "vvCanvas::setCurrentFrame()");

  _renderer->setCurrentFrame(frame);
  emit currentFrame(frame);
  updateGL();
}

void vvCanvas::startAnimation(const double fps)
{
  vvDebugMsg::msg(3, "vvCanvas::startAnimation()");

  _vd->dt = 1.0f / static_cast<float>(fps);
  const float delay = std::abs(_vd->dt * 1000.0f);
  _animTimer->start(static_cast<int>(delay));
}

void vvCanvas::stopAnimation()
{
  vvDebugMsg::msg(3, "vvCanvas::stopAnimation()");

  _animTimer->stop();
}

void vvCanvas::setTimeStep(const int step)
{
  vvDebugMsg::msg(3, "vvCanvas::setTimeStep()");

  int f = step;
  while (f < 0)
  {
    f += _vd->frames;
  }

  while (f >= _vd->frames)
  {
    f -= _vd->frames;
  }

  setCurrentFrame(f);
}

void vvCanvas::incTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::incTimeStep()");

  int f = _renderer->getCurrentFrame();
  f = (f >= _vd->frames - 1) ? 0 : f + 1;
  setCurrentFrame(f);
}

void vvCanvas::decTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::decTimeStep()");

  int f = _renderer->getCurrentFrame();
  f = (f <= 0) ? _vd->frames - 1 : f - 1;
  setCurrentFrame(f);
}

void vvCanvas::firstTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::firstTimeStep()");

  setCurrentFrame(0);
}

void vvCanvas::lastTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::lastTimeStep()");

  setCurrentFrame(_vd->frames - 1);
}

<commit_msg>Resize volume to fit the viewport<commit_after>// Virvo - Virtual Reality Volume Rendering
// Copyright (C) 1999-2003 University of Stuttgart, 2004-2005 Brown University
// Contact: Jurgen P. Schulze, jschulze@ucsd.edu
//
// This file is part of Virvo.
//
// Virvo is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library (see license.txt); if not, write to the
// Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA

#include <GL/glew.h>

#include "vvcanvas.h"

#include <virvo/vvdebugmsg.h>
#include <virvo/vvfileio.h>
#include <virvo/vvgltools.h>

#include <QSettings>
#include <QTimer>

#include <iostream>

using vox::vvObjView;

vvCanvas::vvCanvas(const QGLFormat& format, const QString& filename, QWidget* parent)
  : QGLWidget(format, parent)
  , _vd(NULL)
  , _renderer(NULL)
  , _projectionType(vox::vvObjView::PERSPECTIVE)
  , _doubleBuffering(format.doubleBuffer())
  , _superSamples(format.samples())
{
  vvDebugMsg::msg(1, "vvCanvas::vvCanvas()");

  if (filename != "")
  {
    _vd = new vvVolDesc(filename.toStdString().c_str());
  }
  else
  {
    // load default volume
    _vd = new vvVolDesc;
    _vd->vox[0] = 32;
    _vd->vox[1] = 32;
    _vd->vox[2] = 32;
    _vd->frames = 0;
  }

  // init ui
  setMouseTracking(true);
  setFocusPolicy(Qt::StrongFocus);

  // read persistent settings
  QSettings settings;
  QColor qcolor = settings.value("canvas/bgcolor").value<QColor>();
  _bgColor = vvColor(qcolor.redF(), qcolor.greenF(), qcolor.blueF());

  _animTimer = new QTimer(this);
  connect(_animTimer, SIGNAL(timeout()), this, SLOT(incTimeStep()));
}

vvCanvas::~vvCanvas()
{
  vvDebugMsg::msg(1, "vvCanvas::~vvCanvas()");

  delete _renderer;
  delete _vd;
}

void vvCanvas::setParameter(ParameterType param, const vvParam& value)
{
  vvDebugMsg::msg(3, "vvCanvas::setParameter()");

  switch (param)
  {
  case VV_BG_COLOR:
    _bgColor = value;
    break;
  case VV_DOUBLEBUFFERING:
    _doubleBuffering = value;
    break;
  case VV_SUPERSAMPLES:
    _superSamples = value;
    break;
  default:
    break;
  }
}

void vvCanvas::setVolDesc(vvVolDesc* vd)
{
  vvDebugMsg::msg(3, "vvCanvas::setVolDesc()");

  delete _vd;
  _vd = vd;

  if (_vd != NULL)
  {
    createRenderer();
  }

  foreach (vvPlugin* plugin, _plugins)
  {
    plugin->setVolDesc(_vd);
  }

  emit newVolDesc(_vd);
}

void vvCanvas::setPlugins(const QList<vvPlugin*>& plugins)
{
  vvDebugMsg::msg(3, "vvCanvas::setPlugins()");

  _plugins = plugins;
}

vvVolDesc* vvCanvas::getVolDesc() const
{
  vvDebugMsg::msg(3, "vvCanvas::getVolDesc()");

  return _vd;
}

vvRenderer* vvCanvas::getRenderer() const
{
  vvDebugMsg::msg(3, "vvCanvas::getRenderer()");

  return _renderer;
}

void vvCanvas::loadCamera(const QString& filename)
{
  vvDebugMsg::msg(3, "vvCanvas::loadCamera()");

  QByteArray ba = filename.toLatin1();
  _ov.loadCamera(ba.data());
}

void vvCanvas::saveCamera(const QString& filename)
{
  vvDebugMsg::msg(3, "vvCanvas::saveCamera()");

  QByteArray ba = filename.toLatin1();
  _ov.saveCamera(ba.data());
}

void vvCanvas::initializeGL()
{
  vvDebugMsg::msg(1, "vvCanvas::initializeGL()");

  glewInit();
  init();
}

void vvCanvas::paintGL()
{
  vvDebugMsg::msg(3, "vvCanvas::paintGL()");

  if (_renderer == NULL)
  {
    return;
  }

  if (_doubleBuffering)
  {
    glDrawBuffer(GL_BACK);
  }
  else
  {
    glDrawBuffer(GL_FRONT);
  }

  glClearColor(_bgColor[0], _bgColor[1], _bgColor[2], 0.0f);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

  glMatrixMode(GL_MODELVIEW);
  _ov.setModelviewMatrix(vvObjView::CENTER);

  foreach (vvPlugin* plugin, _plugins)
  {
    if (plugin->isActive())
    {
      plugin->prerender();
    }
  }

  _renderer->renderVolumeGL();

  foreach (vvPlugin* plugin, _plugins)
  {
    if (plugin->isActive())
    {
      plugin->postrender();
    }
  }
}

void vvCanvas::resizeGL(const int w, const int h)
{
  vvDebugMsg::msg(3, "vvCanvas::resizeGL()");

  glViewport(0, 0, w, h);
  if (h > 0)
  {
    _ov.setAspectRatio(static_cast<float>(w) / static_cast<float>(h));
  }
  updateGL();

  emit resized(QSize(w, h));
}

void vvCanvas::mouseMoveEvent(QMouseEvent* event)
{
  vvDebugMsg::msg(3, "vvCanvas::mouseMoveEvent()");

  switch (_mouseButton)
  {
  case Qt::LeftButton:
  {
    _ov._camera.trackballRotation(width(), height(),
      _lastMousePos.x(), _lastMousePos.y(),
      event->pos().x(), event->pos().y());
    break;
  }
  case Qt::MiddleButton:
  {
    const float pixelInWorld = _ov.getViewportWidth() / static_cast<float>(width());
    const float dx = static_cast<float>(event->pos().x() - _lastMousePos.x());
    const float dy = static_cast<float>(event->pos().y() - _lastMousePos.y());
    vvVector2f pan(pixelInWorld * dx, pixelInWorld * dy);
    _ov._camera.translate(pan[0], -pan[1], 0.0f);
    break;
  }
  case Qt::RightButton:
  {
    const float factor = event->pos().y() - _lastMousePos.y();
    _ov._camera.translate(0.0f, 0.0f, factor);
    break;
  }
  default:
    break;
  }
  _lastMousePos = event->pos();
  updateGL();
}

void vvCanvas::mousePressEvent(QMouseEvent* event)
{
  vvDebugMsg::msg(3, "vvCanvas::mousePressEvent()");

  _mouseButton = event->button();
  _lastMousePos = event->pos();
}

void vvCanvas::mouseReleaseEvent(QMouseEvent*)
{
  vvDebugMsg::msg(3, "vvCanvas::mouseReleaseEvent()");

  _mouseButton = Qt::NoButton;
}

void vvCanvas::init()
{
  vvDebugMsg::msg(3, "vvCanvas::init()");

  vvFileIO* fio = new vvFileIO;
  fio->loadVolumeData(_vd, vvFileIO::ALL_DATA);
  delete fio;

  // default transfer function
  if (_vd->tf.isEmpty())
  {
    _vd->tf.setDefaultAlpha(0, _vd->real[0], _vd->real[1]);
    _vd->tf.setDefaultColors((_vd->chan == 1) ? 0 : 3, _vd->real[0], _vd->real[1]);
  }

  // init renderer
  if (_vd != NULL)
  {
    _currentRenderer = "viewport";
    _currentOptions["voxeltype"] = "arb";
    createRenderer();
  }

  updateProjection();

  foreach (vvPlugin* plugin, _plugins)
  {
    plugin->setVolDesc(_vd);
  }

  emit newVolDesc(_vd);
}

void vvCanvas::createRenderer()
{
  vvDebugMsg::msg(3, "vvCanvas::createRenderer()");

  vvRenderState state;
  if (_renderer)
  {
    state = *_renderer;
    delete _renderer;
  }

  const float DEFAULT_OBJ_SIZE = 0.6f;
  _vd->resizeEdgeMax(_ov.getViewportWidth() * DEFAULT_OBJ_SIZE);

  vvRendererFactory::Options opt(_currentOptions);
  _renderer = vvRendererFactory::create(_vd, state, _currentRenderer.c_str(), opt);
}

void vvCanvas::updateProjection()
{
  vvDebugMsg::msg(3, "vvCanvas::updateProjection()");

  if (_projectionType == vvObjView::PERSPECTIVE)
  {
    _ov.setProjection(vvObjView::PERSPECTIVE, vvObjView::DEF_FOV, vvObjView::DEF_CLIP_NEAR, vvObjView::DEF_CLIP_FAR);
  }
  else if (_projectionType == vvObjView::ORTHO)
  {
    _ov.setProjection(vvObjView::ORTHO, vvObjView::DEF_VIEWPORT_WIDTH, vvObjView::DEF_CLIP_NEAR, vvObjView::DEF_CLIP_FAR);
  }
}

void vvCanvas::setCurrentFrame(const int frame)
{
  vvDebugMsg::msg(3, "vvCanvas::setCurrentFrame()");

  _renderer->setCurrentFrame(frame);
  emit currentFrame(frame);
  updateGL();
}

void vvCanvas::startAnimation(const double fps)
{
  vvDebugMsg::msg(3, "vvCanvas::startAnimation()");

  _vd->dt = 1.0f / static_cast<float>(fps);
  const float delay = std::abs(_vd->dt * 1000.0f);
  _animTimer->start(static_cast<int>(delay));
}

void vvCanvas::stopAnimation()
{
  vvDebugMsg::msg(3, "vvCanvas::stopAnimation()");

  _animTimer->stop();
}

void vvCanvas::setTimeStep(const int step)
{
  vvDebugMsg::msg(3, "vvCanvas::setTimeStep()");

  int f = step;
  while (f < 0)
  {
    f += _vd->frames;
  }

  while (f >= _vd->frames)
  {
    f -= _vd->frames;
  }

  setCurrentFrame(f);
}

void vvCanvas::incTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::incTimeStep()");

  int f = _renderer->getCurrentFrame();
  f = (f >= _vd->frames - 1) ? 0 : f + 1;
  setCurrentFrame(f);
}

void vvCanvas::decTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::decTimeStep()");

  int f = _renderer->getCurrentFrame();
  f = (f <= 0) ? _vd->frames - 1 : f - 1;
  setCurrentFrame(f);
}

void vvCanvas::firstTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::firstTimeStep()");

  setCurrentFrame(0);
}

void vvCanvas::lastTimeStep()
{
  vvDebugMsg::msg(3, "vvCanvas::lastTimeStep()");

  setCurrentFrame(_vd->frames - 1);
}

<|endoftext|>


<commit_before>#include "connection-manager.h"
#include "glib-helpers.h"
#include "protocol.h"

G_DEFINE_TYPE(SteamConnectionManager, steam_connection_manager, TP_TYPE_BASE_CONNECTION_MANAGER);

static void stema_connection_manager_constructed (GObject * object)
{
	GLIB_CALL_PARENT(steam_connection_manager_parent_class, constructed, object);
	tp_base_connection_manager_add_protocol(TP_BASE_CONNECTION_MANAGER(object), steam_protocol_new());
}

void steam_connection_manager_class_init(SteamConnectionManagerClass * klass)
{
	GObjectClass *object_class = G_OBJECT_CLASS(klass);

	object_class->constructed = stema_connection_manager_constructed;
	klass->parent_class.cm_dbus_name = "steam";
}

void steam_connection_manager_init(SteamConnectionManager * scm)
{

}
<commit_msg>connection-manager: unref created protocol<commit_after>#include "connection-manager.h"
#include "glib-helpers.h"
#include "protocol.h"

G_DEFINE_TYPE(SteamConnectionManager, steam_connection_manager, TP_TYPE_BASE_CONNECTION_MANAGER);

static void stema_connection_manager_constructed (GObject * object)
{
	GLIB_CALL_PARENT(steam_connection_manager_parent_class, constructed, object);

	TpBaseProtocol * p = steam_protocol_new();
	tp_base_connection_manager_add_protocol(TP_BASE_CONNECTION_MANAGER(object), p);
	g_object_unref(p);
}

void steam_connection_manager_class_init(SteamConnectionManagerClass * klass)
{
	GObjectClass *object_class = G_OBJECT_CLASS(klass);

	object_class->constructed = stema_connection_manager_constructed;
	klass->parent_class.cm_dbus_name = "steam";
}

void steam_connection_manager_init(SteamConnectionManager * scm)
{

}
<|endoftext|>


<commit_before>#pragma once

#include <mapbox/geometry.hpp>
#include <mapbox/variant.hpp>

#include <algorithm>
#include <string>
#include <unordered_map>
#include <vector>

namespace mapbox {
namespace geojsonvt {
namespace detail {

struct vt_point : mapbox::geometry::point<double> {
    double z = 0.0; // simplification tolerance

    vt_point(double x_, double y_, double z_) : mapbox::geometry::point<double>(x_, y_), z(z_) {
    }

    vt_point(double x_, double y_) : vt_point(x_, y_, 0.0) {
    }
};

template <uint8_t I, typename T>
inline double get(const T&);

template <>
inline double get<0>(const vt_point& p) {
    return p.x;
}
template <>
inline double get<1>(const vt_point& p) {
    return p.y;
}
template <>
inline double get<0>(const mapbox::geometry::point<double>& p) {
    return p.x;
}
template <>
inline double get<1>(const mapbox::geometry::point<double>& p) {
    return p.y;
}

template <uint8_t I>
inline vt_point intersect(const vt_point&, const vt_point&, const double);

template <>
inline vt_point intersect<0>(const vt_point& a, const vt_point& b, const double x) {
    const double y = (x - a.x) * (b.y - a.y) / (b.x - a.x) + a.y;
    return { x, y, 1.0 };
}
template <>
inline vt_point intersect<1>(const vt_point& a, const vt_point& b, const double y) {
    const double x = (y - a.y) * (b.x - a.x) / (b.y - a.y) + a.x;
    return { x, y, 1.0 };
}

using vt_multi_point = std::vector<vt_point>;

struct vt_line_string : std::vector<vt_point> {
    using container_type = std::vector<vt_point>;
    using container_type::container_type;
    double dist = 0.0; // line length
};

struct vt_linear_ring : std::vector<vt_point> {
    using container_type = std::vector<vt_point>;
    using container_type::container_type;
    double area = 0.0; // polygon ring area
};

using vt_multi_line_string = std::vector<vt_line_string>;
using vt_polygon = std::vector<vt_linear_ring>;
using vt_multi_polygon = std::vector<vt_polygon>;

struct vt_geometry_collection;

using vt_geometry = mapbox::util::variant<vt_point,
                                          vt_line_string,
                                          vt_polygon,
                                          vt_multi_point,
                                          vt_multi_line_string,
                                          vt_multi_polygon,
                                          vt_geometry_collection>;

struct vt_geometry_collection : std::vector<vt_geometry> {};

using property_map = mapbox::geometry::property_map;
using identifier = mapbox::geometry::identifier;

template <class T>
using optional = std::experimental::optional<T>;

template <class T>
struct vt_geometry_type;

template <>
struct vt_geometry_type<geometry::point<double>> {
    using type = vt_point;
};
template <>
struct vt_geometry_type<geometry::line_string<double>> {
    using type = vt_line_string;
};
template <>
struct vt_geometry_type<geometry::polygon<double>> {
    using type = vt_polygon;
};
template <>
struct vt_geometry_type<geometry::multi_point<double>> {
    using type = vt_multi_point;
};
template <>
struct vt_geometry_type<geometry::multi_line_string<double>> {
    using type = vt_multi_line_string;
};
template <>
struct vt_geometry_type<geometry::multi_polygon<double>> {
    using type = vt_multi_polygon;
};
template <>
struct vt_geometry_type<geometry::geometry<double>> {
    using type = vt_geometry;
};
template <>
struct vt_geometry_type<geometry::geometry_collection<double>> {
    using type = vt_geometry_collection;
};

struct vt_feature {
    vt_geometry geometry;
    property_map properties;
    optional<identifier> id;

    mapbox::geometry::box<double> bbox = { { 2, 1 }, { -1, 0 } };
    uint32_t num_points = 0;

    vt_feature(const vt_geometry& geom, const property_map& props, const optional<identifier>& id_)
        : geometry(geom), properties(props), id(id_) {

        mapbox::geometry::for_each_point(geom, [&](const vt_point& p) {
            bbox.min.x = std::min(p.x, bbox.min.x);
            bbox.min.y = std::min(p.y, bbox.min.y);
            bbox.max.x = std::max(p.x, bbox.max.x);
            bbox.max.y = std::max(p.y, bbox.max.y);
            ++num_points;
        });
    }
};

using vt_features = std::vector<vt_feature>;

} // namespace detail
} // namespace geojsonvt
} // namespace mapbox
<commit_msg>Fix compilation errors with libc++ on QNX 7<commit_after>#pragma once

#include <mapbox/geometry.hpp>
#include <mapbox/variant.hpp>

#include <algorithm>
#include <string>
#include <unordered_map>
#include <vector>

namespace mapbox {
namespace geojsonvt {
namespace detail {

struct vt_point : mapbox::geometry::point<double> {
    double z = 0.0; // simplification tolerance

    vt_point(double x_, double y_, double z_) : mapbox::geometry::point<double>(x_, y_), z(z_) {
    }

    vt_point(double x_, double y_) : vt_point(x_, y_, 0.0) {
    }
};

template <uint8_t I, typename T>
inline double get(const T&);

template <>
inline double get<0>(const vt_point& p) {
    return p.x;
}
template <>
inline double get<1>(const vt_point& p) {
    return p.y;
}
template <>
inline double get<0>(const mapbox::geometry::point<double>& p) {
    return p.x;
}
template <>
inline double get<1>(const mapbox::geometry::point<double>& p) {
    return p.y;
}

template <uint8_t I>
inline vt_point intersect(const vt_point&, const vt_point&, const double);

template <>
inline vt_point intersect<0>(const vt_point& a, const vt_point& b, const double x) {
    const double y = (x - a.x) * (b.y - a.y) / (b.x - a.x) + a.y;
    return { x, y, 1.0 };
}
template <>
inline vt_point intersect<1>(const vt_point& a, const vt_point& b, const double y) {
    const double x = (y - a.y) * (b.x - a.x) / (b.y - a.y) + a.x;
    return { x, y, 1.0 };
}

using vt_multi_point = std::vector<vt_point>;

struct vt_line_string : std::vector<vt_point> {
    using container_type = std::vector<vt_point>;
    vt_line_string() = default;
    vt_line_string(std::initializer_list<vt_point> args)
      : container_type(std::move(args)) {}

    double dist = 0.0; // line length
};

struct vt_linear_ring : std::vector<vt_point> {
    using container_type = std::vector<vt_point>;
    vt_linear_ring() = default;
    vt_linear_ring(std::initializer_list<vt_point> args)
      : container_type(std::move(args)) {}

    double area = 0.0; // polygon ring area
};

using vt_multi_line_string = std::vector<vt_line_string>;
using vt_polygon = std::vector<vt_linear_ring>;
using vt_multi_polygon = std::vector<vt_polygon>;

struct vt_geometry_collection;

using vt_geometry = mapbox::util::variant<vt_point,
                                          vt_line_string,
                                          vt_polygon,
                                          vt_multi_point,
                                          vt_multi_line_string,
                                          vt_multi_polygon,
                                          vt_geometry_collection>;

struct vt_geometry_collection : std::vector<vt_geometry> {};

using property_map = mapbox::geometry::property_map;
using identifier = mapbox::geometry::identifier;

template <class T>
using optional = std::experimental::optional<T>;

template <class T>
struct vt_geometry_type;

template <>
struct vt_geometry_type<geometry::point<double>> {
    using type = vt_point;
};
template <>
struct vt_geometry_type<geometry::line_string<double>> {
    using type = vt_line_string;
};
template <>
struct vt_geometry_type<geometry::polygon<double>> {
    using type = vt_polygon;
};
template <>
struct vt_geometry_type<geometry::multi_point<double>> {
    using type = vt_multi_point;
};
template <>
struct vt_geometry_type<geometry::multi_line_string<double>> {
    using type = vt_multi_line_string;
};
template <>
struct vt_geometry_type<geometry::multi_polygon<double>> {
    using type = vt_multi_polygon;
};
template <>
struct vt_geometry_type<geometry::geometry<double>> {
    using type = vt_geometry;
};
template <>
struct vt_geometry_type<geometry::geometry_collection<double>> {
    using type = vt_geometry_collection;
};

struct vt_feature {
    vt_geometry geometry;
    property_map properties;
    optional<identifier> id;

    mapbox::geometry::box<double> bbox = { { 2, 1 }, { -1, 0 } };
    uint32_t num_points = 0;

    vt_feature(const vt_geometry& geom, const property_map& props, const optional<identifier>& id_)
        : geometry(geom), properties(props), id(id_) {

        mapbox::geometry::for_each_point(geom, [&](const vt_point& p) {
            bbox.min.x = std::min(p.x, bbox.min.x);
            bbox.min.y = std::min(p.y, bbox.min.y);
            bbox.max.x = std::max(p.x, bbox.max.x);
            bbox.max.y = std::max(p.y, bbox.max.y);
            ++num_points;
        });
    }
};

using vt_features = std::vector<vt_feature>;

} // namespace detail
} // namespace geojsonvt
} // namespace mapbox
<|endoftext|>


<commit_before>#include <babylon/materials/textures/hdr_cube_texture.h>

#include <nlohmann/json.hpp>

#include <babylon/babylon_stl_util.h>
#include <babylon/core/logging.h>
#include <babylon/engines/constants.h>
#include <babylon/engines/engine.h>
#include <babylon/engines/scene.h>
#include <babylon/materials/material.h>
#include <babylon/materials/textures/internal_texture.h>
#include <babylon/materials/textures/texture_constants.h>
#include <babylon/misc/highdynamicrange/cube_map_to_spherical_polynomial_tools.h>
#include <babylon/misc/highdynamicrange/hdr_tools.h>
#include <babylon/misc/tools.h>

namespace BABYLON {

std::vector<std::string> HDRCubeTexture::_facesMapping{
  "right", //
  "left",  //
  "up",    //
  "down",  //
  "front", //
  "back"   //
};

HDRCubeTexture::HDRCubeTexture(
  const std::string& iUrl, Scene* scene, size_t size, bool iNoMipmap, bool generateHarmonics,
  bool iGammaSpace, bool /*reserved*/, const std::function<void()>& onLoad,
  const std::function<void(const std::string& message, const std::string& exception)>& onError)
    : BaseTexture(scene)
    , url{iUrl}
    , rotationY{this, &HDRCubeTexture::get_rotationY, &HDRCubeTexture::set_rotationY}
    , boundingBoxPosition{Vector3::Zero()}
    , _isBlocking{true}
    , _rotationY{0.f}
    , _generateHarmonics{generateHarmonics}
    , _noMipmap{iNoMipmap}
    , _size{size}
    , _onLoad{onLoad}
    , _onError{onError}
    , _boundingBoxSize{std::nullopt}
{
  if (iUrl.empty()) {
    return;
  }

  name            = iUrl;
  url             = iUrl;
  hasAlpha        = false;
  isCube          = true;
  _textureMatrix  = Matrix::Identity();
  _onLoad         = onLoad;
  _onError        = onError;
  gammaSpace      = iGammaSpace;
  coordinatesMode = TextureConstants::CUBIC_MODE;

  _noMipmap = noMipmap;
  _size     = size;

  _texture = _getFromCache(url, _noMipmap);

  if (!_texture) {
    if (!scene->useDelayedTextureLoading) {
      loadTexture();
    }
    else {
      delayLoadState = Constants::DELAYLOADSTATE_NOTLOADED;
    }
  }
  else if (onLoad) {
    if (_texture->isReady) {
      Tools::SetImmediate([&onLoad]() -> void { onLoad(); });
    }
    else {
      // _texture->onLoadedObservable.add(onLoad);
    }
  }
}

HDRCubeTexture::~HDRCubeTexture() = default;

std::string HDRCubeTexture::getClassName() const
{
  return "HDRCubeTexture";
}

void HDRCubeTexture::set_isBlocking(bool value)
{
  _isBlocking = value;
}

bool HDRCubeTexture::get_isBlocking() const
{
  return _isBlocking;
}

void HDRCubeTexture::set_rotationY(float value)
{
  _rotationY = value;
  auto mat   = Matrix::RotationY(_rotationY);
  setReflectionTextureMatrix(mat);
}

float HDRCubeTexture::get_rotationY() const
{
  return _rotationY;
}

void HDRCubeTexture::set_boundingBoxSize(const std::optional<Vector3>& value)
{
  if (!value.has_value()) {
    return;
  }

  if (_boundingBoxSize && (*_boundingBoxSize).equals(*value)) {
    return;
  }
  _boundingBoxSize = value;
  auto scene       = getScene();
  if (scene) {
    scene->markAllMaterialsAsDirty(Constants::MATERIAL_TextureDirtyFlag);
  }
}

std::optional<Vector3>& HDRCubeTexture::get_boundingBoxSize()
{
  return _boundingBoxSize;
}

void HDRCubeTexture::loadTexture()
{
  const auto callback = [this](const ArrayBuffer& buffer) -> std::vector<ArrayBufferView> {
    lodGenerationOffset = 0.f;
    lodGenerationScale  = 0.8f;

    auto scene = getScene();

    if (!scene) {
      return {};
    }
    // Extract the raw linear data.
    auto data = HDRTools::GetCubeMapTextureData(buffer, _size);

    // Generate harmonics if needed.
    if (_generateHarmonics) {
      auto _sphericalPolynomial
        = CubeMapToSphericalPolynomialTools::ConvertCubeMapToSphericalPolynomial(data);
      sphericalPolynomial = _sphericalPolynomial;
    }

    std::vector<ArrayBufferView> results;
    Uint8Array byteArray;

    // Push each faces.
    for (unsigned int j = 0; j < 6; ++j) {

      // Create uintarray fallback.
      if (!scene->getEngine()->getCaps().textureFloat) {
        // 3 channels of 1 bytes per pixel in bytes.
        byteArray.resize(_size * _size * 3);
      }

      auto dataFace = data[HDRCubeTexture::_facesMapping[j]].float32Array();

      // If special cases.
      if (gammaSpace || !byteArray.empty()) {
        for (size_t i = 0; i < _size * _size; ++i) {

          // Put in gamma space if requested.
          if (gammaSpace) {
            dataFace[(i * 3) + 0] = std::pow(dataFace[(i * 3) + 0], Math::ToGammaSpace);
            dataFace[(i * 3) + 1] = std::pow(dataFace[(i * 3) + 1], Math::ToGammaSpace);
            dataFace[(i * 3) + 2] = std::pow(dataFace[(i * 3) + 2], Math::ToGammaSpace);
          }

          // Convert to int texture for fallback.
          if (!byteArray.empty()) {
            auto r = std::max(dataFace[(i * 3) + 0] * 255, 0.f);
            auto g = std::max(dataFace[(i * 3) + 1] * 255, 0.f);
            auto b = std::max(dataFace[(i * 3) + 2] * 255, 0.f);

            // May use luminance instead if the result is not accurate.
            auto max = std::max(std::max(r, g), b);
            if (max > 255) {
              auto scale = 255.f / max;
              r *= scale;
              g *= scale;
              b *= scale;
            }

            byteArray[(i * 3) + 0] = static_cast<uint8_t>(r);
            byteArray[(i * 3) + 1] = static_cast<uint8_t>(g);
            byteArray[(i * 3) + 2] = static_cast<uint8_t>(b);
          }
        }
      }

      if (!byteArray.empty()) {
        results.emplace_back(byteArray);
      }
      else {
        results.emplace_back(dataFace);
      }
    }
    return results;
  };

  auto scene = getScene();
  if (scene) {
    _texture = scene->getEngine()->createRawCubeTextureFromUrl(
      url, scene, static_cast<int>(_size), Constants::TEXTUREFORMAT_RGB,
      scene->getEngine()->getCaps().textureFloat ? Constants::TEXTURETYPE_FLOAT :
                                                   Constants::TEXTURETYPE_UNSIGNED_INT,
      _noMipmap, callback, nullptr, _onLoad, _onError);
  }
}

HDRCubeTexturePtr HDRCubeTexture::clone() const
{
  auto scene = getScene();
  if (!scene) {
    return nullptr;
  }

  auto newTexture
    = HDRCubeTexture::New(url, scene, _size, _noMipmap, _generateHarmonics, gammaSpace);

  // Base texture
  newTexture->level            = level;
  newTexture->wrapU            = wrapU;
  newTexture->wrapV            = wrapV;
  newTexture->coordinatesIndex = coordinatesIndex;
  newTexture->coordinatesMode  = coordinatesMode();

  return newTexture;
}

void HDRCubeTexture::delayLoad(const std::string& /*forcedExtension*/)
{
  if (delayLoadState != Constants::DELAYLOADSTATE_NOTLOADED) {
    return;
  }

  delayLoadState = Constants::DELAYLOADSTATE_LOADED;
  _texture       = _getFromCache(url, _noMipmap);

  if (!_texture) {
    loadTexture();
  }
}

Matrix* HDRCubeTexture::getReflectionTextureMatrix()
{
  return &_textureMatrix;
}

void HDRCubeTexture::setReflectionTextureMatrix(Matrix& value)
{
  _textureMatrix = value;

  if (value.updateFlag == _textureMatrix.updateFlag) {
    return;
  }

  if (value.isIdentity() != _textureMatrix.isIdentity()) {
    getScene()->markAllMaterialsAsDirty(
      Constants::MATERIAL_TextureDirtyFlag, [this](Material* mat) -> bool {
        auto activeTextures = mat->getActiveTextures();
        auto it
          = std::find_if(activeTextures.begin(), activeTextures.end(),
                         [this](const BaseTexturePtr& texture) { return texture.get() == this; });
        return it != activeTextures.end();
      });
  }
}

HDRCubeTexture* HDRCubeTexture::Parse(const json& /*parsedTexture*/, Scene* /*scene*/,
                                      const std::string& /*rootUrl*/)
{
  return nullptr;
}

json HDRCubeTexture::serialize() const
{
  return nullptr;
}

} // end of namespace BABYLON
<commit_msg>Updated HDRCubeTexture class to v4.1.0<commit_after>#include <babylon/materials/textures/hdr_cube_texture.h>

#include <nlohmann/json.hpp>

#include <babylon/babylon_stl_util.h>
#include <babylon/core/logging.h>
#include <babylon/engines/constants.h>
#include <babylon/engines/engine.h>
#include <babylon/engines/scene.h>
#include <babylon/materials/material.h>
#include <babylon/materials/textures/internal_texture.h>
#include <babylon/materials/textures/texture_constants.h>
#include <babylon/misc/highdynamicrange/cube_map_to_spherical_polynomial_tools.h>
#include <babylon/misc/highdynamicrange/hdr_tools.h>
#include <babylon/misc/tools.h>

namespace BABYLON {

std::vector<std::string> HDRCubeTexture::_facesMapping{
  "right", //
  "left",  //
  "up",    //
  "down",  //
  "front", //
  "back"   //
};

HDRCubeTexture::HDRCubeTexture(
  const std::string& iUrl, Scene* scene, size_t size, bool iNoMipmap, bool generateHarmonics,
  bool iGammaSpace, bool /*reserved*/, const std::function<void()>& onLoad,
  const std::function<void(const std::string& message, const std::string& exception)>& onError)
    : BaseTexture(scene)
    , url{iUrl}
    , rotationY{this, &HDRCubeTexture::get_rotationY, &HDRCubeTexture::set_rotationY}
    , boundingBoxPosition{Vector3::Zero()}
    , _isBlocking{true}
    , _rotationY{0.f}
    , _noMipmap{iNoMipmap}
    , _size{size}
    , _onLoad{onLoad}
    , _onError{onError}
    , _boundingBoxSize{std::nullopt}
{
  if (iUrl.empty()) {
    return;
  }

  name            = iUrl;
  url             = iUrl;
  hasAlpha        = false;
  isCube          = true;
  _textureMatrix  = Matrix::Identity();
  _onLoad         = onLoad;
  _onError        = onError;
  gammaSpace      = iGammaSpace;
  coordinatesMode = TextureConstants::CUBIC_MODE;

  _noMipmap          = noMipmap;
  _size              = size;
  _generateHarmonics = generateHarmonics;

  _texture = _getFromCache(url, _noMipmap);

  if (!_texture) {
    if (!scene->useDelayedTextureLoading) {
      loadTexture();
    }
    else {
      delayLoadState = Constants::DELAYLOADSTATE_NOTLOADED;
    }
  }
  else if (onLoad) {
    if (_texture->isReady) {
      Tools::SetImmediate([&onLoad]() -> void { onLoad(); });
    }
    else {
      // _texture->onLoadedObservable.add(onLoad);
    }
  }
}

HDRCubeTexture::~HDRCubeTexture() = default;

std::string HDRCubeTexture::getClassName() const
{
  return "HDRCubeTexture";
}

void HDRCubeTexture::set_isBlocking(bool value)
{
  _isBlocking = value;
}

bool HDRCubeTexture::get_isBlocking() const
{
  return _isBlocking;
}

void HDRCubeTexture::set_rotationY(float value)
{
  _rotationY = value;
  auto mat   = Matrix::RotationY(_rotationY);
  setReflectionTextureMatrix(mat);
}

float HDRCubeTexture::get_rotationY() const
{
  return _rotationY;
}

void HDRCubeTexture::set_boundingBoxSize(const std::optional<Vector3>& value)
{
  if (!value.has_value()) {
    return;
  }

  if (_boundingBoxSize && (*_boundingBoxSize).equals(*value)) {
    return;
  }
  _boundingBoxSize = value;
  auto scene       = getScene();
  if (scene) {
    scene->markAllMaterialsAsDirty(Constants::MATERIAL_TextureDirtyFlag);
  }
}

std::optional<Vector3>& HDRCubeTexture::get_boundingBoxSize()
{
  return _boundingBoxSize;
}

void HDRCubeTexture::loadTexture()
{
  const auto callback = [this](const ArrayBuffer& buffer) -> std::vector<ArrayBufferView> {
    lodGenerationOffset = 0.f;
    lodGenerationScale  = 0.8f;

    auto scene = getScene();

    if (!scene) {
      return {};
    }
    // Extract the raw linear data.
    auto data = HDRTools::GetCubeMapTextureData(buffer, _size);

    // Generate harmonics if needed.
    if (_generateHarmonics) {
      auto _sphericalPolynomial
        = CubeMapToSphericalPolynomialTools::ConvertCubeMapToSphericalPolynomial(data);
      sphericalPolynomial = _sphericalPolynomial;
    }

    std::vector<ArrayBufferView> results;
    Uint8Array byteArray;

    // Push each faces.
    for (unsigned int j = 0; j < 6; ++j) {

      // Create uintarray fallback.
      if (!scene->getEngine()->getCaps().textureFloat) {
        // 3 channels of 1 bytes per pixel in bytes.
        byteArray.resize(_size * _size * 3);
      }

      auto dataFace = data[HDRCubeTexture::_facesMapping[j]].float32Array();

      // If special cases.
      if (gammaSpace || !byteArray.empty()) {
        for (size_t i = 0; i < _size * _size; ++i) {

          // Put in gamma space if requested.
          if (gammaSpace) {
            dataFace[(i * 3) + 0] = std::pow(dataFace[(i * 3) + 0], Math::ToGammaSpace);
            dataFace[(i * 3) + 1] = std::pow(dataFace[(i * 3) + 1], Math::ToGammaSpace);
            dataFace[(i * 3) + 2] = std::pow(dataFace[(i * 3) + 2], Math::ToGammaSpace);
          }

          // Convert to int texture for fallback.
          if (!byteArray.empty()) {
            auto r = std::max(dataFace[(i * 3) + 0] * 255, 0.f);
            auto g = std::max(dataFace[(i * 3) + 1] * 255, 0.f);
            auto b = std::max(dataFace[(i * 3) + 2] * 255, 0.f);

            // May use luminance instead if the result is not accurate.
            auto max = std::max(std::max(r, g), b);
            if (max > 255) {
              auto scale = 255.f / max;
              r *= scale;
              g *= scale;
              b *= scale;
            }

            byteArray[(i * 3) + 0] = static_cast<uint8_t>(r);
            byteArray[(i * 3) + 1] = static_cast<uint8_t>(g);
            byteArray[(i * 3) + 2] = static_cast<uint8_t>(b);
          }
        }
      }

      if (!byteArray.empty()) {
        results.emplace_back(byteArray);
      }
      else {
        results.emplace_back(dataFace);
      }
    }
    return results;
  };

  auto scene = getScene();
  if (scene) {
    _texture = scene->getEngine()->createRawCubeTextureFromUrl(
      url, scene, static_cast<int>(_size), Constants::TEXTUREFORMAT_RGB,
      scene->getEngine()->getCaps().textureFloat ? Constants::TEXTURETYPE_FLOAT :
                                                   Constants::TEXTURETYPE_UNSIGNED_INT,
      _noMipmap, callback, nullptr, _onLoad, _onError);
  }
}

HDRCubeTexturePtr HDRCubeTexture::clone() const
{
  auto scene = getScene();
  if (!scene) {
    return nullptr;
  }

  auto newTexture
    = HDRCubeTexture::New(url, scene, _size, _noMipmap, _generateHarmonics, gammaSpace);

  // Base texture
  newTexture->level            = level;
  newTexture->wrapU            = wrapU;
  newTexture->wrapV            = wrapV;
  newTexture->coordinatesIndex = coordinatesIndex;
  newTexture->coordinatesMode  = coordinatesMode();

  return newTexture;
}

void HDRCubeTexture::delayLoad(const std::string& /*forcedExtension*/)
{
  if (delayLoadState != Constants::DELAYLOADSTATE_NOTLOADED) {
    return;
  }

  delayLoadState = Constants::DELAYLOADSTATE_LOADED;
  _texture       = _getFromCache(url, _noMipmap);

  if (!_texture) {
    loadTexture();
  }
}

Matrix* HDRCubeTexture::getReflectionTextureMatrix()
{
  return &_textureMatrix;
}

void HDRCubeTexture::setReflectionTextureMatrix(Matrix& value)
{
  _textureMatrix = value;

  if (value.updateFlag == _textureMatrix.updateFlag) {
    return;
  }

  if (value.isIdentity() != _textureMatrix.isIdentity()) {
    getScene()->markAllMaterialsAsDirty(
      Constants::MATERIAL_TextureDirtyFlag, [this](Material* mat) -> bool {
        auto activeTextures = mat->getActiveTextures();
        auto it
          = std::find_if(activeTextures.begin(), activeTextures.end(),
                         [this](const BaseTexturePtr& texture) { return texture.get() == this; });
        return it != activeTextures.end();
      });
  }
}

HDRCubeTexture* HDRCubeTexture::Parse(const json& /*parsedTexture*/, Scene* /*scene*/,
                                      const std::string& /*rootUrl*/)
{
  return nullptr;
}

json HDRCubeTexture::serialize() const
{
  return nullptr;
}

} // end of namespace BABYLON
<|endoftext|>