Example #1
0
// swaps every time (keeps all values visible)
void BinaryInsertionSort(SortArray& A)
{
    for (size_t i = 1; i < A.size(); ++i)
    {
        value_type key = A[i];
        A.mark(i);

        int lo = 0, hi = i;
        while (lo < hi) {
            int mid = (lo + hi) / 2;
            if (key <= A[mid])
                hi = mid;
            else
                lo = mid + 1;
        }

        // item has to go into position lo

        ssize_t j = i - 1;
        while (j >= lo)
        {
            A.swap(j, j+1);
            j--;
        }

        A.unmark(i);
    }
}
Example #2
0
void ScriptDebuggerLocal::profiling_end() {

	int ofs = 0;

	for (int i = 0; i < ScriptServer::get_language_count(); i++) {
		ofs += ScriptServer::get_language(i)->profiling_get_accumulated_data(&pinfo[ofs], pinfo.size() - ofs);
	}

	SortArray<ScriptLanguage::ProfilingInfo, _ScriptDebuggerLocalProfileInfoSort> sort;
	sort.sort(pinfo.ptr(), ofs);

	uint64_t total_us = 0;
	for (int i = 0; i < ofs; i++) {
		total_us += pinfo[i].self_time;
	}

	float total_time = total_us / 1000000.0;

	for (int i = 0; i < ofs; i++) {

		print_line(itos(i) + ":" + pinfo[i].signature);
		float tt = USEC_TO_SEC(pinfo[i].total_time);
		float st = USEC_TO_SEC(pinfo[i].self_time);
		print_line("\ttotal_ms: " + rtos(tt) + "\tself_ms: " + rtos(st) + "total%: " + itos(tt * 100 / total_time) + "\tself%: " + itos(st * 100 / total_time) + "\tcalls: " + itos(pinfo[i].call_count));
	}

	for (int i = 0; i < ScriptServer::get_language_count(); i++) {
		ScriptServer::get_language(i)->profiling_stop();
	}

	profiling = false;
}
Example #3
0
void CombSort(SortArray& A)
{
    const double shrink = 1.3;

    bool swapped = false;
    size_t gap = A.size();

    while ((gap > 1) || swapped)
    {
        if (gap > 1) {
            gap = (size_t)((float)gap / shrink);
        }

        swapped = false;

        for (size_t i = 0; gap + i < A.size(); ++i)
        {
            if (A[i] > A[i + gap])
            {
                A.swap(i, i+gap);
                swapped = true;
            }
        }
    }
}
Example #4
0
void OddEvenSort(SortArray& A)
{
    bool sorted = false;

    while (!sorted)
    {
        sorted = true;

        for (size_t i = 1; i < A.size()-1; i += 2)
        {
            if(A[i] > A[i+1])
            {
                A.swap(i, i+1);
                sorted = false;
            }
        }

        for (size_t i = 0; i < A.size()-1; i += 2)
        {
            if(A[i] > A[i+1])
            {
                A.swap(i, i+1);
                sorted = false;
            }
        }
    }
}
Example #5
0
void CocktailShakerSort(SortArray& A)
{
    size_t lo = 0, hi = A.size()-1, mov = lo;

    while (lo < hi)
    {
        for (size_t i = hi; i > lo; --i)
        {
            if (A[i-1] > A[i])
            {
                A.swap(i-1, i);
                mov = i;
            }
        }

        lo = mov;

        for (size_t i = lo; i < hi; ++i)
        {
            if (A[i] > A[i+1])
            {
                A.swap(i, i+1);
                mov = i;
            }
        }

        hi = mov;
    }
}
Example #6
0
void Array::sort_custom(Object *p_obj,const StringName& p_function){

	ERR_FAIL_NULL(p_obj);

	SortArray<Variant,_ArrayVariantSortCustom> avs;
	avs.compare.obj=p_obj;
	avs.compare.func=p_function;
	avs.sort(_p->array.ptr(),_p->array.size());

}
Example #7
0
Array &Array::sort_custom(Object *p_obj, const StringName &p_function) {

	ERR_FAIL_NULL_V(p_obj, *this);

	SortArray<Variant, _ArrayVariantSortCustom, true> avs;
	avs.compare.obj = p_obj;
	avs.compare.func = p_function;
	avs.sort(_p->array.ptrw(), _p->array.size());
	return *this;
}
void VoxelMeshUpdater::thread_sync(int queue_index, Stats stats) {

	if (!_input.blocks.empty()) {
		// Cleanup input vector

		if (queue_index >= _input.blocks.size()) {
			_input.blocks.clear();

		} else if (queue_index > 0) {

			// Shift up remaining items since we use a Vector
			shift_up(_input.blocks, queue_index);
		}
	}

	stats.remaining_blocks = _input.blocks.size();
	bool needs_sort;

	{
		// Get input
		MutexLock lock(_input_mutex);

		_input.blocks.append_array(_shared_input.blocks);
		_input.priority_position = _shared_input.priority_position;

		_shared_input.blocks.clear();
		_block_indexes.clear();

		needs_sort = _needs_sort;
		_needs_sort = false;
	}

	if(!_output.blocks.empty()) {

//		print_line(String("VoxelMeshUpdater: posting {0} blocks, {1} remaining ; cost [{2}..{3}] usec")
//				   .format(varray(_output.blocks.size(), _input.blocks.size(), stats.min_time, stats.max_time)));

		// Post output
		MutexLock lock(_output_mutex);
		_shared_output.blocks.append_array(_output.blocks);
		_shared_output.stats = stats;
		_output.blocks.clear();
	}

	if (!_input.blocks.empty() && needs_sort) {
		// Re-sort priority

		SortArray<VoxelMeshUpdater::InputBlock, BlockUpdateComparator> sorter;
		sorter.compare.center = _input.priority_position;
		sorter.sort(_input.blocks.ptrw(), _input.blocks.size());
	}
}
Example #9
0
void BubbleSort(SortArray& A)
{
    for (size_t i = 0; i < A.size()-1; ++i)
    {
        for (size_t j = 0; j < A.size()-1 - i; ++j)
        {
            if (A[j] > A[j + 1])
            {
                A.swap(j, j+1);
            }
        }
    }
}
Example #10
0
void SelectionSort(SortArray& A)
{
    volatile ssize_t jMin = 0;
    A.watch(&jMin, 3);

    for (size_t i = 0; i < A.size()-1; ++i)
    {
        jMin = i;

        for (size_t j = i+1; j < A.size(); ++j)
        {
            if (A[j] < A[jMin]) {
                A.mark_swap(j, jMin);
                jMin = j;
            }
        }

        A.swap(i, jMin);

        // mark the last good element
        if (i > 0) A.unmark(i-1);
        A.mark(i);
    }
    A.unwatch_all();
}
Example #11
0
void GnomeSort(SortArray& A)
{
    for (size_t i = 1; i < A.size(); )
    {
        if (A[i] >= A[i-1])
        {
            ++i;
        }
        else
        {
            A.swap(i, i-1);
            if (i > 1) --i;
        }
    }
}
void VoxelProviderThread::thread_sync(int emerge_index, Stats stats) {

	if (!_input.blocks_to_emerge.empty()) {
		// Cleanup emerge vector

		if (emerge_index >= _input.blocks_to_emerge.size()) {
			_input.blocks_to_emerge.clear();

		} else if (emerge_index > 0) {

			// Shift up remaining items since we use a Vector
			shift_up(_input.blocks_to_emerge, emerge_index);
		}
	}

	{
		// Get input
		MutexLock lock(_input_mutex);

		_input.blocks_to_emerge.append_array(_shared_input.blocks_to_emerge);
		_input.blocks_to_immerge.append_array(_shared_input.blocks_to_immerge);
		_input.priority_block_position = _shared_input.priority_block_position;

		_shared_input.blocks_to_emerge.clear();
		_shared_input.blocks_to_immerge.clear();
	}

	stats.remaining_blocks = _input.blocks_to_emerge.size();

//	print_line(String("VoxelProviderThread: posting {0} blocks, {1} remaining ; cost [{2}..{3}] usec")
//			   .format(varray(_output.size(), _input.blocks_to_emerge.size(), stats.min_time, stats.max_time)));

	{
		// Post output
		MutexLock lock(_output_mutex);
		_shared_output.append_array(_output);
		_shared_stats = stats;
		_output.clear();
	}

	if (!_input.blocks_to_emerge.empty()) {
		// Re-sort priority

		SortArray<Vector3i, BlockPositionComparator> sorter;
		sorter.compare.center = _input.priority_block_position;
		sorter.sort(_input.blocks_to_emerge.ptrw(), _input.blocks_to_emerge.size());
	}
}
Example #13
0
static void _generate_contacts_edge_edge(const Vector3 *p_points_A, int p_point_count_A, const Vector3 *p_points_B, int p_point_count_B, _CollectorCallback *p_callback) {

#ifdef DEBUG_ENABLED
	ERR_FAIL_COND(p_point_count_A != 2);
	ERR_FAIL_COND(p_point_count_B != 2); // circle is actually a 4x3 matrix
#endif

	Vector3 rel_A = p_points_A[1] - p_points_A[0];
	Vector3 rel_B = p_points_B[1] - p_points_B[0];

	Vector3 c = rel_A.cross(rel_B).cross(rel_B);

	//if ( Math::abs(rel_A.dot(c) )<_EDGE_IS_VALID_SUPPORT_TRESHOLD ) {
	if (Math::abs(rel_A.dot(c)) < CMP_EPSILON) {

		// should handle somehow..
		//ERR_PRINT("TODO FIX");
		//return;

		Vector3 axis = rel_A.normalized(); //make an axis
		Vector3 base_A = p_points_A[0] - axis * axis.dot(p_points_A[0]);
		Vector3 base_B = p_points_B[0] - axis * axis.dot(p_points_B[0]);

		//sort all 4 points in axis
		real_t dvec[4] = { axis.dot(p_points_A[0]), axis.dot(p_points_A[1]), axis.dot(p_points_B[0]), axis.dot(p_points_B[1]) };

		SortArray<real_t> sa;
		sa.sort(dvec, 4);

		//use the middle ones as contacts
		p_callback->call(base_A + axis * dvec[1], base_B + axis * dvec[1]);
		p_callback->call(base_A + axis * dvec[2], base_B + axis * dvec[2]);

		return;
	}

	real_t d = (c.dot(p_points_B[0]) - p_points_A[0].dot(c)) / rel_A.dot(c);

	if (d < 0.0)
		d = 0.0;
	else if (d > 1.0)
		d = 1.0;

	Vector3 closest_A = p_points_A[0] + rel_A * d;
	Vector3 closest_B = Geometry::get_closest_point_to_segment_uncapped(closest_A, p_points_B);
	p_callback->call(closest_A, closest_B);
}
Example #14
0
// swaps every time (keeps all values visible)
void InsertionSort(SortArray& A)
{
    for (size_t i = 1; i < A.size(); ++i)
    {
        value_type key = A[i];
        A.mark(i);

        ssize_t j = i - 1;
        while (j >= 0 && A[j] > key)
        {
            A.swap(j, j+1);
            j--;
        }

        A.unmark(i);
    }
}
Example #15
0
size_t PartitionLL(SortArray& A, size_t lo, size_t hi)
{
    // pick pivot and move to back
    size_t p = QuickSortSelectPivot(A, lo, hi);

    value_type pivot = A[p];
    A.swap(p, hi-1);
    A.mark(hi-1);

    volatile ssize_t i = lo;
    A.watch(&i, 3);

    for (size_t j = lo; j < hi-1; ++j)
    {
        if (A[j] <= pivot) {
            A.swap(i, j);
            ++i;
        }
    }

    A.swap(i, hi-1);
    A.unmark(hi-1);
    A.unwatch_all();

    return i;
}
Example #16
0
void Merge(SortArray& A, size_t lo, size_t mid, size_t hi)
{
    // mark merge boundaries
    A.mark(lo);
    A.mark(mid,3);
    A.mark(hi-1);

    // allocate output
    std::vector<value_type> out(hi-lo);

    // merge
    size_t i = lo, j = mid, o = 0; // first and second halves
    while (i < mid && j < hi)
    {
        // copy out for fewer time steps
        value_type ai = A[i], aj = A[j];

        out[o++] = (ai < aj ? (++i, ai) : (++j, aj));
    }

    // copy rest
    while (i < mid) out[o++] = A[i++];
    while (j < hi) out[o++] = A[j++];

    ASSERT(o == hi-lo);

    A.unmark(mid);

    // copy back
    for (i = 0; i < hi-lo; ++i)
        A.set(lo + i, out[i]);

    A.unmark(lo);
    A.unmark(hi-1);
}
Example #17
0
void ScriptDebuggerLocal::idle_poll() {

	if (!profiling)
		return;

	uint64_t diff = OS::get_singleton()->get_ticks_usec() - idle_accum;

	if (diff < 1000000) //show every one second
		return;

	idle_accum = OS::get_singleton()->get_ticks_usec();

	int ofs = 0;
	for (int i = 0; i < ScriptServer::get_language_count(); i++) {
		ofs += ScriptServer::get_language(i)->profiling_get_frame_data(&pinfo[ofs], pinfo.size() - ofs);
	}

	SortArray<ScriptLanguage::ProfilingInfo, _ScriptDebuggerLocalProfileInfoSort> sort;
	sort.sort(pinfo.ptr(), ofs);

	//falta el frame time

	uint64_t script_time_us = 0;

	for (int i = 0; i < ofs; i++) {

		script_time_us += pinfo[i].self_time;
	}

	float script_time = USEC_TO_SEC(script_time_us);

	float total_time = frame_time;

	//print script total

	print_line("FRAME: total: " + rtos(frame_time) + " script: " + rtos(script_time) + "/" + itos(script_time * 100 / total_time) + " %");

	for (int i = 0; i < ofs; i++) {

		print_line(itos(i) + ":" + pinfo[i].signature);
		float tt = USEC_TO_SEC(pinfo[i].total_time);
		float st = USEC_TO_SEC(pinfo[i].self_time);
		print_line("\ttotal: " + rtos(tt) + "/" + itos(tt * 100 / total_time) + " % \tself: " + rtos(st) + "/" + itos(st * 100 / total_time) + " % tcalls: " + itos(pinfo[i].call_count));
	}
}
Example #18
0
// with extra item on stack
void InsertionSort2(SortArray& A)
{
    for (size_t i = 1; i < A.size(); ++i)
    {
        value_type tmp, key = A[i];
        A.mark(i);

        ssize_t j = i - 1;
        while (j >= 0 && (tmp = A[j]) > key)
        {
            A.set(j + 1, tmp);
            j--;
        }
        A.set(j + 1, key);

        A.unmark(i);
    }
}
Example #19
0
int ConcavePolygonShape2DSW::_generate_bvh(BVH *p_bvh,int p_len,int p_depth) {

	if (p_len==1) {

		bvh_depth=MAX(p_depth,bvh_depth);
		bvh.push_back(*p_bvh);
		return bvh.size()-1;
	}

	//else sort best

	Rect2 global_aabb=p_bvh[0].aabb;
	for(int i=1;i<p_len;i++) {
		global_aabb=global_aabb.merge(p_bvh[i].aabb);
	}

	if (global_aabb.size.x > global_aabb.size.y) {

		SortArray<BVH,BVH_CompareX> sort;
		sort.sort(p_bvh,p_len);

	} else {

		SortArray<BVH,BVH_CompareY> sort;
		sort.sort(p_bvh,p_len);

	}

	int median = p_len/2;


	BVH node;
	node.aabb=global_aabb;
	int node_idx = bvh.size();
	bvh.push_back(node);

	int l = _generate_bvh(p_bvh,median,p_depth+1);
	int r = _generate_bvh(&p_bvh[median],p_len-median,p_depth+1);
	bvh[node_idx].left=l;
	bvh[node_idx].right=r;

	return node_idx;

}
Example #20
0
void QuickSortLR(SortArray& A, ssize_t lo, ssize_t hi)
{
    // pick pivot and watch
    volatile ssize_t p = QuickSortSelectPivot(A, lo, hi+1);

    value_type pivot = A[p];
    A.watch(&p, 2);

    volatile ssize_t i = lo, j = hi;
    A.watch(&i, 3);
    A.watch(&j, 3);

    while (i <= j)
    {
        while (A[i] < pivot)
            i++;

        while (A[j] > pivot)
            j--;

        if (i <= j)
        {
            A.swap(i,j);

            // follow pivot if it is swapped
            if (p == i) p = j;
            else if (p == j) p = i;

            i++, j--;
        }
    }

    A.unwatch_all();

    if (lo < j)
        QuickSortLR(A, lo, j);

    if (i < hi)
        QuickSortLR(A, i, hi);
}
Example #21
0
std::pair<ssize_t,ssize_t> PartitionTernaryLL(SortArray& A, ssize_t lo, ssize_t hi)
{
    // pick pivot and swap to back
    ssize_t p = QuickSortSelectPivot(A, lo, hi);

    value_type pivot = A[p];
    A.swap(p, hi-1);
    A.mark(hi-1);

    volatile ssize_t i = lo, k = hi-1;
    A.watch(&i, 3);

    for (ssize_t j = lo; j < k; ++j)
    {
        int cmp = A[j].cmp(pivot); // ternary comparison
        if (cmp == 0) {
            A.swap(--k, j);
            --j; // reclassify A[j]
            A.mark(k,4);
        }
        else if (cmp < 0) {
            A.swap(i++, j);
        }
    }

    // unwatch i, because the pivot is swapped there
    // in the first step of the following swap loop.
    A.unwatch_all();

    ssize_t j = i + (hi-k);

    for (ssize_t s = 0; s < hi-k; ++s) {
        A.swap(i+s, hi-1-s);
        A.mark_swap(i+s, hi-1-s);
    }
    A.unmark_all();

    return std::make_pair(i,j);
}
Example #22
0
void ShellSort(SortArray& A)
{
    size_t incs[16] = { 1391376, 463792, 198768, 86961, 33936,
                        13776, 4592, 1968, 861, 336,
                        112, 48, 21, 7, 3, 1 };

    for (size_t k = 0; k < 16; k++)
    {
        for (size_t h = incs[k], i = h; i < A.size(); i++)
        {
            value_type v = A[i];
            size_t j = i;

            while (j >= h && A[j-h] > v)
            {
                A.set(j, A[j-h]);
                j -= h;
            }

            A.set(j, v);
        }
    }
}
Example #23
0
void ScriptDebuggerRemote::_send_profiling_data(bool p_for_frame) {

	int ofs = 0;

	for (int i = 0; i < ScriptServer::get_language_count(); i++) {
		if (p_for_frame)
			ofs += ScriptServer::get_language(i)->profiling_get_frame_data(&profile_info[ofs], profile_info.size() - ofs);
		else
			ofs += ScriptServer::get_language(i)->profiling_get_accumulated_data(&profile_info[ofs], profile_info.size() - ofs);
	}

	for (int i = 0; i < ofs; i++) {
		profile_info_ptrs[i] = &profile_info[i];
	}

	SortArray<ScriptLanguage::ProfilingInfo *, ProfileInfoSort> sa;
	sa.sort(profile_info_ptrs.ptr(), ofs);

	int to_send = MIN(ofs, max_frame_functions);

	//check signatures first
	uint64_t total_script_time = 0;

	for (int i = 0; i < to_send; i++) {

		if (!profiler_function_signature_map.has(profile_info_ptrs[i]->signature)) {

			int idx = profiler_function_signature_map.size();
			packet_peer_stream->put_var("profile_sig");
			packet_peer_stream->put_var(2);
			packet_peer_stream->put_var(profile_info_ptrs[i]->signature);
			packet_peer_stream->put_var(idx);

			profiler_function_signature_map[profile_info_ptrs[i]->signature] = idx;
		}

		total_script_time += profile_info_ptrs[i]->self_time;
	}

	//send frames then

	if (p_for_frame) {
		packet_peer_stream->put_var("profile_frame");
		packet_peer_stream->put_var(8 + profile_frame_data.size() * 2 + to_send * 4);
	} else {
		packet_peer_stream->put_var("profile_total");
		packet_peer_stream->put_var(8 + to_send * 4);
	}

	packet_peer_stream->put_var(Engine::get_singleton()->get_frames_drawn()); //total frame time
	packet_peer_stream->put_var(frame_time); //total frame time
	packet_peer_stream->put_var(idle_time); //idle frame time
	packet_peer_stream->put_var(fixed_time); //fixed frame time
	packet_peer_stream->put_var(fixed_frame_time); //fixed frame time

	packet_peer_stream->put_var(USEC_TO_SEC(total_script_time)); //total script execution time

	if (p_for_frame) {

		packet_peer_stream->put_var(profile_frame_data.size()); //how many profile framedatas to send
		packet_peer_stream->put_var(to_send); //how many script functions to send
		for (int i = 0; i < profile_frame_data.size(); i++) {

			packet_peer_stream->put_var(profile_frame_data[i].name);
			packet_peer_stream->put_var(profile_frame_data[i].data);
		}
	} else {
		packet_peer_stream->put_var(0); //how many script functions to send
		packet_peer_stream->put_var(to_send); //how many script functions to send
	}

	for (int i = 0; i < to_send; i++) {

		int sig_id = -1;

		if (profiler_function_signature_map.has(profile_info_ptrs[i]->signature)) {
			sig_id = profiler_function_signature_map[profile_info_ptrs[i]->signature];
		}

		packet_peer_stream->put_var(sig_id);
		packet_peer_stream->put_var(profile_info_ptrs[i]->call_count);
		packet_peer_stream->put_var(profile_info_ptrs[i]->total_time / 1000000.0);
		packet_peer_stream->put_var(profile_info_ptrs[i]->self_time / 1000000.0);
	}

	if (p_for_frame) {
		profile_frame_data.clear();
	}
}
Example #24
0
Vector<StringName> EditorExportPlatform::get_dependencies(bool p_bundles) const {


	Set<StringName> exported;

	if (FileAccess::exists("res://engine.cfg"))
		exported.insert("res://engine.cfg");

	if (EditorImportExport::get_singleton()->get_export_filter()!=EditorImportExport::EXPORT_SELECTED) {

		String filter;
		if (EditorImportExport::get_singleton()->get_export_filter()==EditorImportExport::EXPORT_ALL) {
			_add_filter_to_list(exported,"*");
		} else {
			_add_to_list(EditorFileSystem::get_singleton()->get_filesystem(),exported);
			_add_filter_to_list(exported,EditorImportExport::get_singleton()->get_export_custom_filter());

		}


	} else {


		Map<String,Map<String,String> > remapped_paths;

		Set<String> scene_extensions;
		Set<String> resource_extensions;

		{

			List<String> l;
	//		SceneLoader::get_recognized_extensions(&l);
	//		for(List<String>::Element *E=l.front();E;E=E->next()) {
	//
	//			scene_extensions.insert(E->get());
	//		}
			ResourceLoader::get_recognized_extensions_for_type("",&l);
			for(List<String>::Element *E=l.front();E;E=E->next()) {

				resource_extensions.insert(E->get());
			}
		}


		List<StringName> toexport;

		EditorImportExport::get_singleton()->get_export_file_list(&toexport);

		print_line("TO EXPORT: "+itos(toexport.size()));


		for (List<StringName>::Element *E=toexport.front();E;E=E->next()) {

			print_line("DEP: "+String(E->get()));
			exported.insert(E->get());
			if (p_bundles && EditorImportExport::get_singleton()->get_export_file_action(E->get())==EditorImportExport::ACTION_BUNDLE) {
				print_line("NO BECAUSE OF BUNDLE!");
				continue; //no dependencies needed to be copied
			}

			List<String> testsubs;
			testsubs.push_back(E->get());

			while(testsubs.size()) {
				//recursive subdep search!
				List<String> deplist;
				ResourceLoader::get_dependencies(testsubs.front()->get(),&deplist);
				testsubs.pop_front();

				List<String> subdeps;

				for (List<String>::Element *F=deplist.front();F;F=F->next()) {

					StringName dep = F->get();

					if (exported.has(dep) || EditorImportExport::get_singleton()->get_export_file_action(dep)!=EditorImportExport::ACTION_NONE)
						continue; //dependency added or to be added
					print_line(" SUBDEP: "+String(dep));

					exported.insert(dep);
					testsubs.push_back(dep);
				}
			}
		}

		_add_filter_to_list(exported,EditorImportExport::get_singleton()->get_export_custom_filter());

	}

	Vector<StringName> ret;
	ret.resize(exported.size());


	int idx=0;
	for(Set<StringName>::Element *E=exported.front();E;E=E->next()) {

		ret[idx++]=E->get();

	}

	SortArray<StringName,__EESortDepCmp> sort; //some platforms work better if this is sorted
	sort.sort(ret.ptr(),ret.size());

	return ret;

}
Example #25
0
void VisualServerCanvas::_render_canvas_item(Item *p_canvas_item, const Transform2D &p_transform, const Rect2 &p_clip_rect, const Color &p_modulate, int p_z, RasterizerCanvas::Item **z_list, RasterizerCanvas::Item **z_last_list, Item *p_canvas_clip, Item *p_material_owner) {

	Item *ci = p_canvas_item;

	if (!ci->visible)
		return;

	Rect2 rect = ci->get_rect();
	Transform2D xform = p_transform * ci->xform;
	Rect2 global_rect = xform.xform(rect);
	global_rect.pos += p_clip_rect.pos;

	if (ci->use_parent_material && p_material_owner)
		ci->material_owner = p_material_owner;
	else {
		p_material_owner = ci;
		ci->material_owner = NULL;
	}

	Color modulate(ci->modulate.r * p_modulate.r, ci->modulate.g * p_modulate.g, ci->modulate.b * p_modulate.b, ci->modulate.a * p_modulate.a);

	if (modulate.a < 0.007)
		return;

	int child_item_count = ci->child_items.size();
	Item **child_items = (Item **)alloca(child_item_count * sizeof(Item *));
	copymem(child_items, ci->child_items.ptr(), child_item_count * sizeof(Item *));

	if (ci->clip) {
		if (p_canvas_clip != NULL) {
			ci->final_clip_rect = p_canvas_clip->final_clip_rect.clip(global_rect);
		} else {
			ci->final_clip_rect = global_rect;
		}
		ci->final_clip_owner = ci;

	} else {
		ci->final_clip_owner = p_canvas_clip;
	}

	if (ci->sort_y) {

		SortArray<Item *, ItemPtrSort> sorter;
		sorter.sort(child_items, child_item_count);
	}

	if (ci->z_relative)
		p_z = CLAMP(p_z + ci->z, VS::CANVAS_ITEM_Z_MIN, VS::CANVAS_ITEM_Z_MAX);
	else
		p_z = ci->z;

	for (int i = 0; i < child_item_count; i++) {

		if (!child_items[i]->behind)
			continue;
		_render_canvas_item(child_items[i], xform, p_clip_rect, modulate, p_z, z_list, z_last_list, (Item *)ci->final_clip_owner, p_material_owner);
	}

	if (ci->copy_back_buffer) {

		ci->copy_back_buffer->screen_rect = xform.xform(ci->copy_back_buffer->rect).clip(p_clip_rect);
	}

	if ((!ci->commands.empty() && p_clip_rect.intersects(global_rect)) || ci->vp_render || ci->copy_back_buffer) {
		//something to draw?
		ci->final_transform = xform;
		ci->final_modulate = Color(modulate.r * ci->self_modulate.r, modulate.g * ci->self_modulate.g, modulate.b * ci->self_modulate.b, modulate.a * ci->self_modulate.a);
		ci->global_rect_cache = global_rect;
		ci->global_rect_cache.pos -= p_clip_rect.pos;
		ci->light_masked = false;

		int zidx = p_z - VS::CANVAS_ITEM_Z_MIN;

		if (z_last_list[zidx]) {
			z_last_list[zidx]->next = ci;
			z_last_list[zidx] = ci;

		} else {
			z_list[zidx] = ci;
			z_last_list[zidx] = ci;
		}

		ci->next = NULL;
	}

	for (int i = 0; i < child_item_count; i++) {

		if (child_items[i]->behind)
			continue;
		_render_canvas_item(child_items[i], xform, p_clip_rect, modulate, p_z, z_list, z_last_list, (Item *)ci->final_clip_owner, p_material_owner);
	}
}
Example #26
0
_FORCE_INLINE_ static void _generate_contacts_edge_edge(const Vector2 * p_points_A,int p_point_count_A, const Vector2 * p_points_B,int p_point_count_B,_CollectorCallback2D *p_collector) {

#ifdef DEBUG_ENABLED
	ERR_FAIL_COND( p_point_count_A != 2 );
	ERR_FAIL_COND( p_point_count_B != 2 ); // circle is actually a 4x3 matrix
#endif


	Vector2 rel_A=p_points_A[1]-p_points_A[0];
	Vector2 rel_B=p_points_B[1]-p_points_B[0];

	Vector2 t = p_collector->normal.tangent();

	real_t dA[2]={t.dot(p_points_A[0]),t.dot(p_points_A[1])};
	Vector2 pA[2]={p_points_A[0],p_points_A[1]};

	if (dA[0]>dA[1]) {
		SWAP(dA[0],dA[1]);
		SWAP(pA[0],pA[1]);
	}

	float dB[2]={t.dot(p_points_B[0]),t.dot(p_points_B[1])};
	Vector2 pB[2]={p_points_B[0],p_points_B[1]};
	if (dB[0]>dB[1]) {
		SWAP(dB[0],dB[1]);
		SWAP(pB[0],pB[1]);
	}


	if (dA[0]<dB[0]) {

		Vector2 n = (p_points_A[1]-p_points_A[0]).normalized().tangent();
		real_t d = n.dot(p_points_A[1]);

		if (dA[1]>dB[1]) {
			//A contains B
			for(int i=0;i<2;i++) {

				Vector2 b = p_points_B[i];
				Vector2 a = n.plane_project(d,b);
				if (p_collector->normal.dot(a) > p_collector->normal.dot(b)-CMP_EPSILON)
					continue;
				p_collector->call(a,b);

			}
		} else {

			// B0,A1 containment

			Vector2 n_B = (p_points_B[1]-p_points_B[0]).normalized().tangent();
			real_t d_B = n_B.dot(p_points_B[1]);

			// first, B on A

			{
				Vector2 b = p_points_B[0];
				Vector2 a = n.plane_project(d,b);
				if (p_collector->normal.dot(a) < p_collector->normal.dot(b)-CMP_EPSILON)
					p_collector->call(a,b);
			}

			// second, A on B

			{
				Vector2 a = p_points_A[1];
				Vector2 b = n_B.plane_project(d_B,a);
				if (p_collector->normal.dot(a) < p_collector->normal.dot(b)-CMP_EPSILON)
					p_collector->call(a,b);
			}



		}


	} else {

		Vector2 n = (p_points_B[1]-p_points_B[0]).normalized().tangent();
		real_t d = n.dot(p_points_B[1]);

		if (dB[1]>dA[1]) {
			//B contains A
			for(int i=0;i<2;i++) {

				Vector2 a = p_points_A[i];
				Vector2 b = n.plane_project(d,a);
				if (p_collector->normal.dot(a) > p_collector->normal.dot(b)-CMP_EPSILON)
					continue;
				p_collector->call(a,b);
			}
		} else {

			// A0,B1 containment
			Vector2 n_A = (p_points_A[1]-p_points_A[0]).normalized().tangent();
			real_t d_A = n_A.dot(p_points_A[1]);

			// first A on B

			{
				Vector2 a = p_points_A[0];
				Vector2 b = n.plane_project(d,a);
				if (p_collector->normal.dot(a) < p_collector->normal.dot(b)-CMP_EPSILON)
					p_collector->call(a,b);

			}

			//second, B on A

			{

				Vector2 b = p_points_B[1];
				Vector2 a = n_A.plane_project(d_A,b);
				if (p_collector->normal.dot(a) < p_collector->normal.dot(b)-CMP_EPSILON)
					p_collector->call(a,b);
			}

		}
	}


#if 0

	Vector2 axis = rel_A.normalized();
	Vector2 axis_B = rel_B.normalized();
	if (axis.dot(axis_B)<0)
		axis_B=-axis_B;
	axis=(axis+axis_B)*0.5;

	Vector2 normal_A = axis.tangent();
	real_t dA = normal_A.dot(p_points_A[0]);
	Vector2 normal_B = rel_B.tangent().normalized();
	real_t dB = normal_A.dot(p_points_B[0]);

	Vector2 A[4]={ normal_A.plane_project(dA,p_points_B[0]), normal_A.plane_project(dA,p_points_B[1]), p_points_A[0], p_points_A[1] };
	Vector2 B[4]={ p_points_B[0], p_points_B[1], normal_B.plane_project(dB,p_points_A[0]), normal_B.plane_project(dB,p_points_A[1]) };

	_generate_contacts_Pair dvec[4];
	for(int i=0;i<4;i++) {
		dvec[i].d=axis.dot(p_points_A[0]-A[i]);
		dvec[i].idx=i;
	}

	SortArray<_generate_contacts_Pair> sa;
	sa.sort(dvec,4);

	for(int i=1;i<=2;i++) {

		Vector2 a = A[i];
		Vector2 b = B[i];
		if (p_collector->normal.dot(a) > p_collector->normal.dot(b)-CMP_EPSILON)
			continue;
		p_collector->call(a,b);
	}

#elif 0
	Vector2 axis = rel_A.normalized(); //make an axis
	Vector2 axis_B = rel_B.normalized();
	if (axis.dot(axis_B)<0)
		axis_B=-axis_B;
	axis=(axis+axis_B)*0.5;
	Vector2 base_A = p_points_A[0] - axis * axis.dot(p_points_A[0]);
	Vector2 base_B = p_points_B[0] - axis * axis.dot(p_points_B[0]);

	//sort all 4 points in axis
	float dvec[4]={ axis.dot(p_points_A[0]), axis.dot(p_points_A[1]), axis.dot(p_points_B[0]), axis.dot(p_points_B[1]) };

	//todo , find max/min and then use 2 central points
	SortArray<float> sa;
	sa.sort(dvec,4);

	//use the middle ones as contacts
	for (int i=1;i<=2;i++) {

		Vector2 a = base_A+axis*dvec[i];
		Vector2 b = base_B+axis*dvec[i];
		if (p_collector->normal.dot(a) > p_collector->normal.dot(b)-0.01) {
			print_line("fail a: "+a);
			print_line("fail b: "+b);
			continue;
		}
		print_line("res a: "+a);
		print_line("res b: "+b);
		p_collector->call(a,b);
	}
#endif
}
Example #27
0
void MergeSort(SortArray& A)
{
    return MergeSort(A, 0, A.size());
}
Example #28
0
void QuickSortTernaryLR(SortArray& A, ssize_t lo, ssize_t hi)
{
    if (hi <= lo) return;

    int cmp;

    // pick pivot and swap to back
    ssize_t piv = QuickSortSelectPivot(A, lo, hi+1);
    A.swap(piv, hi);
    A.mark(hi);

    const value_type& pivot = A[hi];

    // schema: |p ===  |i <<< | ??? |j >>> |q === |piv
    volatile ssize_t i = lo, j = hi-1;
    volatile ssize_t p = lo, q = hi-1;

    A.watch(&i, 3);
    A.watch(&j, 3);

    for (;;)
    {
        // partition on left
        while (i <= j && (cmp = A[i].cmp(pivot)) <= 0)
        {
            if (cmp == 0) {
                A.mark(p,4);
                A.swap(i, p++);
            }
            ++i;
        }

        // partition on right
        while (i <= j && (cmp = A[j].cmp(pivot)) >= 0)
        {
            if (cmp == 0) {
                A.mark(q,4);
                A.swap(j, q--);
            }
            --j;
        }

        if (i > j) break;

        // swap item between < > regions
        A.swap(i++, j--);
    }

    // swap pivot to right place
    A.swap(i,hi);
    A.mark_swap(i,hi);

    ssize_t num_less = i - p;
    ssize_t num_greater = q - j;

    // swap equal ranges into center, but avoid swapping equal elements
    j = i-1; i = i+1;

    ssize_t pe = lo + std::min(p-lo, num_less);
    for (ssize_t k = lo; k < pe; k++, j--) {
        A.swap(k,j);
        A.mark_swap(k,j);
    }

    ssize_t qe = hi-1 - std::min(hi-1-q, num_greater-1); // one already greater at end
    for (ssize_t k = hi-1; k > qe; k--, i++) {
        A.swap(i,k);
        A.mark_swap(i,k);
    }

    A.unwatch_all();
    A.unmark_all();

    QuickSortTernaryLR(A, lo, lo + num_less - 1);
    QuickSortTernaryLR(A, hi - num_greater + 1, hi);
}
Example #29
0
void QuickSortTernaryLR(SortArray& A)
{
    return QuickSortTernaryLR(A, 0, A.size()-1);
}
Example #30
0
void QuickSortTernaryLL(SortArray& A)
{
    return QuickSortTernaryLL(A, 0, A.size());
}