Ejemplo n.º 1
0
DVector<DVector<Face3> > Geometry::separate_objects(DVector<Face3> p_array) {

	DVector<DVector<Face3> > objects;

	int len = p_array.size();

	DVector<Face3>::Read r = p_array.read();

	const Face3 *arrayptr = r.ptr();

	DVector<_FaceClassify> fc;

	fc.resize(len);

	DVector<_FaceClassify>::Write fcw = fc.write();

	_FaceClassify *_fcptr = fcw.ptr();

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

		_fcptr[i].face = arrayptr[i];
	}

	bool error = _connect_faces(_fcptr, len, -1);

	if (error) {

		ERR_FAIL_COND_V(error, DVector<DVector<Face3> >()); // invalid geometry
	}

	/* group connected faces in separate objects */

	int group = 0;
	for (int i = 0; i < len; i++) {

		if (!_fcptr[i].valid)
			continue;
		if (_group_face(_fcptr, len, i, group)) {
			group++;
		}
	}

	/* group connected faces in separate objects */

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

		_fcptr[i].face = arrayptr[i];
	}

	if (group >= 0) {

		objects.resize(group);
		DVector<DVector<Face3> >::Write obw = objects.write();
		DVector<Face3> *group_faces = obw.ptr();

		for (int i = 0; i < len; i++) {
			if (!_fcptr[i].valid)
				continue;
			if (_fcptr[i].group >= 0 && _fcptr[i].group < group) {

				group_faces[_fcptr[i].group].push_back(_fcptr[i].face);
			}
		}
	}

	return objects;
}
Ejemplo n.º 2
0
RID VisualServer::_make_test_cube() {

	DVector<Vector3> vertices;
	DVector<Vector3> normals;
	DVector<float> tangents;	
	DVector<Vector3> uvs;
							
	int vtx_idx=0;
#define ADD_VTX(m_idx);\
	vertices.push_back( face_points[m_idx] );\
	normals.push_back( normal_points[m_idx] );\
	tangents.push_back( normal_points[m_idx][1] );\
	tangents.push_back( normal_points[m_idx][2] );\
	tangents.push_back( normal_points[m_idx][0] );\
	tangents.push_back( 1.0 );\
	uvs.push_back( Vector3(uv_points[m_idx*2+0],uv_points[m_idx*2+1],0) );\
	vtx_idx++;\

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

	
		Vector3 face_points[4];
		Vector3 normal_points[4];
		float uv_points[8]={0,0,0,1,1,1,1,0};
	
		for (int j=0;j<4;j++) {
		
			float v[3];
			v[0]=1.0;
			v[1]=1-2*((j>>1)&1);
			v[2]=v[1]*(1-2*(j&1));
		
			for (int k=0;k<3;k++) {
			
				if (i<3)
					face_points[j][(i+k)%3]=v[k]*(i>=3?-1:1);
				else
					face_points[3-j][(i+k)%3]=v[k]*(i>=3?-1:1);
			}
			normal_points[j]=Vector3();
			normal_points[j][i%3]=(i>=3?-1:1);
		}

	//tri 1
		ADD_VTX(0);
		ADD_VTX(1);
		ADD_VTX(2);
	//tri 2
		ADD_VTX(2);
		ADD_VTX(3);
		ADD_VTX(0);

	}

	RID test_cube = mesh_create();

	Array d;
	d.resize(VS::ARRAY_MAX);
	d[VisualServer::ARRAY_NORMAL]= normals ;
	d[VisualServer::ARRAY_TANGENT]= tangents ;
	d[VisualServer::ARRAY_TEX_UV]= uvs ;
	d[VisualServer::ARRAY_VERTEX]= vertices ;

	DVector<int> indices;
	indices.resize(vertices.size());
	for(int i=0;i<vertices.size();i++)
		indices.set(i,i);
	d[VisualServer::ARRAY_INDEX]=indices;

	mesh_add_surface( test_cube, PRIMITIVE_TRIANGLES,d );
	

	RID material = fixed_material_create();
	//material_set_flag(material, MATERIAL_FLAG_BILLBOARD_TOGGLE,true);
	fixed_material_set_texture( material, FIXED_MATERIAL_PARAM_DIFFUSE, get_test_texture() );
	fixed_material_set_param( material, FIXED_MATERIAL_PARAM_SPECULAR_EXP, 70 );
	fixed_material_set_param( material, FIXED_MATERIAL_PARAM_EMISSION, Vector3(0.2,0.2,0.2) );

	fixed_material_set_param( material, FIXED_MATERIAL_PARAM_DIFFUSE, Color(1, 1, 1) );
	fixed_material_set_param( material, FIXED_MATERIAL_PARAM_SPECULAR, Color(1,1,1) );

	mesh_surface_set_material(test_cube, 0, material );
	
	return test_cube;
}
bool NavigationPolygonEditor::forward_input_event(const InputEvent& p_event) {


	if (!node)
		return false;

	if (node->get_navigation_polygon().is_null()) {
		if (p_event.type==InputEvent::MOUSE_BUTTON && p_event.mouse_button.button_index==1 && p_event.mouse_button.pressed) {
			create_nav->set_text("No NavigationPolygon resource on this node.\nCreate and assign one?");
			create_nav->popup_centered_minsize();
		}
		return (p_event.type==InputEvent::MOUSE_BUTTON && p_event.mouse_button.button_index==1);;
	}


	switch(p_event.type) {

		case InputEvent::MOUSE_BUTTON: {

			const InputEventMouseButton &mb=p_event.mouse_button;

			Matrix32 xform = canvas_item_editor->get_canvas_transform() * node->get_global_transform();


			Vector2 gpoint = Point2(mb.x,mb.y);
			Vector2 cpoint = canvas_item_editor->get_canvas_transform().affine_inverse().xform(gpoint);
			cpoint=canvas_item_editor->snap_point(cpoint);
			cpoint = node->get_global_transform().affine_inverse().xform(cpoint);



			//first check if a point is to be added (segment split)
			real_t grab_treshold=EDITOR_DEF("poly_editor/point_grab_radius",8);

			switch(mode) {


				case MODE_CREATE: {

					if (mb.button_index==BUTTON_LEFT && mb.pressed) {


						if (!wip_active) {

							wip.clear();
							wip.push_back( cpoint );
							wip_active=true;
							edited_point_pos=cpoint;
							edited_outline=-1;
							canvas_item_editor->get_viewport_control()->update();
							edited_point=1;
							return true;
						} else {


							if (wip.size()>1 && xform.xform(wip[0]).distance_to(gpoint)<grab_treshold) {
								//wip closed
								_wip_close();

								return true;
							} else {

								wip.push_back( cpoint );
								edited_point=wip.size();
								canvas_item_editor->get_viewport_control()->update();
								return true;

								//add wip point
							}
						}
					} else if (mb.button_index==BUTTON_RIGHT && mb.pressed && wip_active) {
						_wip_close();
					}



				} break;

				case MODE_EDIT: {

					if (mb.button_index==BUTTON_LEFT) {
						if (mb.pressed) {

							if (mb.mod.control) {


								//search edges
								int closest_outline=-1;
								int closest_idx=-1;
								Vector2 closest_pos;
								real_t closest_dist=1e10;

								for(int j=0;j<node->get_navigation_polygon()->get_outline_count();j++) {


									DVector<Vector2> points=node->get_navigation_polygon()->get_outline(j);

									int pc=points.size();
									DVector<Vector2>::Read poly=points.read();

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

										Vector2 points[2] ={ xform.xform(poly[i]),
											xform.xform(poly[(i+1)%pc]) };

										Vector2 cp = Geometry::get_closest_point_to_segment_2d(gpoint,points);
										if (cp.distance_squared_to(points[0])<CMP_EPSILON2 || cp.distance_squared_to(points[1])<CMP_EPSILON2)
											continue; //not valid to reuse point

										real_t d = cp.distance_to(gpoint);
										if (d<closest_dist && d<grab_treshold) {
											closest_dist=d;
											closest_outline=j;
											closest_pos=cp;
											closest_idx=i;
										}


									}
								}

								if (closest_idx>=0) {

									pre_move_edit=node->get_navigation_polygon()->get_outline(closest_outline);
									DVector<Point2> poly = pre_move_edit;
									poly.insert(closest_idx+1,xform.affine_inverse().xform(closest_pos));
									edited_point=closest_idx+1;
									edited_outline=closest_outline;
									edited_point_pos=xform.affine_inverse().xform(closest_pos);
									node->get_navigation_polygon()->set_outline(closest_outline,poly);
									canvas_item_editor->get_viewport_control()->update();
									return true;
								}
							} else {

								//look for points to move
								int closest_outline=-1;
								int closest_idx=-1;
								Vector2 closest_pos;
								real_t closest_dist=1e10;

								for(int j=0;j<node->get_navigation_polygon()->get_outline_count();j++) {


									DVector<Vector2> points=node->get_navigation_polygon()->get_outline(j);

									int pc=points.size();
									DVector<Vector2>::Read poly=points.read();

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


										Vector2 cp =xform.xform(poly[i]);

										real_t d = cp.distance_to(gpoint);
										if (d<closest_dist && d<grab_treshold) {
											closest_dist=d;
											closest_pos=cp;
											closest_outline=j;
											closest_idx=i;
										}
									}
								}

								if (closest_idx>=0) {

									pre_move_edit=node->get_navigation_polygon()->get_outline(closest_outline);
									edited_point=closest_idx;
									edited_outline=closest_outline;
									edited_point_pos=xform.affine_inverse().xform(closest_pos);
									canvas_item_editor->get_viewport_control()->update();
									return true;
								}
							}
						} else {

							if (edited_point!=-1) {

								//apply

								DVector<Vector2> poly = node->get_navigation_polygon()->get_outline(edited_outline);
								ERR_FAIL_INDEX_V(edited_point,poly.size(),false);
								poly.set(edited_point,edited_point_pos);
								undo_redo->create_action(TTR("Edit Poly"));
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"set_outline",edited_outline,poly);
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"set_outline",edited_outline,pre_move_edit);
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_do_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->add_undo_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->commit_action();

								edited_point=-1;
								return true;
							}
						}
					} if (mb.button_index==BUTTON_RIGHT && mb.pressed && edited_point==-1) {

						int closest_outline=-1;
						int closest_idx=-1;
						Vector2 closest_pos;
						real_t closest_dist=1e10;

						for(int j=0;j<node->get_navigation_polygon()->get_outline_count();j++) {


							DVector<Vector2> points=node->get_navigation_polygon()->get_outline(j);

							int pc=points.size();
							DVector<Vector2>::Read poly=points.read();

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


								Vector2 cp =xform.xform(poly[i]);

								real_t d = cp.distance_to(gpoint);
								if (d<closest_dist && d<grab_treshold) {
									closest_dist=d;
									closest_pos=cp;
									closest_outline=j;
									closest_idx=i;
								}
							}
						}

						if (closest_idx>=0) {


							DVector<Vector2> poly = node->get_navigation_polygon()->get_outline(closest_outline);

							if (poly.size()>3) {
								undo_redo->create_action(TTR("Edit Poly (Remove Point)"));
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"set_outline",closest_outline,poly);
								poly.remove(closest_idx);
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"set_outline",closest_outline,poly);
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_do_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->add_undo_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->commit_action();
							} else {

								undo_redo->create_action(TTR("Remove Poly And Point"));
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"add_outline_at_index",poly,closest_outline);
								poly.remove(closest_idx);
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"remove_outline",closest_outline);
								undo_redo->add_do_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_undo_method(node->get_navigation_polygon().ptr(),"make_polygons_from_outlines");
								undo_redo->add_do_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->add_undo_method(canvas_item_editor->get_viewport_control(),"update");
								undo_redo->commit_action();

							}
							return true;
						}
					}



				} break;
			}



		} break;
		case InputEvent::MOUSE_MOTION: {

			const InputEventMouseMotion &mm=p_event.mouse_motion;

			if (edited_point!=-1 && (wip_active || mm.button_mask&BUTTON_MASK_LEFT)) {

				Vector2 gpoint = Point2(mm.x,mm.y);
				Vector2 cpoint = canvas_item_editor->get_canvas_transform().affine_inverse().xform(gpoint);
				cpoint=canvas_item_editor->snap_point(cpoint);
				edited_point_pos = node->get_global_transform().affine_inverse().xform(cpoint);

				canvas_item_editor->get_viewport_control()->update();

			}

		} break;
	}

	return false;
}
Ejemplo n.º 4
0
void FileDialog::_action_pressed() {
	
	if (mode==MODE_OPEN_FILES) {

		TreeItem *ti=tree->get_next_selected(NULL);
		String fbase=dir_access->get_current_dir();

		DVector<String> files;
		while(ti) {

			files.push_back( fbase.plus_file(ti->get_text(0)) );
			ti=tree->get_next_selected(ti);
		}

		if (files.size()) {
			emit_signal("files_selected",files);
			hide();
		}

		return;
	}

	String f=dir_access->get_current_dir().plus_file(file->get_text());
	                   
	if (mode==MODE_OPEN_FILE && dir_access->file_exists(f)) {
		emit_signal("file_selected",f);
		hide();
	}

	if (mode==MODE_OPEN_DIR) {


		String path=dir_access->get_current_dir();
		/*if (tree->get_selected()) {
			Dictionary d = tree->get_selected()->get_metadata(0);
			if (d["dir"]) {
				path=path+"/"+String(d["name"]);
			}
		}*/
		path=path.replace("\\","/");
		emit_signal("dir_selected",path);
		hide();
	}

	if (mode==MODE_SAVE_FILE) {
		
		bool valid=false;

		if (filter->get_selected()==filter->get_item_count()-1) {
			valid=true; //match none
		} else if (filters.size()>1 && filter->get_selected()==0) {
			// match all filters
			for (int i=0;i<filters.size();i++) {

				String flt=filters[i].get_slice(";",0);
				for (int j=0;j<flt.get_slice_count(",");j++) {

					String str = flt.get_slice(",",j).strip_edges();
					if (f.match(str)) {
						valid=true;
						break;
					}
				}
				if (valid)
					break;
			}
		} else {
			int idx=filter->get_selected();
			if (filters.size()>1)
				idx--;
			if (idx>=0 && idx<filters.size()) {

				String flt=filters[idx].get_slice(";",0);
				int filterSliceCount=flt.get_slice_count(",");
				for (int j=0;j<filterSliceCount;j++) {

					String str = (flt.get_slice(",",j).strip_edges());
					if (f.match(str)) {
						valid=true;
						break;
					}
				}

				if (!valid && filterSliceCount>0) {
					String str = (flt.get_slice(",",0).strip_edges());
					f+=str.substr(1, str.length()-1);
					file->set_text(f.get_file());
					valid=true;
				}
			} else {
				valid=true;
			}
		}


		if (!valid) {

			exterr->popup_centered_minsize(Size2(250,80));
			return;

		}

		if (dir_access->file_exists(f)) {
			confirm_save->set_text("File Exists, Overwrite?");
			confirm_save->popup_centered(Size2(200,80));
		} else {
			

			emit_signal("file_selected",f);
			hide();
		}
	}
}
Ejemplo n.º 5
0
void PathRemap::load_remaps() {

	// default remaps first
	DVector<String> remaps = GlobalConfig::get_singleton()->get("remap/all");

	{
		int rlen = remaps.size();

		ERR_FAIL_COND( rlen%2 );
		DVector<String>::Read r = remaps.read();
		for(int i=0;i<rlen/2;i++) {

			String from = r[i*2+0];
			String to = r[i*2+1];
			add_remap(from,to);
		}
	}


	// platform remaps second, so override
	remaps = GlobalConfig::get_singleton()->get("remap/"+OS::get_singleton()->get_name());
//	remaps = Globals::get_singleton()->get("remap/PSP");
	{
		int rlen = remaps.size();

		ERR_FAIL_COND( rlen%2 );
		DVector<String>::Read r = remaps.read();
		for(int i=0;i<rlen/2;i++) {

			String from = r[i*2+0];
			String to = r[i*2+1];
//			print_line("add remap: "+from+" -> "+to);
			add_remap(from,to);
		}
	}


	//locale based remaps

	if (GlobalConfig::get_singleton()->has("locale/translation_remaps")) {

		Dictionary remaps = GlobalConfig::get_singleton()->get("locale/translation_remaps");
		List<Variant> rk;
		remaps.get_key_list(&rk);
		for(List<Variant>::Element *E=rk.front();E;E=E->next()) {

			String source = E->get();
			StringArray sa = remaps[E->get()];
			int sas = sa.size();
			StringArray::Read r = sa.read();

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

				String s = r[i];
				int qp = s.find_last(":");
				if (qp!=-1) {
					String path = s.substr(0,qp);
					String locale = s.substr(qp+1,s.length());
					add_remap(source,path,locale);
				}
			}
		}

	}

}
Ejemplo n.º 6
0
void NavigationPolygon::make_polygons_from_outlines() {

    List<TriangulatorPoly> in_poly,out_poly;

    Vector2 outside_point(-1e10,-1e10);

    for(int i=0; i<outlines.size(); i++) {

        DVector<Vector2> ol = outlines[i];
        int olsize = ol.size();
        if (olsize<3)
            continue;
        DVector<Vector2>::Read r=ol.read();
        for(int j=0; j<olsize; j++) {
            outside_point.x = MAX( r[j].x, outside_point.x );
            outside_point.y = MAX( r[j].y, outside_point.y );
        }

    }

    outside_point+=Vector2(0.7239784,0.819238); //avoid precision issues



    for(int i=0; i<outlines.size(); i++) {

        DVector<Vector2> ol = outlines[i];
        int olsize = ol.size();
        if (olsize<3)
            continue;
        DVector<Vector2>::Read r=ol.read();

        int interscount=0;
        //test if this is an outer outline
        for(int k=0; k<outlines.size(); k++) {

            if (i==k)
                continue; //no self intersect

            DVector<Vector2> ol2 = outlines[k];
            int olsize2 = ol2.size();
            if (olsize2<3)
                continue;
            DVector<Vector2>::Read r2=ol2.read();

            for(int l=0; l<olsize2; l++) {

                if (Geometry::segment_intersects_segment_2d(r[0],outside_point,r2[l],r2[(l+1)%olsize2],NULL)) {
                    interscount++;
                }
            }

        }

        bool outer = (interscount%2)==0;

        TriangulatorPoly tp;
        tp.Init(olsize);
        for(int j=0; j<olsize; j++) {
            tp[j]=r[j];
        }

        if (outer)
            tp.SetOrientation(TRIANGULATOR_CCW);
        else {
            tp.SetOrientation(TRIANGULATOR_CW);
            tp.SetHole(true);
        }

        in_poly.push_back(tp);
    }


    TriangulatorPartition tpart;
    if (tpart.ConvexPartition_HM(&in_poly,&out_poly)==0) { //failed!
        print_line("convex partition failed!");
        return;
    }

    polygons.clear();
    vertices.resize(0);

    Map<Vector2,int> points;
    for(List<TriangulatorPoly>::Element*I = out_poly.front(); I; I=I->next()) {

        TriangulatorPoly& tp = I->get();

        struct Polygon p;

        for(int i=0; i<tp.GetNumPoints(); i++) {

            Map<Vector2,int>::Element *E=points.find(tp[i]);
            if (!E) {
                E=points.insert(tp[i],vertices.size());
                vertices.push_back(tp[i]);
            }
            p.indices.push_back(E->get());
        }

        polygons.push_back(p);
    }

    emit_signal(CoreStringNames::get_singleton()->changed);
}
void Polygon2DEditor::_menu_option(int p_option) {

	switch(p_option) {

		case MODE_CREATE: {

			mode=MODE_CREATE;
			button_create->set_pressed(true);
			button_edit->set_pressed(false);
		} break;
		case MODE_EDIT: {

			mode=MODE_EDIT;
			button_create->set_pressed(false);
			button_edit->set_pressed(true);
		} break;
		case MODE_EDIT_UV: {

			if (node->get_texture().is_null()) {

				error->set_text("No texture in this polygon.\nSet a texture to be able to edit UV.");
				error->popup_centered_minsize();
				return;
			}


			DVector<Vector2> points = node->get_polygon();
			DVector<Vector2> uvs = node->get_uv();
			if (uvs.size()!=points.size()) {
				undo_redo->create_action("Create UV Map");
				undo_redo->add_do_method(node,"set_uv",points);
				undo_redo->add_undo_method(node,"set_uv",uvs);
				undo_redo->add_do_method(uv_edit_draw,"update");
				undo_redo->add_undo_method(uv_edit_draw,"update");
				undo_redo->commit_action();

			}


			uv_edit->popup_centered_ratio(0.85);
		} break;
		case UVEDIT_POLYGON_TO_UV: {

			DVector<Vector2> points = node->get_polygon();
			if (points.size()==0)
				break;
			DVector<Vector2> uvs = node->get_uv();
			undo_redo->create_action("Create UV Map");
			undo_redo->add_do_method(node,"set_uv",points);
			undo_redo->add_undo_method(node,"set_uv",uvs);
			undo_redo->add_do_method(uv_edit_draw,"update");
			undo_redo->add_undo_method(uv_edit_draw,"update");
			undo_redo->commit_action();


		} break;
		case UVEDIT_UV_TO_POLYGON: {

			DVector<Vector2> points = node->get_polygon();
			DVector<Vector2> uvs = node->get_uv();
			if (uvs.size()==0)
				break;

			undo_redo->create_action("Create UV Map");
			undo_redo->add_do_method(node,"set_polygon",uvs);
			undo_redo->add_undo_method(node,"set_polygon",points);
			undo_redo->add_do_method(uv_edit_draw,"update");
			undo_redo->add_undo_method(uv_edit_draw,"update");
			undo_redo->commit_action();

		} break;
		case UVEDIT_UV_CLEAR: {

			DVector<Vector2> uvs = node->get_uv();
			if (uvs.size()==0)
				break;
			undo_redo->create_action("Create UV Map");
			undo_redo->add_do_method(node,"set_uv",DVector<Vector2>());
			undo_redo->add_undo_method(node,"set_uv",uvs);
			undo_redo->add_do_method(uv_edit_draw,"update");
			undo_redo->add_undo_method(uv_edit_draw,"update");
			undo_redo->commit_action();

		} break;


	}
}
Ejemplo n.º 8
0
	virtual Variant call(const StringName& p_method,const Variant** p_args,int p_argcount,Variant::CallError &r_error) {

		print_line("attempt to call "+String(p_method));

		r_error.error=Variant::CallError::CALL_OK;

		Map<StringName,MethodData >::Element *E=method_map.find(p_method);
		if (!E) {

			print_line("no exists");
			r_error.error=Variant::CallError::CALL_ERROR_INVALID_METHOD;
			return Variant();
		}


		int ac = E->get().argtypes.size();
		if (ac<p_argcount) {

			print_line("fewargs");
			r_error.error=Variant::CallError::CALL_ERROR_TOO_FEW_ARGUMENTS;
			r_error.argument=ac;
			return Variant();
		}

		if (ac>p_argcount) {

			print_line("manyargs");
			r_error.error=Variant::CallError::CALL_ERROR_TOO_MANY_ARGUMENTS;
			r_error.argument=ac;
			return Variant();
		}



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

			if (!Variant::can_convert(p_args[i]->get_type(),E->get().argtypes[i])) {

				r_error.error=Variant::CallError::CALL_ERROR_INVALID_ARGUMENT;
				r_error.argument=i;
				r_error.expected=E->get().argtypes[i];
			}
		}


		jvalue *v=NULL;

		if (p_argcount) {

			v=(jvalue*)alloca( sizeof(jvalue)*p_argcount );
		}

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


			switch(E->get().argtypes[i]) {

				case Variant::BOOL: {

					v[i].z=*p_args[i];
				} break;
				case Variant::INT: {

					v[i].i=*p_args[i];
				} break;
				case Variant::REAL: {

					v[i].f=*p_args[i];
				} break;
				case Variant::STRING: {

					String s = *p_args[i];
					jstring jStr = env->NewStringUTF(s.utf8().get_data());
					v[i].l=jStr;
				} break;
				case Variant::STRING_ARRAY: {

					DVector<String> sarray = *p_args[i];
					jobjectArray arr = env->NewObjectArray(sarray.size(),env->FindClass("java/lang/String"),env->NewStringUTF(""));

					for(int j=0;j<sarray.size();j++) {

						env->SetObjectArrayElement(arr,j,env->NewStringUTF( sarray[i].utf8().get_data() ));
					}
					v[i].l=arr;

				} break;
				case Variant::INT_ARRAY: {

					DVector<int> array = *p_args[i];
					jintArray arr = env->NewIntArray(array.size());
					DVector<int>::Read r = array.read();
					env->SetIntArrayRegion(arr,0,array.size(),r.ptr());
					v[i].l=arr;

				} break;
				case Variant::REAL_ARRAY: {

					DVector<float> array = *p_args[i];
					jfloatArray arr = env->NewFloatArray(array.size());
					DVector<float>::Read r = array.read();
					env->SetFloatArrayRegion(arr,0,array.size(),r.ptr());
					v[i].l=arr;

				} break;
				default: {

					ERR_FAIL_V(Variant());
				} break;

			}
		}

		print_line("calling method!!");

		Variant ret;

		switch(E->get().ret_type) {

			case Variant::NIL: {


				print_line("call void");
				env->CallVoidMethodA(instance,E->get().method,v);
			} break;
			case Variant::BOOL: {

				ret = env->CallBooleanMethodA(instance,E->get().method,v);
				print_line("call bool");
			} break;
			case Variant::INT: {

				ret = env->CallIntMethodA(instance,E->get().method,v);
				print_line("call int");
			} break;
			case Variant::REAL: {

				ret = env->CallFloatMethodA(instance,E->get().method,v);
			} break;
			case Variant::STRING: {

				jobject o = env->CallObjectMethodA(instance,E->get().method,v);
				String singname = env->GetStringUTFChars((jstring)o, NULL );
			} break;
			case Variant::STRING_ARRAY: {

				jobjectArray arr = (jobjectArray)env->CallObjectMethodA(instance,E->get().method,v);

				int stringCount = env->GetArrayLength(arr);
				DVector<String> sarr;

				for (int i=0; i<stringCount; i++) {
					jstring string = (jstring) env->GetObjectArrayElement(arr, i);
					const char *rawString = env->GetStringUTFChars(string, 0);
					sarr.push_back(String(rawString));
				}

				ret=sarr;

			} break;
			case Variant::INT_ARRAY: {

				jintArray arr = (jintArray)env->CallObjectMethodA(instance,E->get().method,v);

				int fCount = env->GetArrayLength(arr);
				DVector<int> sarr;
				sarr.resize(fCount);

				DVector<int>::Write w = sarr.write();
				env->GetIntArrayRegion(arr,0,fCount,w.ptr());
				w = DVector<int>::Write();
				ret=sarr;
			} break;
			case Variant::REAL_ARRAY: {

				jfloatArray arr = (jfloatArray)env->CallObjectMethodA(instance,E->get().method,v);

				int fCount = env->GetArrayLength(arr);
				DVector<float> sarr;
				sarr.resize(fCount);

				DVector<float>::Write w = sarr.write();
				env->GetFloatArrayRegion(arr,0,fCount,w.ptr());
				w = DVector<float>::Write();
				ret=sarr;
			} break;
			default: {


				print_line("failure..");
				ERR_FAIL_V(Variant());
			} break;
		}

		print_line("success");

		return ret;
	}
Ejemplo n.º 9
0
void ThetaOperator::forwardEstimation(
		boost::ptr_vector<MeshContext>& contextStack ,
		                        FitobCalculator* calc ,
		                        int& stackIndex ,
		                        double& timeStamp ){

	FITOB_OUT_LEVEL3(verb(),"ThetaOperator::forwardEstimation stackIndex:" << stackIndex << "timeStamp"
			<< timeStamp << " contextStack.size():" << contextStack.size());

	MeshContext& actualContext = contextStack[stackIndex];

	if (thetaExpression_->isConstantExpression(actualContext) == false){
		FITOB_ERROR_EXIT(" ThetaOperator, theta expression is not constant ");
	}
    // evaluate the the expression (theta time) and store it
	thetaTime_ = thetaExpression_->eval(actualContext.minGlobCoord());

	// todo: these values now are not taken in consideration,
	// This might be a future feature, to split up one Theta operator in small theta operators
	// in case of too large macro time step
	// 19.09.2010 -> at todays knowledge this is not necessary, this would only make things worse
	maxThetaTime_ = 10.0; //calc->getXMLConfiguration().get()->getDoubleConfiguration("thetaconfigurations.solver.maxThetaStep.<xmlattr>.value" );
	nr_Theta_ = ceil(thetaTime_/maxThetaTime_);

	const boost::shared_ptr<ModelCollection>& factorModels = calc->getModelCollection();
	const boost::shared_ptr<ScriptModel>& scriptModel = calc->getScriptModel();
	const OperatorSequence& scriptBody = scriptModel->bodyOpSeq();
	const Domain& actDom = actualContext.getDom();
	int nrFactors = factorModels->nrFactors();

	Domain newDom(actDom);

	FITOB_OUT_LEVEL3(verb(),"ThetaOperator::forwardEstimation nrFactors:" << factorModels->nrFactors() << " thetaTime:" << thetaTime_ );
	for (int factorIndex = 0 ; factorIndex < nrFactors ; factorIndex++)
	{
		const FactorModelBase& model = factorModels->getModel(factorIndex);
		int globalIndex = model.getGlobalIndex();

		const DVector& startVal = calc->getStartDomain()->getGradedAxis(globalIndex);

		// get the points of the normal distribution
		DVector stdPoints;
		returnScaledNormalDistribution( actDom.getMaximalLevel() ,
				factorModels->stdFactor(factorIndex) , 1 ,  stdPoints );

		FITOB_OUT_LEVEL3(verb(),"ThetaOperator::forwardEstimation factorIndex:" << factorIndex << " P.size():" << stdPoints.size());
		// here we calculate the scaling
		if (startVal.size() > 1){
			for (unsigned int pointI = 0; pointI < stdPoints.size() ; pointI++ ){
				double endVal = 0.0;
				model.forwardEstimation(startVal[pointI] , timeStamp + thetaTime_ ,
						stdPoints[pointI] , actDom.getAverage() , endVal );
				if (verb()>3){
					std::cout << endVal << ",";
				}
				stdPoints[pointI] = endVal;
			}
			if (verb()>3) std::cout << std::endl;
		} else {
			for (unsigned int pointI = 0; pointI < stdPoints.size() ; pointI++ ){
				double endVal = 0.0;
				model.forwardEstimation(startVal[0] , timeStamp + thetaTime_ ,
						stdPoints[pointI] , actDom.getAverage() , endVal );
				if (verb()>3){
					std::cout << endVal << ",";
				}
				stdPoints[pointI] = endVal;
			}
			if (verb()>3) std::cout << std::endl;
		}

		//and call forwardEstimation_DiffusionEnlarement
		int stackIndex_tmp = 0;
		scriptBody.forwardEstimation_DiffusionEnlarement( contextStack ,
                calc ,stdPoints , globalIndex , stackIndex_tmp  , timeStamp );

		// sort stdPoints vector - not necessary (even in mean reversion case)
		// - this is not necessary since we estimate the values from 0 till T and not for dT
		std::sort( stdPoints.begin(),stdPoints.end() );

		// set the axis in the new domain
		newDom.setAxis(stdPoints,globalIndex);
	}

	// add new context, extend contextStack
	contextStack.push_back(new MeshContext(newDom,timeStamp));
	FITOB_OUT_LEVEL3(verb(),"ThetaOperator::forwardEstimation New Domain:" << newDom.toString() );
	timeStamp = timeStamp + thetaTime_;
	stackIndex = stackIndex + 1;

}
Ejemplo n.º 10
0
Variant::operator String() const {

	switch( type ) {
	
		case NIL: return ""; 
		case BOOL: return _data._bool ? "True" : "False";
		case INT: return String::num(_data._int);
		case REAL: return String::num(_data._real);
		case STRING: return *reinterpret_cast<const String*>(_data._mem);
		case VECTOR2: return operator Vector2();
		case RECT2: return operator Rect2();
		case MATRIX32: return operator Matrix32();
		case VECTOR3: return operator Vector3();
		case PLANE: return operator Plane();
		//case QUAT: 
		case _AABB: return operator AABB();
		case QUAT: return operator Quat();
		case MATRIX3: return operator Matrix3();
		case TRANSFORM: return operator Transform();
		case NODE_PATH: return operator NodePath();
		case INPUT_EVENT: return operator InputEvent();
		case COLOR: return String::num( operator Color().r)+","+String::num( operator Color().g)+","+String::num( operator Color().b)+","+String::num( operator Color().a) ;
		case DICTIONARY: {
			
			const Dictionary &d =*reinterpret_cast<const Dictionary*>(_data._mem);
			//const String *K=NULL;
			String str;
			List<Variant> keys;
			d.get_key_list(&keys);

			Vector<_VariantStrPair> pairs;

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

				_VariantStrPair sp;
				sp.key=String(E->get());
				sp.value=d[E->get()];
				pairs.push_back(sp);
			}

			pairs.sort();

			for(int i=0;i<pairs.size();i++) {
				if (i>0)
					str+=", ";
				str+="("+pairs[i].key+":"+pairs[i].value+")";
			}
			
			return str;
		} break;
		case VECTOR3_ARRAY: { 
		
			DVector<Vector3> vec = operator DVector<Vector3>();
			String str;
			for(int i=0;i<vec.size();i++) {
			
				if (i>0)
					str+=", ";
				str=str+Variant( vec[i] );
			}
			return str;
		} break;
		case STRING_ARRAY: {

			DVector<String> vec = operator DVector<String>();
			String str;
			for(int i=0;i<vec.size();i++) {

				if (i>0)
					str+=", ";
				str=str+vec[i];
			}
			return str;
		} break;
		case INT_ARRAY: {

			DVector<int> vec = operator DVector<int>();
			String str;
			for(int i=0;i<vec.size();i++) {

				if (i>0)
					str+=", ";
				str=str+itos(vec[i]);
			}
			return str;
		} break;
		case REAL_ARRAY: {

			DVector<real_t> vec = operator DVector<real_t>();
			String str;
			for(int i=0;i<vec.size();i++) {

				if (i>0)
					str+=", ";
				str=str+rtos(vec[i]);
			}
			return str;
		} break;
		case ARRAY: {

			Array arr = operator Array();
			String str;
			for (int i=0; i<arr.size(); i++) {
				if (i)
					str+=", ";
				str += String(arr[i]);
			};
			return str;

		} break;
		case OBJECT: {

			if (_get_obj().obj)
				return "["+_get_obj().obj->get_type()+":"+itos(_get_obj().obj->get_instance_ID())+"]";
			else
				return "[Object:null]";

		} break;
		default: {
			return "["+get_type_name(type)+"]";
		}		
	}
	
	return "";
}
Ejemplo n.º 11
0
bool TileMapEditor::forward_input_event(const InputEvent& p_event) {

	if (!node || !node->get_tileset().is_valid() || !node->is_visible())
		return false;

	Matrix32 xform = CanvasItemEditor::get_singleton()->get_canvas_transform() * node->get_global_transform();
	Matrix32 xform_inv = xform.affine_inverse();

	switch(p_event.type) {

		case InputEvent::MOUSE_BUTTON: {

			const InputEventMouseButton &mb=p_event.mouse_button;

			if (mb.button_index==BUTTON_LEFT) {

				if (mb.pressed) {

					if (Input::get_singleton()->is_key_pressed(KEY_SPACE))
						return false; //drag

					if (tool==TOOL_NONE) {

						if (mb.mod.shift) {

							if (mb.mod.control)
								tool=TOOL_RECTANGLE_PAINT;
							else
								tool=TOOL_LINE_PAINT;

							selection_active=false;
							rectangle_begin=over_tile;

							return true;
						}

						if (mb.mod.control) {

							tool=TOOL_PICKING;
							_pick_tile(over_tile);

							return true;
						}

						tool=TOOL_PAINTING;
					}

					if (tool==TOOL_PAINTING) {

						int id = get_selected_tile();

						if (id!=TileMap::INVALID_CELL) {

							tool=TOOL_PAINTING;

							paint_undo.clear();
							paint_undo[over_tile]=_get_op_from_cell(over_tile);

							_set_cell(over_tile, id, flip_h, flip_v, transpose);
						}
					} else if (tool==TOOL_PICKING) {

						_pick_tile(over_tile);
					} else if (tool==TOOL_SELECTING) {

						selection_active=true;
						rectangle_begin=over_tile;
					}

					return true;

				} else {

					if (tool!=TOOL_NONE) {

						if (tool==TOOL_PAINTING) {

							int id=get_selected_tile();

							if (id!=TileMap::INVALID_CELL && paint_undo.size()) {

								undo_redo->create_action(TTR("Paint TileMap"));
								for (Map<Point2i,CellOp>::Element *E=paint_undo.front();E;E=E->next()) {

									Point2 p=E->key();
									undo_redo->add_do_method(node,"set_cellv",p,id,flip_h,flip_v,transpose);
									undo_redo->add_undo_method(node,"set_cellv",p,E->get().idx,E->get().xf,E->get().yf,E->get().tr);
								}
								undo_redo->commit_action();

								paint_undo.clear();
							}
						} else if (tool==TOOL_LINE_PAINT) {

							int id=get_selected_tile();

							if (id!=TileMap::INVALID_CELL) {

								undo_redo->create_action("Line Draw");
								for (Map<Point2i,CellOp>::Element *E=paint_undo.front();E;E=E->next()) {

									_set_cell(E->key(), id, flip_h, flip_v, transpose, true);
								}
								undo_redo->commit_action();

								paint_undo.clear();

								canvas_item_editor->update();
							}
						} else if (tool==TOOL_RECTANGLE_PAINT) {

							int id=get_selected_tile();

							if (id!=TileMap::INVALID_CELL) {

								undo_redo->create_action("Rectangle Paint");
								for (int i=rectangle.pos.y;i<=rectangle.pos.y+rectangle.size.y;i++) {
									for (int j=rectangle.pos.x;j<=rectangle.pos.x+rectangle.size.x;j++) {

										_set_cell(Point2i(j, i), id, flip_h, flip_v, transpose, true);
									}
								}
								undo_redo->commit_action();

								canvas_item_editor->update();
							}
						} else if (tool==TOOL_DUPLICATING) {

							Point2 ofs = over_tile-rectangle.pos;

							undo_redo->create_action(TTR("Duplicate"));
							for (List<TileData>::Element *E=copydata.front();E;E=E->next()) {

								_set_cell(E->get().pos+ofs,E->get().cell,E->get().flip_h,E->get().flip_v,E->get().transpose,true);
							}
							undo_redo->commit_action();

							copydata.clear();

							canvas_item_editor->update();

						} else if (tool==TOOL_SELECTING) {

							canvas_item_editor->update();

						} else if (tool==TOOL_BUCKET) {

							DVector<Vector2> points = _bucket_fill(over_tile);

							if (points.size() == 0)
								return false;

							Dictionary op;
							op["id"] = get_selected_tile();
							op["flip_h"] = flip_h;
							op["flip_v"] = flip_v;
							op["transpose"] = transpose;

							undo_redo->create_action("Bucket Fill");

							undo_redo->add_do_method(this, "_fill_points", points, op);
							undo_redo->add_undo_method(this, "_erase_points", points);

							undo_redo->commit_action();
						}

						tool=TOOL_NONE;

						return true;
					}
				}
			} else if (mb.button_index==BUTTON_RIGHT) {

				if (mb.pressed) {

					if (tool==TOOL_SELECTING || selection_active) {

						tool=TOOL_NONE;
						selection_active=false;

						canvas_item_editor->update();

						return true;
					}

					if (tool==TOOL_DUPLICATING) {

						tool=TOOL_NONE;
						copydata.clear();

						canvas_item_editor->update();

						return true;
					}

					if (tool==TOOL_NONE) {

						paint_undo.clear();

						Point2 local = node->world_to_map(xform_inv.xform(Point2(mb.x, mb.y)));

						if (mb.mod.shift) {

							if (mb.mod.control)
								tool=TOOL_RECTANGLE_ERASE;
							else
								tool=TOOL_LINE_ERASE;

							selection_active=false;
							rectangle_begin=local;
						} else {

							tool=TOOL_ERASING;

							paint_undo[local]=_get_op_from_cell(local);
							_set_cell(local, TileMap::INVALID_CELL);
						}

						return true;
					}

				} else {
					if (tool==TOOL_ERASING || tool==TOOL_RECTANGLE_ERASE || tool==TOOL_LINE_ERASE) {

						if (paint_undo.size()) {
							undo_redo->create_action(TTR("Erase TileMap"));
							for (Map<Point2i,CellOp>::Element *E=paint_undo.front();E;E=E->next()) {

								Point2 p=E->key();
								undo_redo->add_do_method(node,"set_cellv",p,TileMap::INVALID_CELL,false,false,false);
								undo_redo->add_undo_method(node,"set_cellv",p,E->get().idx,E->get().xf,E->get().yf,E->get().tr);
							}

							undo_redo->commit_action();
							paint_undo.clear();
						}

						if (tool==TOOL_RECTANGLE_ERASE || tool==TOOL_LINE_ERASE) {
							canvas_item_editor->update();
						}

						tool=TOOL_NONE;

						return true;
					}
				}
			}
		} break;
		case InputEvent::MOUSE_MOTION: {

			const InputEventMouseMotion &mm=p_event.mouse_motion;

			Point2i new_over_tile = node->world_to_map(xform_inv.xform(Point2(mm.x,mm.y)));

			if (new_over_tile!=over_tile) {

				over_tile=new_over_tile;
				canvas_item_editor->update();
			}

			if (tool==TOOL_PAINTING) {

				int id = get_selected_tile();
				if (id!=TileMap::INVALID_CELL) {

					if (!paint_undo.has(over_tile)) {
						paint_undo[over_tile]=_get_op_from_cell(over_tile);
					}

					_set_cell(over_tile, id, flip_h, flip_v, transpose);

					return true;
				}
			}

			if (tool==TOOL_SELECTING) {

				_select(rectangle_begin, over_tile);

				return true;
			}

			if (tool==TOOL_LINE_PAINT || tool==TOOL_LINE_ERASE) {

				int id = get_selected_tile();
				bool erasing = (tool==TOOL_LINE_ERASE);

				if (erasing && paint_undo.size()) {

					for (Map<Point2i, CellOp>::Element *E=paint_undo.front();E;E=E->next()) {

						_set_cell(E->key(), E->get().idx, E->get().xf, E->get().yf, E->get().tr);
					}
				}

				paint_undo.clear();

				if (id!=TileMap::INVALID_CELL) {

					Vector<Point2i> points = line(rectangle_begin.x, over_tile.x, rectangle_begin.y, over_tile.y);

					for (int i=0;i<points.size();i++) {

						paint_undo[points[i]]=_get_op_from_cell(points[i]);

						if (erasing)
							_set_cell(points[i], TileMap::INVALID_CELL);
					}

					canvas_item_editor->update();
				}

				return true;
			}
			if (tool==TOOL_RECTANGLE_PAINT || tool==TOOL_RECTANGLE_ERASE) {

				_select(rectangle_begin, over_tile);

				if (tool==TOOL_RECTANGLE_ERASE) {

					if (paint_undo.size()) {

						for (Map<Point2i, CellOp>::Element *E=paint_undo.front();E;E=E->next()) {

							_set_cell(E->key(), E->get().idx, E->get().xf, E->get().yf, E->get().tr);
						}
					}

					paint_undo.clear();

					for (int i=rectangle.pos.y;i<=rectangle.pos.y+rectangle.size.y;i++) {
						for (int j=rectangle.pos.x;j<=rectangle.pos.x+rectangle.size.x;j++) {

							Point2i tile = Point2i(j, i);
							paint_undo[tile]=_get_op_from_cell(tile);

							_set_cell(tile, TileMap::INVALID_CELL);
						}
					}
				}

				return true;
			}
			if (tool==TOOL_ERASING) {

				if (!paint_undo.has(over_tile)) {
					paint_undo[over_tile]=_get_op_from_cell(over_tile);
				}

				_set_cell(over_tile, TileMap::INVALID_CELL);

				return true;
			}
			if (tool==TOOL_PICKING && Input::get_singleton()->is_mouse_button_pressed(BUTTON_LEFT)) {

				_pick_tile(over_tile);

				return true;
			}
		} break;
		case InputEvent::KEY: {

			const InputEventKey &k = p_event.key;

			if (!k.pressed)
				break;

			if (k.scancode==KEY_ESCAPE) {

				if (tool==TOOL_DUPLICATING)
					copydata.clear();
				else if (tool==TOOL_SELECTING || selection_active)
					selection_active=false;

				tool=TOOL_NONE;

				canvas_item_editor->update();

				return true;
			}

			if (tool!=TOOL_NONE || !mouse_over)
				return false;

			if (k.scancode==KEY_DELETE) {

				_menu_option(OPTION_ERASE_SELECTION);

				return true;
			}

			if (k.mod.command) {

				if (k.scancode==KEY_F) {

					search_box->select_all();
					search_box->grab_focus();

					return true;
				}
				if (k.scancode==KEY_B) {

					tool=TOOL_SELECTING;
					selection_active=false;

					canvas_item_editor->update();

					return true;
				}
				if (k.scancode==KEY_D) {

					_update_copydata();

					if (selection_active) {
						tool=TOOL_DUPLICATING;

						canvas_item_editor->update();

						return true;
					}
				}
			} else {

				if (k.scancode==KEY_A) {

					flip_h=!flip_h;
					mirror_x->set_pressed(flip_h);
					canvas_item_editor->update();
					return true;
				}
				if (k.scancode==KEY_S) {

					flip_v=!flip_v;
					mirror_y->set_pressed(flip_v);
					canvas_item_editor->update();
					return true;
				}
			}
		} break;
	}

	return false;
}
Error EditorTextureImportPlugin::import2(const String& p_path, const Ref<ResourceImportMetadata>& p_from,EditorExportPlatform::ImageCompression p_compr, bool p_external){



	ERR_FAIL_COND_V(p_from->get_source_count()==0,ERR_INVALID_PARAMETER);

	Ref<ResourceImportMetadata> from=p_from;

	Ref<ImageTexture> texture;
	Vector<Ref<AtlasTexture> > atlases;
	bool atlas = from->get_option("atlas");
	bool large = from->get_option("large");

	int flags=from->get_option("flags");
	int format=from->get_option("format");
	float quality=from->get_option("quality");

	uint32_t tex_flags=0;

	if (flags&EditorTextureImportPlugin::IMAGE_FLAG_REPEAT)
		tex_flags|=Texture::FLAG_REPEAT;
	if (flags&EditorTextureImportPlugin::IMAGE_FLAG_FILTER)
		tex_flags|=Texture::FLAG_FILTER;
	if (!(flags&EditorTextureImportPlugin::IMAGE_FLAG_NO_MIPMAPS))
		tex_flags|=Texture::FLAG_MIPMAPS;
	if (flags&EditorTextureImportPlugin::IMAGE_FLAG_CONVERT_TO_LINEAR)
		tex_flags|=Texture::FLAG_CONVERT_TO_LINEAR;
	if (flags&EditorTextureImportPlugin::IMAGE_FLAG_USE_ANISOTROPY)
		tex_flags|=Texture::FLAG_ANISOTROPIC_FILTER;

	print_line("path: "+p_path+" flags: "+itos(tex_flags));
	float shrink=1;
	if (from->has_option("shrink"))
		shrink=from->get_option("shrink");

	if (large) {
		ERR_FAIL_COND_V(from->get_source_count()!=1,ERR_INVALID_PARAMETER);

		String src_path = EditorImportPlugin::expand_source_path(from->get_source_path(0));


		int cell_size=from->get_option("large_cell_size");
		ERR_FAIL_COND_V(cell_size<128 || cell_size>16384,ERR_CANT_OPEN);

		EditorProgress pg("ltex","Import Large Texture",3);

		pg.step("Load Source Image",0);
		Image img;
		Error err = ImageLoader::load_image(src_path,&img);
		if (err) {
			return err;
		}

		pg.step("Slicing",1);

		Map<Vector2,Image> pieces;
		for(int i=0;i<img.get_width();i+=cell_size) {
			int w = MIN(img.get_width()-i,cell_size);
			for(int j=0;j<img.get_height();j+=cell_size) {
				int h = MIN(img.get_height()-j,cell_size);

				Image piece(w,h,0,img.get_format());
				piece.blit_rect(img,Rect2(i,j,w,h),Point2(0,0));
				if (!piece.is_invisible()) {
					pieces[Vector2(i,j)]=piece;
					//print_line("ADDING PIECE AT "+Vector2(i,j));
				}
			}
		}

		Ref<LargeTexture> existing;
		if (ResourceCache::has(p_path)) {
			existing = ResourceCache::get(p_path);
		}

		if (existing.is_valid()) {
			existing->clear();
		} else {
			existing = Ref<LargeTexture>(memnew( LargeTexture ));
		}

		existing->set_size(Size2(img.get_width(),img.get_height()));
		pg.step("Inserting",2);

		for (Map<Vector2,Image>::Element *E=pieces.front();E;E=E->next()) {

			Ref<ImageTexture> imgtex = Ref<ImageTexture>( memnew( ImageTexture ) );
			imgtex->create_from_image(E->get(),tex_flags);
			_process_texture_data(imgtex,format,quality,flags,p_compr,tex_flags,shrink);
			existing->add_piece(E->key(),imgtex);
		}

		if (!p_external) {
			from->set_editor(get_name());
			existing->set_path(p_path);
			existing->set_import_metadata(from);
		}
		pg.step("Saving",3);

		err = ResourceSaver::save(p_path,existing);
		if (err!=OK) {
			EditorNode::add_io_error("Couldn't save large texture: "+p_path);
			return err;
		}

		return OK;


	} else if (atlas) {

		//prepare atlas!
		Vector< Image > sources;
		Vector< Image > tsources;
		bool alpha=false;
		bool crop = from->get_option("crop");

		EditorProgress ep("make_atlas","Build Atlas For: "+p_path.get_file(),from->get_source_count()+3);

		print_line("sources: "+itos(from->get_source_count()));

		for(int i=0;i<from->get_source_count();i++) {

			String path = EditorImportPlugin::expand_source_path(from->get_source_path(i));
			String md5 = FileAccess::get_md5(path);
			from->set_source_md5(i,FileAccess::get_md5(path));
			ep.step("Loading Image: "+path,i);
			print_line("source path: "+path+" md5 "+md5);
			Image src;
			Error err = ImageLoader::load_image(path,&src);
			if (err) {
				EditorNode::add_io_error("Couldn't load image: "+path);
				return err;
			}

			if (src.detect_alpha())
				alpha=true;

			tsources.push_back(src);
		}
		ep.step("Converting Images",sources.size());

		int base_index=0;


		Map<uint64_t,int> source_md5;
		Map<int,List<int> > source_map;

		for(int i=0;i<tsources.size();i++) {

			Image src = tsources[i];

			if (alpha) {
				src.convert(Image::FORMAT_RGBA);
			} else {
				src.convert(Image::FORMAT_RGB);
			}

			DVector<uint8_t> data = src.get_data();
			MD5_CTX md5;
			DVector<uint8_t>::Read r=data.read();
			MD5Init(&md5);
			int len=data.size();
			for(int j=0;j<len;j++) {
				uint8_t b = r[j];
				b>>=2; //to aid in comparing
				MD5Update(&md5,(unsigned char*)&b,1);
			}
			MD5Final(&md5);
			uint64_t *cmp = (uint64_t*)md5.digest; //less bits, but still useful for this

			tsources[i]=Image(); //clear

			if (source_md5.has(*cmp)) {
				int sidx=source_md5[*cmp];
				source_map[sidx].push_back(i);
				print_line("REUSING "+from->get_source_path(i));

			} else {
				int sidx=sources.size();
				source_md5[*cmp]=sidx;
				sources.push_back(src);
				List<int> sm;
				sm.push_back(i);
				source_map[sidx]=sm;

			}


		}

		//texturepacker is not really good for optimizing, so..
		//will at some point likely replace with my own
		//first, will find the nearest to a square packing
		int border=1;

		Vector<Size2i> src_sizes;
		Vector<Rect2> crops;

		ep.step("Cropping Images",sources.size()+1);

		for(int j=0;j<sources.size();j++) {

			Size2i s;
			if (crop) {
				Rect2 crop = sources[j].get_used_rect();
				print_line("CROP: "+crop);
				s=crop.size;
				crops.push_back(crop);
			} else {

				s=Size2i(sources[j].get_width(),sources[j].get_height());
			}
			s+=Size2i(border*2,border*2);
			src_sizes.push_back(s); //add a line to constraint width
		}

		Vector<Point2i> dst_positions;
		Size2i dst_size;
		EditorAtlas::fit(src_sizes,dst_positions,dst_size);

		print_line("size that workeD: "+itos(dst_size.width)+","+itos(dst_size.height));

		ep.step("Blitting Images",sources.size()+2);

		bool blit_to_po2=tex_flags&Texture::FLAG_MIPMAPS;
		int atlas_w=dst_size.width;
		int atlas_h=dst_size.height;
		if (blit_to_po2) {
			atlas_w=nearest_power_of_2(dst_size.width);
			atlas_h=nearest_power_of_2(dst_size.height);
		}
		Image atlas;
		atlas.create(atlas_w,atlas_h,0,alpha?Image::FORMAT_RGBA:Image::FORMAT_RGB);


		atlases.resize(from->get_source_count());

		for(int i=0;i<sources.size();i++) {

			int x=dst_positions[i].x;
			int y=dst_positions[i].y;

			Size2 sz = Size2(sources[i].get_width(),sources[i].get_height());

			Rect2 region;
			Rect2 margin;

			if (crop && sz!=crops[i].size) {
				Rect2 rect = crops[i];
				rect.size=sz-rect.size;
				region=Rect2(x+border,y+border,crops[i].size.width,crops[i].size.height);
				margin=rect;
				atlas.blit_rect(sources[i],crops[i],Point2(x+border,y+border));
			} else {
				region=Rect2(x+border,y+border,sz.x,sz.y);
				atlas.blit_rect(sources[i],Rect2(0,0,sources[i].get_width(),sources[i].get_height()),Point2(x+border,y+border));
			}

			ERR_CONTINUE( !source_map.has(i) );
			for (List<int>::Element *E=source_map[i].front();E;E=E->next()) {

				String apath = p_path.get_base_dir().plus_file(from->get_source_path(E->get()).get_file().basename()+".atex");

				Ref<AtlasTexture> at;

				if (ResourceCache::has(apath)) {
					at = Ref<AtlasTexture>( ResourceCache::get(apath)->cast_to<AtlasTexture>() );
				} else {

					at = Ref<AtlasTexture>( memnew( AtlasTexture ) );
				}
				at->set_region(region);
				at->set_margin(margin);
				at->set_path(apath);
				atlases[E->get()]=at;
				print_line("Atlas Tex: "+apath);
			}
		}
		if (ResourceCache::has(p_path)) {
			texture = Ref<ImageTexture> ( ResourceCache::get(p_path)->cast_to<ImageTexture>() );
		} else {
			texture = Ref<ImageTexture>( memnew( ImageTexture ) );
		}
		texture->create_from_image(atlas,tex_flags);

	} else {
Ejemplo n.º 13
0
Geometry::MeshData Geometry::build_convex_mesh(const DVector<Plane> &p_planes) {

	MeshData mesh;

#define SUBPLANE_SIZE 1024.0

	float subplane_size = 1024.0; // should compute this from the actual plane
	for (int i = 0; i < p_planes.size(); i++) {

		Plane p = p_planes[i];

		Vector3 ref = Vector3(0.0, 1.0, 0.0);

		if (ABS(p.normal.dot(ref)) > 0.95)
			ref = Vector3(0.0, 0.0, 1.0); // change axis

		Vector3 right = p.normal.cross(ref).normalized();
		Vector3 up = p.normal.cross(right).normalized();

		Vector<Vector3> vertices;

		Vector3 center = p.get_any_point();
		// make a quad clockwise
		vertices.push_back(center - up * subplane_size + right * subplane_size);
		vertices.push_back(center - up * subplane_size - right * subplane_size);
		vertices.push_back(center + up * subplane_size - right * subplane_size);
		vertices.push_back(center + up * subplane_size + right * subplane_size);

		for (int j = 0; j < p_planes.size(); j++) {

			if (j == i)
				continue;

			Vector<Vector3> new_vertices;
			Plane clip = p_planes[j];

			if (clip.normal.dot(p.normal) > 0.95)
				continue;

			if (vertices.size() < 3)
				break;

			for (int k = 0; k < vertices.size(); k++) {

				int k_n = (k + 1) % vertices.size();

				Vector3 edge0_A = vertices[k];
				Vector3 edge1_A = vertices[k_n];

				real_t dist0 = clip.distance_to(edge0_A);
				real_t dist1 = clip.distance_to(edge1_A);

				if (dist0 <= 0) { // behind plane

					new_vertices.push_back(vertices[k]);
				}

				// check for different sides and non coplanar
				if ((dist0 * dist1) < 0) {

					// calculate intersection
					Vector3 rel = edge1_A - edge0_A;

					real_t den = clip.normal.dot(rel);
					if (Math::abs(den) < CMP_EPSILON)
						continue; // point too short

					real_t dist = -(clip.normal.dot(edge0_A) - clip.d) / den;
					Vector3 inters = edge0_A + rel * dist;
					new_vertices.push_back(inters);
				}
			}

			vertices = new_vertices;
		}

		if (vertices.size() < 3)
			continue;

		//result is a clockwise face

		MeshData::Face face;

		// add face indices
		for (int j = 0; j < vertices.size(); j++) {

			int idx = -1;
			for (int k = 0; k < mesh.vertices.size(); k++) {

				if (mesh.vertices[k].distance_to(vertices[j]) < 0.001) {

					idx = k;
					break;
				}
			}

			if (idx == -1) {

				idx = mesh.vertices.size();
				mesh.vertices.push_back(vertices[j]);
			}

			face.indices.push_back(idx);
		}
		face.plane = p;
		mesh.faces.push_back(face);

		//add edge

		for (int j = 0; j < face.indices.size(); j++) {

			int a = face.indices[j];
			int b = face.indices[(j + 1) % face.indices.size()];

			bool found = false;
			for (int k = 0; k < mesh.edges.size(); k++) {

				if (mesh.edges[k].a == a && mesh.edges[k].b == b) {
					found = true;
					break;
				}
				if (mesh.edges[k].b == a && mesh.edges[k].a == b) {
					found = true;
					break;
				}
			}

			if (found)
				continue;
			MeshData::Edge edge;
			edge.a = a;
			edge.b = b;
			mesh.edges.push_back(edge);
		}
	}

	return mesh;
}
Ejemplo n.º 14
0
DVector<Face3> Geometry::wrap_geometry(DVector<Face3> p_array, float *p_error) {

#define _MIN_SIZE 1.0
#define _MAX_LENGTH 20

	int face_count = p_array.size();
	DVector<Face3>::Read facesr = p_array.read();
	const Face3 *faces = facesr.ptr();

	AABB global_aabb;

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

		if (i == 0) {

			global_aabb = faces[i].get_aabb();
		} else {

			global_aabb.merge_with(faces[i].get_aabb());
		}
	}

	global_aabb.grow_by(0.01); // avoid numerical error

	// determine amount of cells in grid axis
	int div_x, div_y, div_z;

	if (global_aabb.size.x / _MIN_SIZE < _MAX_LENGTH)
		div_x = (int)(global_aabb.size.x / _MIN_SIZE) + 1;
	else
		div_x = _MAX_LENGTH;

	if (global_aabb.size.y / _MIN_SIZE < _MAX_LENGTH)
		div_y = (int)(global_aabb.size.y / _MIN_SIZE) + 1;
	else
		div_y = _MAX_LENGTH;

	if (global_aabb.size.z / _MIN_SIZE < _MAX_LENGTH)
		div_z = (int)(global_aabb.size.z / _MIN_SIZE) + 1;
	else
		div_z = _MAX_LENGTH;

	Vector3 voxelsize = global_aabb.size;
	voxelsize.x /= div_x;
	voxelsize.y /= div_y;
	voxelsize.z /= div_z;

	// create and initialize cells to zero
	//print_line("Wrapper: Initializing Cells");

	uint8_t ***cell_status = memnew_arr(uint8_t **, div_x);
	for (int i = 0; i < div_x; i++) {

		cell_status[i] = memnew_arr(uint8_t *, div_y);

		for (int j = 0; j < div_y; j++) {

			cell_status[i][j] = memnew_arr(uint8_t, div_z);

			for (int k = 0; k < div_z; k++) {

				cell_status[i][j][k] = 0;
			}
		}
	}

	// plot faces into cells
	//print_line("Wrapper (1/6): Plotting Faces");

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

		Face3 f = faces[i];
		for (int j = 0; j < 3; j++) {

			f.vertex[j] -= global_aabb.pos;
		}
		_plot_face(cell_status, 0, 0, 0, div_x, div_y, div_z, voxelsize, f);
	}

	// determine which cells connect to the outside by traversing the outside and recursively flood-fill marking

	//print_line("Wrapper (2/6): Flood Filling");

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

		for (int j = 0; j < div_y; j++) {

			_mark_outside(cell_status, i, j, 0, div_x, div_y, div_z);
			_mark_outside(cell_status, i, j, div_z - 1, div_x, div_y, div_z);
		}
	}

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

		for (int j = 0; j < div_y; j++) {

			_mark_outside(cell_status, 0, j, i, div_x, div_y, div_z);
			_mark_outside(cell_status, div_x - 1, j, i, div_x, div_y, div_z);
		}
	}

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

		for (int j = 0; j < div_z; j++) {

			_mark_outside(cell_status, i, 0, j, div_x, div_y, div_z);
			_mark_outside(cell_status, i, div_y - 1, j, div_x, div_y, div_z);
		}
	}

	// build faces for the inside-outside cell divisors

	//print_line("Wrapper (3/6): Building Faces");

	DVector<Face3> wrapped_faces;

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

		for (int j = 0; j < div_y; j++) {

			for (int k = 0; k < div_z; k++) {

				_build_faces(cell_status, i, j, k, div_x, div_y, div_z, wrapped_faces);
			}
		}
	}

	//print_line("Wrapper (4/6): Transforming Back Vertices");

	// transform face vertices to global coords

	int wrapped_faces_count = wrapped_faces.size();
	DVector<Face3>::Write wrapped_facesw = wrapped_faces.write();
	Face3 *wrapped_faces_ptr = wrapped_facesw.ptr();

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

		for (int j = 0; j < 3; j++) {

			Vector3 &v = wrapped_faces_ptr[i].vertex[j];
			v = v * voxelsize;
			v += global_aabb.pos;
		}
	}

	// clean up grid
	//print_line("Wrapper (5/6): Grid Cleanup");

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

		for (int j = 0; j < div_y; j++) {

			memdelete_arr(cell_status[i][j]);
		}

		memdelete_arr(cell_status[i]);
	}

	memdelete_arr(cell_status);
	if (p_error)
		*p_error = voxelsize.length();

	//print_line("Wrapper (6/6): Finished.");
	return wrapped_faces;
}
Ejemplo n.º 15
0
jvalue _variant_to_jvalue(JNIEnv *env, Variant::Type p_type, const Variant* p_arg, bool force_jobject = false) {

	jvalue v;

	switch(p_type) {

		case Variant::BOOL: {

			if (force_jobject) {
				jclass bclass = env->FindClass("java/lang/Boolean");
				jmethodID ctor = env->GetMethodID(bclass, "<init>", "(Z)V");
				jvalue val;
				val.z = (bool)(*p_arg);
				jobject obj = env->NewObjectA(bclass, ctor, &val);
				v.l = obj;
			} else {
				v.z=*p_arg;
			};
		} break;
		case Variant::INT: {

			if (force_jobject) {

				jclass bclass = env->FindClass("java/lang/Integer");
				jmethodID ctor = env->GetMethodID(bclass, "<init>", "(I)V");
				jvalue val;
				val.i = (int)(*p_arg);
				jobject obj = env->NewObjectA(bclass, ctor, &val);
				v.l = obj;

			} else {
				v.i=*p_arg;
			};
		} break;
		case Variant::REAL: {

			if (force_jobject) {

				jclass bclass = env->FindClass("java/lang/Double");
				jmethodID ctor = env->GetMethodID(bclass, "<init>", "(D)V");
				jvalue val;
				val.d = (double)(*p_arg);
				jobject obj = env->NewObjectA(bclass, ctor, &val);
				v.l = obj;

			} else {
				v.f=*p_arg;
			};
		} break;
		case Variant::STRING: {

			String s = *p_arg;
			jstring jStr = env->NewStringUTF(s.utf8().get_data());
			v.l=jStr;
		} break;
		case Variant::STRING_ARRAY: {

			DVector<String> sarray = *p_arg;
			jobjectArray arr = env->NewObjectArray(sarray.size(),env->FindClass("java/lang/String"),env->NewStringUTF(""));

			for(int j=0;j<sarray.size();j++) {

				env->SetObjectArrayElement(arr,j,env->NewStringUTF( sarray[j].utf8().get_data() ));
			}
			v.l=arr;

		} break;

		case Variant::DICTIONARY: {

			Dictionary dict = *p_arg;
			jclass dclass = env->FindClass("com/android/godot/Dictionary");
			jmethodID ctor = env->GetMethodID(dclass, "<init>", "()V");
			jobject jdict = env->NewObject(dclass, ctor);

			Array keys = dict.keys();

			jobjectArray jkeys = env->NewObjectArray(keys.size(), env->FindClass("java/lang/String"), env->NewStringUTF(""));
			for (int j=0; j<keys.size(); j++) {
				env->SetObjectArrayElement(jkeys, j, env->NewStringUTF(String(keys[j]).utf8().get_data()));
			};

			jmethodID set_keys = env->GetMethodID(dclass, "set_keys", "([Ljava/lang/String;)V");
			jvalue val;
			val.l = jkeys;
			env->CallVoidMethodA(jdict, set_keys, &val);

			jobjectArray jvalues = env->NewObjectArray(keys.size(), env->FindClass("java/lang/Object"), NULL);

			for (int j=0; j<keys.size(); j++) {
				Variant var = dict[keys[j]];
				val = _variant_to_jvalue(env, var.get_type(), &var, true);
				env->SetObjectArrayElement(jvalues, j, val.l);
			};

			jmethodID set_values = env->GetMethodID(dclass, "set_values", "([Ljava/lang/Object;)V");
			val.l = jvalues;
			env->CallVoidMethodA(jdict, set_values, &val);

			v.l = jdict;
		} break;

		case Variant::INT_ARRAY: {

			DVector<int> array = *p_arg;
			jintArray arr = env->NewIntArray(array.size());
			DVector<int>::Read r = array.read();
			env->SetIntArrayRegion(arr,0,array.size(),r.ptr());
			v.l=arr;

		} break;
		case Variant::RAW_ARRAY: {
			DVector<uint8_t> array = *p_arg;
			jbyteArray arr = env->NewByteArray(array.size());
			DVector<uint8_t>::Read r = array.read();
			env->SetByteArrayRegion(arr,0,array.size(),reinterpret_cast<const signed char*>(r.ptr()));
			v.l=arr;

		} break;
		case Variant::REAL_ARRAY: {

			DVector<float> array = *p_arg;
			jfloatArray arr = env->NewFloatArray(array.size());
			DVector<float>::Read r = array.read();
			env->SetFloatArrayRegion(arr,0,array.size(),r.ptr());
			v.l=arr;

		} break;
		default: {

			v.i = 0;
		} break;

	}
	return v;
};
Ejemplo n.º 16
0
void ConcavePolygonShapeSW::_setup(DVector<Vector3> p_faces) {

	int src_face_count=p_faces.size();
	ERR_FAIL_COND(src_face_count%3);
	src_face_count/=3;

	DVector<Vector3>::Read r = p_faces.read();
	const Vector3 * facesr= r.ptr();

#if 0
	Map<Vector3,int> point_map;
	List<Face> face_list;


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

		Face3 faceaux;

		for(int j=0;j<3;j++) {

			faceaux.vertex[j]=facesr[i*3+j].snapped(_POINT_SNAP);
			//faceaux.vertex[j]=facesr[i*3+j];//facesr[i*3+j].snapped(_POINT_SNAP);
		}

		ERR_CONTINUE( faceaux.is_degenerate() );

		Face face;

		for(int j=0;j<3;j++) {


			Map<Vector3,int>::Element *E=point_map.find(faceaux.vertex[j]);
			if (E) {

				face.indices[j]=E->value();
			} else {

				face.indices[j]=point_map.size();
				point_map.insert(faceaux.vertex[j],point_map.size());

			}
		}

		face_list.push_back(face);
	}

	vertices.resize( point_map.size() );

	DVector<Vector3>::Write vw = vertices.write();
	Vector3 *verticesw=vw.ptr();

	AABB _aabb;

	for( Map<Vector3,int>::Element *E=point_map.front();E;E=E->next()) {

		if (E==point_map.front()) {
			_aabb.pos=E->key();
		} else {

			_aabb.expand_to(E->key());
		}
		verticesw[E->value()]=E->key();
	}

	point_map.clear(); // not needed anymore

	faces.resize(face_list.size());
	DVector<Face>::Write w = faces.write();
	Face *facesw=w.ptr();

	int fc=0;

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

		facesw[fc++]=E->get();
	}

	face_list.clear();


	DVector<_VolumeSW_BVH_Element> bvh_array;
	bvh_array.resize( fc );

	DVector<_VolumeSW_BVH_Element>::Write bvhw = bvh_array.write();
	_VolumeSW_BVH_Element *bvh_arrayw=bvhw.ptr();


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

		AABB face_aabb;
		face_aabb.pos=verticesw[facesw[i].indices[0]];
		face_aabb.expand_to( verticesw[facesw[i].indices[1]] );
		face_aabb.expand_to( verticesw[facesw[i].indices[2]] );

		bvh_arrayw[i].face_index=i;
		bvh_arrayw[i].aabb=face_aabb;
		bvh_arrayw[i].center=face_aabb.pos+face_aabb.size*0.5;

	}

	w=DVector<Face>::Write();
	vw=DVector<Vector3>::Write();


	int count=0;
	_VolumeSW_BVH *bvh_tree=_volume_sw_build_bvh(bvh_arrayw,fc,count);

	ERR_FAIL_COND(count==0);

	bvhw=DVector<_VolumeSW_BVH_Element>::Write();

	bvh.resize( count+1 );

	DVector<BVH>::Write bvhw2 = bvh.write();
	BVH*bvh_arrayw2=bvhw2.ptr();

	int idx=0;
	_fill_bvh(bvh_tree,bvh_arrayw2,idx);

	set_aabb(_aabb);

#else
	DVector<_VolumeSW_BVH_Element> bvh_array;
	bvh_array.resize( src_face_count );

	DVector<_VolumeSW_BVH_Element>::Write bvhw = bvh_array.write();
	_VolumeSW_BVH_Element *bvh_arrayw=bvhw.ptr();

	faces.resize(src_face_count);
	DVector<Face>::Write w = faces.write();
	Face *facesw=w.ptr();

	vertices.resize( src_face_count*3 );

	DVector<Vector3>::Write vw = vertices.write();
	Vector3 *verticesw=vw.ptr();

	AABB _aabb;


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

		Face3 face( facesr[i*3+0], facesr[i*3+1], facesr[i*3+2] );

		bvh_arrayw[i].aabb=face.get_aabb();
		bvh_arrayw[i].center = bvh_arrayw[i].aabb.pos + bvh_arrayw[i].aabb.size * 0.5;
		bvh_arrayw[i].face_index=i;
		facesw[i].indices[0]=i*3+0;
		facesw[i].indices[1]=i*3+1;
		facesw[i].indices[2]=i*3+2;
		facesw[i].normal=face.get_plane().normal;
		verticesw[i*3+0]=face.vertex[0];
		verticesw[i*3+1]=face.vertex[1];
		verticesw[i*3+2]=face.vertex[2];
		if (i==0)
			_aabb=bvh_arrayw[i].aabb;
		else
			_aabb.merge_with(bvh_arrayw[i].aabb);

	}

	w=DVector<Face>::Write();
	vw=DVector<Vector3>::Write();

	int count=0;
	_VolumeSW_BVH *bvh_tree=_volume_sw_build_bvh(bvh_arrayw,src_face_count,count);

	bvh.resize( count+1 );

	DVector<BVH>::Write bvhw2 = bvh.write();
	BVH*bvh_arrayw2=bvhw2.ptr();

	int idx=0;
	_fill_bvh(bvh_tree,bvh_arrayw2,idx);

	configure(_aabb); // this type of shape has no margin


#endif
}
Ejemplo n.º 17
0
 DVector(const DVector& other) : Base(other.size()) {
     elements_ = other.elements_;
 }
Ejemplo n.º 18
0
bool D_bjmak::sendBuffer(QVector<FileID>& ids, qint64 bufferSize){
    //QString idsBuffer;
    //QString hashBuffer;
    //QString dataBuffer;
    
    std::cout << "sending buffer of " << ids.size() << std::endl;
    
    server->connectionPtr->sendMsg("NEXT");
    const int hashBufferSize = bufferSize / bsize_;
    DVector hashBuffer;
    hashBuffer.reserve(hashBufferSize);

    DVector dataBuffer;
    hashBuffer.reserve(bufferSize);

    DVector idsBuffer;
    hashBuffer.reserve(3000000);
    
    int blockCount;
    int fd;
    bool isCleared = true;
    for(int i = 0; i < ids.size(); ++i){

        if (!ids[i].isREG()){
            idsBuffer.push_back(ids[i].toString());
            //cout << "added not reg " << ids[i].getFullPath().toStdString() << endl;
            continue;
        }
        
        DVector tmpHashBuffer;
        DVector tmpDataBuffer;
        
        if ( (dataBuffer.size()+ids[i].getSize()) > bufferSize ){
            blockCount = (bufferSize-dataBuffer.size()) / bsize_;
            isCleared = false;
        }
        else{
            blockCount = ids[i].getSize() / bsize_;
            
            if ( (ids[i].getSize() % bsize_) != 0 )
                ++blockCount;
            
        }
        
        fd = open(ids[i].getFullPath().toStdString().c_str(), O_RDONLY);
        
        if (fd == -1){
            cout << "error " << strerror(errno) << endl;
            writeLog.warning() << "Error open file <" << ids[i].getFullPath() 
                    << "> " << strerror(errno) 
                    << DebusLogger::endl;
            continue;
        }
        
        if (!getHashesAndData(fd, tmpDataBuffer, tmpHashBuffer, blockCount)){
            cout << "error " << strerror(errno) << endl;
            writeLog.warning() << "Error read file <" << ids[i].getFullPath() 
                    << "> " << strerror(errno) 
                    << DebusLogger::endl;
            continue;
        }

        
        
        
        idsBuffer.push_back(ids[i].toString());
        //cout << "added reg " << ids[i].getFullPath().toStdString() << endl;
        //idsBuffer.push_back(ids[i].toQString());
        hashBuffer.push_back(tmpHashBuffer);
        dataBuffer.push_back(tmpDataBuffer);
        
        if (isCleared)
            close(fd);
    }

    cout << "Sending idsbuffer " << idsBuffer.size() << endl;
    server->connectionPtr->sendMsg(idsBuffer.data(), idsBuffer.size());
    cout << "Sending hashBuffer " << hashBuffer.size() << endl;
    server->connectionPtr->sendMsg(hashBuffer.data(), hashBuffer.size());
    server->connectionPtr->recvMsg();
    DVector reply;
    reply.push_back(server->connectionPtr->dataToVector());
    cout << "Received reply size " << reply.size() << endl;
    DVector newDataBuffer;
    newDataBuffer = this->getDataBufferFromReply(reply, hashBuffer, dataBuffer);
    cout << "sending data size " << newDataBuffer.size() << endl;
    server->connectionPtr->sendMsg(newDataBuffer.data(), newDataBuffer.size());

    if (!isCleared){
        int clearedBlockCount = blockCount;
        blockCount = ids.last().getSize() / bsize_;
        if ( (ids.last().getSize() % bsize_) != 0 )
            ++blockCount;

        blockCount -= clearedBlockCount;
        
        while(blockCount){
            int i;
            if (blockCount*bsize_ > bufferSize)
                i = bufferSize/bsize_;
            else
                i = blockCount;

            cout <<  "bufferSize " << bufferSize << " "
                    << " i " << i << endl;
            
            dataBuffer.clear();
            hashBuffer.clear();
            getHashesAndData(fd, dataBuffer, hashBuffer, i);
            cout <<  "dataBuffer" << dataBuffer.size() << " "
                    << "hashBuffer" << hashBuffer.size() << endl;
            server->connectionPtr->sendMsg(hashBuffer.data(), hashBuffer.size());
            cout <<  "clearedBlockCount" << clearedBlockCount << " "
                    << "blockCount" << blockCount << endl;
            server->connectionPtr->recvMsg();
            cout <<  "clearedBlockCount" << clearedBlockCount << " "
                    << "blockCount" << blockCount << endl;
            DVector reply;
            reply.push_back(server->connectionPtr->dataToString());
            DVector newDataBuffer;
            newDataBuffer = this->getDataBufferFromReply(reply, hashBuffer, dataBuffer);
            server->connectionPtr->sendMsg(newDataBuffer.data(), newDataBuffer.size());
            
            blockCount -= i;
        }
        close(fd);
    }
        

    cout << "sended block" << endl;
    return true;
}
void Polygon2DEditor::_uv_draw() {

	Ref<Texture> base_tex = node->get_texture();
	if (base_tex.is_null())
		return;

	Matrix32 mtx;
	mtx.elements[2]=-uv_draw_ofs;
	mtx.scale_basis(Vector2(uv_draw_zoom,uv_draw_zoom));

	VS::get_singleton()->canvas_item_set_clip(uv_edit_draw->get_canvas_item(),true);
	VS::get_singleton()->canvas_item_add_set_transform(uv_edit_draw->get_canvas_item(),mtx);
	uv_edit_draw->draw_texture(base_tex,Point2());
	VS::get_singleton()->canvas_item_add_set_transform(uv_edit_draw->get_canvas_item(),Matrix32());

	if (snap_show_grid) {
		Size2 s = uv_edit_draw->get_size();
		int last_cell;

		if (snap_step.x!=0) {
			for(int i=0;i<s.width;i++) {
				int cell = Math::fast_ftoi(Math::floor((mtx.affine_inverse().xform(Vector2(i,0)).x-snap_offset.x)/snap_step.x));
				if (i==0)
					last_cell=cell;
				if (last_cell!=cell)
					uv_edit_draw->draw_line(Point2(i,0),Point2(i,s.height),Color(0.3,0.7,1,0.3));
				last_cell=cell;
			}
		}

		if (snap_step.y!=0) {
			for(int i=0;i<s.height;i++) {
				int cell = Math::fast_ftoi(Math::floor((mtx.affine_inverse().xform(Vector2(0,i)).y-snap_offset.y)/snap_step.y));
				if (i==0)
					last_cell=cell;
				if (last_cell!=cell)
					uv_edit_draw->draw_line(Point2(0,i),Point2(s.width,i),Color(0.3,0.7,1,0.3));
				last_cell=cell;
			}
		}
	}

	DVector<Vector2> uvs = node->get_uv();
	Ref<Texture> handle = get_icon("EditorHandle","EditorIcons");

	Rect2 rect(Point2(),mtx.basis_xform(base_tex->get_size()));
	rect.expand_to(mtx.basis_xform(uv_edit_draw->get_size()));

	for(int i=0;i<uvs.size();i++) {

		int next = (i+1)%uvs.size();
		uv_edit_draw->draw_line(mtx.xform(uvs[i]),mtx.xform(uvs[next]),Color(0.9,0.5,0.5),2);
		uv_edit_draw->draw_texture(handle,mtx.xform(uvs[i])-handle->get_size()*0.5);
		rect.expand_to(mtx.basis_xform(uvs[i]));
	}

	rect=rect.grow(200);
	updating_uv_scroll=true;
	uv_hscroll->set_min(rect.pos.x);
	uv_hscroll->set_max(rect.pos.x+rect.size.x);
	uv_hscroll->set_page(uv_edit_draw->get_size().x);
	uv_hscroll->set_val(uv_draw_ofs.x);
	uv_hscroll->set_step(0.001);

	uv_vscroll->set_min(rect.pos.y);
	uv_vscroll->set_max(rect.pos.y+rect.size.y);
	uv_vscroll->set_page(uv_edit_draw->get_size().y);
	uv_vscroll->set_val(uv_draw_ofs.y);
	uv_vscroll->set_step(0.001);
	updating_uv_scroll=false;

}
Ejemplo n.º 20
0
void SceneState::set_bundled_scene(const Dictionary& d) {


	ERR_FAIL_COND( !d.has("names"));
	ERR_FAIL_COND( !d.has("variants"));
	ERR_FAIL_COND( !d.has("node_count"));
	ERR_FAIL_COND( !d.has("nodes"));
	ERR_FAIL_COND( !d.has("conn_count"));
	ERR_FAIL_COND( !d.has("conns"));
//	ERR_FAIL_COND( !d.has("path"));

	int version=1;
	if (d.has("version"))
		version=d["version"];

	if (version>PACK_VERSION) {
		ERR_EXPLAIN("Save format version too new!");
		ERR_FAIL();
	}

	DVector<String> snames = d["names"];
	if (snames.size()) {

		int namecount = snames.size();
		names.resize(namecount);
		DVector<String>::Read r =snames.read();
		for(int i=0;i<names.size();i++)
			names[i]=r[i];
	}

	Array svariants = d["variants"];

	if (svariants.size()) {
		int varcount=svariants.size();
		variants.resize(varcount);
		for(int i=0;i<varcount;i++) {

			variants[i]=svariants[i];
		}

	} else {
		variants.clear();
	}

	nodes.resize(d["node_count"]);
	int nc=nodes.size();
	if (nc) {
		DVector<int> snodes = d["nodes"];
		DVector<int>::Read r = snodes.read();
		int idx=0;
		for(int i=0;i<nc;i++) {
			NodeData &nd = nodes[i];
			nd.parent=r[idx++];
			nd.owner=r[idx++];
			nd.type=r[idx++];
			nd.name=r[idx++];
			nd.instance=r[idx++];
			nd.properties.resize(r[idx++]);
			for(int j=0;j<nd.properties.size();j++) {

				nd.properties[j].name=r[idx++];
				nd.properties[j].value=r[idx++];
			}
			nd.groups.resize(r[idx++]);
			for(int j=0;j<nd.groups.size();j++) {

				nd.groups[j]=r[idx++];
			}
		}

	}

	connections.resize(d["conn_count"]);
	int cc=connections.size();

	if (cc) {

		DVector<int> sconns = d["conns"];
		DVector<int>::Read r = sconns.read();
		int idx=0;
		for(int i=0;i<cc;i++) {
			ConnectionData &cd = connections[i];
			cd.from=r[idx++];
			cd.to=r[idx++];
			cd.signal=r[idx++];
			cd.method=r[idx++];
			cd.flags=r[idx++];
			cd.binds.resize(r[idx++]);

			for(int j=0;j<cd.binds.size();j++) {

				cd.binds[j]=r[idx++];
			}
		}

	}

	Array np;
	if (d.has("node_paths")) {
		np=d["node_paths"];
	}
	node_paths.resize(np.size());
	for(int i=0;i<np.size();i++) {
		node_paths[i]=np[i];
	}

	Array ei;
	if (d.has("editable_instances")) {
		ei=d["editable_instances"];
	}

	if (d.has("base_scene")) {
		base_scene_idx=d["base_scene"];
	}

	editable_instances.resize(ei.size());
	for(int i=0;i<editable_instances.size();i++) {
		editable_instances[i]=ei[i];
	}

//	path=d["path"];

}
Ejemplo n.º 21
0
static String _encode_variant(const Variant& p_variant) {

	switch(p_variant.get_type()) {

		case Variant::BOOL: {
			bool val = p_variant;
			return (val?"true":"false");
		} break;
		case Variant::INT: {
			int val = p_variant;
			return itos(val);
		} break;
		case Variant::REAL: {
			float val = p_variant;
			return rtos(val)+(val==int(val)?".0":"");
		} break;
		case Variant::STRING: {
			String val = p_variant;
			return "\""+val.xml_escape()+"\"";
		} break;
		case Variant::COLOR: {

			Color val = p_variant;
			return "#"+val.to_html();
		} break;
		case Variant::STRING_ARRAY:
		case Variant::INT_ARRAY:
		case Variant::REAL_ARRAY:
		case Variant::ARRAY: {
			Array arr = p_variant;
			String str="[";
			for(int i=0;i<arr.size();i++) {

				if (i>0)
					str+=", ";
				str+=_encode_variant(arr[i]);
			}
			str+="]";
			return str;
		} break;
		case Variant::DICTIONARY: {
			Dictionary d = p_variant;
			String str="{";
			List<Variant> keys;
			d.get_key_list(&keys);
			for(List<Variant>::Element *E=keys.front();E;E=E->next()) {

				if (E!=keys.front())
					str+=", ";
				str+=_encode_variant(E->get());
				str+=":";
				str+=_encode_variant(d[E->get()]);

			}
			str+="}";
			return str;
		} break;
		case Variant::IMAGE: {
			String str="img(";

			Image img=p_variant;
			if (!img.empty()) {

				String format;
				switch(img.get_format()) {

					case Image::FORMAT_GRAYSCALE: format="grayscale"; break;
					case Image::FORMAT_INTENSITY: format="intensity"; break;
					case Image::FORMAT_GRAYSCALE_ALPHA: format="grayscale_alpha"; break;
					case Image::FORMAT_RGB: format="rgb"; break;
					case Image::FORMAT_RGBA: format="rgba"; break;
					case Image::FORMAT_INDEXED : format="indexed"; break;
					case Image::FORMAT_INDEXED_ALPHA: format="indexed_alpha"; break;
					case Image::FORMAT_BC1: format="bc1"; break;
					case Image::FORMAT_BC2: format="bc2"; break;
					case Image::FORMAT_BC3: format="bc3"; break;
					case Image::FORMAT_BC4: format="bc4"; break;
					case Image::FORMAT_BC5: format="bc5"; break;
					case Image::FORMAT_CUSTOM: format="custom custom_size="+itos(img.get_data().size())+""; break;
					default: {}
				}

				str+=format+", ";
				str+=itos(img.get_mipmaps())+", ";
				str+=itos(img.get_width())+", ";
				str+=itos(img.get_height())+", ";
				DVector<uint8_t> data = img.get_data();
				int ds=data.size();
				DVector<uint8_t>::Read r = data.read();
				for(int i=0;i<ds;i++) {
					uint8_t byte = r[i];
					const char  hex[16]={'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
					char bstr[3]={ hex[byte>>4], hex[byte&0xF], 0};
					str+=bstr;
				}
			}
			str+=")";
			return str;
		} break;
		case Variant::INPUT_EVENT: {

			InputEvent ev = p_variant;

			switch(ev.type) {

				case InputEvent::KEY: {

					String mods;
					if (ev.key.mod.control)
						mods+="C";
					if (ev.key.mod.shift)
						mods+="S";
					if (ev.key.mod.alt)
						mods+="A";
					if (ev.key.mod.meta)
						mods+="M";
					if (mods!="")
						mods=", "+mods;

					return "key("+keycode_get_string(ev.key.scancode)+mods+")";
				} break;
				case InputEvent::MOUSE_BUTTON: {

					return "mbutton("+itos(ev.device)+", "+itos(ev.mouse_button.button_index)+")";
				} break;
				case InputEvent::JOYSTICK_BUTTON: {

					return "jbutton("+itos(ev.device)+", "+itos(ev.joy_button.button_index)+")";
				} break;
				case InputEvent::JOYSTICK_MOTION: {

					return "jaxis("+itos(ev.device)+", "+itos(ev.joy_motion.axis)+")";
				} break;
				default: {

					return "nil";
				} break;

			}
		} break;
		default: {}
	}
Ejemplo n.º 22
0
Error MeshDataTool::commit_to_surface(const Ref<Mesh>& p_mesh) {

	ERR_FAIL_COND_V(p_mesh.is_null(),ERR_INVALID_PARAMETER);
	Array arr;
	arr.resize(Mesh::ARRAY_MAX);


	int vcount=vertices.size();

	DVector<Vector3> v;
	DVector<Vector3> n;
	DVector<real_t> t;
	DVector<Vector2> u;
	DVector<Vector2> u2;
	DVector<Color> c;
	DVector<real_t> b;
	DVector<real_t> w;
	DVector<int> in;

	{

		v.resize(vcount);
		DVector<Vector3>::Write vr=v.write();

		DVector<Vector3>::Write nr;
		if (format&Mesh::ARRAY_FORMAT_NORMAL) {
			n.resize(vcount);
			nr = n.write();
		}

		DVector<real_t>::Write ta;
		if (format&Mesh::ARRAY_FORMAT_TANGENT) {
			t.resize(vcount*4);
			ta = t.write();
		}


		DVector<Vector2>::Write uv;
		if (format&Mesh::ARRAY_FORMAT_TEX_UV) {
			u.resize(vcount);
			uv = u.write();
		}

		DVector<Vector2>::Write uv2;
		if (format&Mesh::ARRAY_FORMAT_TEX_UV2) {
			u2.resize(vcount);
			uv2 = u2.write();
		}

		DVector<Color>::Write col;
		if (format&Mesh::ARRAY_FORMAT_COLOR) {
			c.resize(vcount);
			col = c.write();
		}

		DVector<real_t>::Write bo;
		if (format&Mesh::ARRAY_FORMAT_BONES) {
			b.resize(vcount*4);
			bo = b.write();
		}

		DVector<real_t>::Write we;
		if (format&Mesh::ARRAY_FORMAT_WEIGHTS) {
			w.resize(vcount*4);
			we = w.write();
		}


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

			Vertex &vtx=vertices[i];

			vr[i]=vtx.vertex;
			if (nr.ptr())
				nr[i]=vtx.normal;
			if (ta.ptr()) {
				ta[i*4+0]=vtx.tangent.normal.x;
				ta[i*4+1]=vtx.tangent.normal.y;
				ta[i*4+2]=vtx.tangent.normal.z;
				ta[i*4+3]=vtx.tangent.d;
			}
			if (uv.ptr())
				uv[i]=vtx.uv;
			if (uv2.ptr())
				uv2[i]=vtx.uv2;
			if (col.ptr())
				col[i]=vtx.color;

			if (we.ptr()) {

				we[i*4+0]=vtx.weights[0];
				we[i*4+1]=vtx.weights[1];
				we[i*4+2]=vtx.weights[2];
				we[i*4+3]=vtx.weights[3];

			}

			if (bo.ptr()) {

				bo[i*4+0]=vtx.bones[0];
				bo[i*4+1]=vtx.bones[1];
				bo[i*4+2]=vtx.bones[2];
				bo[i*4+3]=vtx.bones[3];
			}

		}

		int fc = faces.size();
		in.resize(fc*3);
		DVector<int>::Write iw=in.write();
		for(int i=0;i<fc;i++) {

			iw[i*3+0]=faces[i].v[0];
			iw[i*3+1]=faces[i].v[1];
			iw[i*3+2]=faces[i].v[2];
		}

	}

	arr[Mesh::ARRAY_VERTEX]=v;
	arr[Mesh::ARRAY_INDEX]=in;
	if (n.size())
		arr[Mesh::ARRAY_NORMAL]=n;
	if (c.size())
		arr[Mesh::ARRAY_COLOR]=c;
	if (u.size())
		arr[Mesh::ARRAY_TEX_UV]=u;
	if (u2.size())
		arr[Mesh::ARRAY_TEX_UV2]=u2;
	if (t.size())
		arr[Mesh::ARRAY_TANGENT]=t;
	if (b.size())
		arr[Mesh::ARRAY_BONES]=b;
	if (w.size())
		arr[Mesh::ARRAY_WEIGHTS]=w;

	Ref<Mesh> ncmesh=p_mesh;
	int sc = ncmesh->get_surface_count();
	ncmesh->add_surface(Mesh::PRIMITIVE_TRIANGLES,arr);
	ncmesh->surface_set_material(sc,material);

	return OK;
}
Ejemplo n.º 23
0
static void _decompress_etc(Image *p_img) {

	ERR_FAIL_COND(p_img->get_format()!=Image::FORMAT_ETC);

	int imgw = p_img->get_width();
	int imgh = p_img->get_height();
	DVector<uint8_t> src=p_img->get_data();
	DVector<uint8_t> dst;

	DVector<uint8_t>::Read r = src.read();

	int mmc=p_img->get_mipmap_count();


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

		dst.resize(dst.size()+imgw*imgh*3);
		const uint8_t *srcbr=&r[p_img->get_mipmap_offset(i)];
		DVector<uint8_t>::Write w = dst.write();

		uint8_t *wptr = &w[dst.size()-imgw*imgh*3];

		int bw=MAX(imgw/4,1);
		int bh=MAX(imgh/4,1);

		for(int y=0;y<bh;y++) {

			for(int x=0;x<bw;x++) {

				uint8_t block[4*4*4];


				rg_etc1::unpack_etc1_block(srcbr,(unsigned int*)block);
				srcbr+=8;

				int maxx=MIN(imgw,4);
				int maxy=MIN(imgh,4);

				for(int yy=0;yy<maxy;yy++) {

					for(int xx=0;xx<maxx;xx++) {

						uint32_t src_ofs = (yy*4+xx)*4;
						uint32_t dst_ofs = ((y*4+yy)*imgw+x*4+xx)*3;
						wptr[dst_ofs+0]=block[src_ofs+0];
						wptr[dst_ofs+1]=block[src_ofs+1];
						wptr[dst_ofs+2]=block[src_ofs+2];

					}
				}

			}

		}

		imgw=MAX(1,imgw/2);
		imgh=MAX(1,imgh/2);
	}


	r=DVector<uint8_t>::Read();
	//print_line("Re Creating ETC into regular image: w "+itos(p_img->get_width())+" h "+itos(p_img->get_height())+" mm "+itos(p_img->get_mipmaps()));
	*p_img=Image(p_img->get_width(),p_img->get_height(),p_img->has_mipmaps(),Image::FORMAT_RGB8,dst);
	if (p_img->has_mipmaps())
		p_img->generate_mipmaps(true);


}
Ejemplo n.º 24
0
Error MeshDataTool::create_from_surface(const Ref<Mesh>& p_mesh,int p_surface) {

	ERR_FAIL_COND_V(p_mesh.is_null(),ERR_INVALID_PARAMETER);

	ERR_FAIL_COND_V(p_mesh.is_null(),ERR_INVALID_PARAMETER);
	ERR_FAIL_COND_V(p_mesh->surface_get_primitive_type(p_surface)!=Mesh::PRIMITIVE_TRIANGLES,ERR_INVALID_PARAMETER);



	Array arrays = p_mesh->surface_get_arrays(p_surface);
	ERR_FAIL_COND_V( arrays.empty(), ERR_INVALID_PARAMETER );

	DVector<Vector3> varray = arrays[Mesh::ARRAY_VERTEX];

	int vcount = varray.size();
	ERR_FAIL_COND_V( vcount == 0, ERR_INVALID_PARAMETER);

	clear();
	format = p_mesh->surface_get_format(p_surface);
	material=p_mesh->surface_get_material(p_surface);

	DVector<Vector3>::Read vr = varray.read();

	DVector<Vector3>::Read nr;
	if (arrays[Mesh::ARRAY_NORMAL].get_type()!=Variant::NIL)
		nr = arrays[Mesh::ARRAY_NORMAL].operator DVector<Vector3>().read();

	DVector<real_t>::Read ta;
	if (arrays[Mesh::ARRAY_TANGENT].get_type()!=Variant::NIL)
		ta = arrays[Mesh::ARRAY_TANGENT].operator DVector<real_t>().read();

	DVector<Vector2>::Read uv;
	if (arrays[Mesh::ARRAY_TEX_UV].get_type()!=Variant::NIL)
		uv = arrays[Mesh::ARRAY_TEX_UV].operator DVector<Vector2>().read();
	DVector<Vector2>::Read uv2;
	if (arrays[Mesh::ARRAY_TEX_UV2].get_type()!=Variant::NIL)
		uv2 = arrays[Mesh::ARRAY_TEX_UV2].operator DVector<Vector2>().read();

	DVector<Color>::Read col;
	if (arrays[Mesh::ARRAY_COLOR].get_type()!=Variant::NIL)
		col = arrays[Mesh::ARRAY_COLOR].operator DVector<Color>().read();

	DVector<real_t>::Read bo;
	if (arrays[Mesh::ARRAY_BONES].get_type()!=Variant::NIL)
		bo = arrays[Mesh::ARRAY_BONES].operator DVector<real_t>().read();

	DVector<real_t>::Read we;
	if (arrays[Mesh::ARRAY_WEIGHTS].get_type()!=Variant::NIL)
		we = arrays[Mesh::ARRAY_WEIGHTS].operator DVector<real_t>().read();


	vertices.resize(vcount);

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

		Vertex v;
		v.vertex=vr[i];
		if (nr.ptr())
			v.normal=nr[i];
		if (ta.ptr())
			v.tangent=Plane(ta[i*4+0],ta[i*4+1],ta[i*4+2],ta[i*4+3]);
		if (uv.ptr())
			v.uv=uv[i];
		if (uv2.ptr())
			v.uv2=uv2[i];
		if (col.ptr())
			v.color=col[i];

		if (we.ptr()) {

			v.weights.push_back(we[i*4+0]);
			v.weights.push_back(we[i*4+1]);
			v.weights.push_back(we[i*4+2]);
			v.weights.push_back(we[i*4+3]);
		}

		if (bo.ptr()) {

			v.bones.push_back(bo[i*4+0]);
			v.bones.push_back(bo[i*4+1]);
			v.bones.push_back(bo[i*4+2]);
			v.bones.push_back(bo[i*4+3]);
		}

		vertices[i]=v;


	}


	DVector<int> indices;

	if (arrays[Mesh::ARRAY_INDEX].get_type()!=Variant::NIL) {

		indices = arrays[Mesh::ARRAY_INDEX];
	} else {
		//make code simpler
		indices.resize(vcount);
		DVector<int>::Write iw=indices.write();
		for(int i=0;i<vcount;i++)
			iw[i]=i;
	}


	int icount=indices.size();
	DVector<int>::Read r = indices.read();


	Map<Point2i,int> edge_indices;

	for(int i=0;i<icount;i+=3) {

		Vertex*v[3]={ &vertices[r[i+0]], &vertices[r[i+1]], &vertices[r[i+2]] };

		int fidx=faces.size();
		Face face;

		for(int j=0;j<3;j++) {

			face.v[j]=r[i+j];

			Point2i edge(r[i+j],r[i+(j+1)%3]);
			if (edge.x > edge.y) {
				SWAP(edge.x,edge.y);
			}

			if (edge_indices.has(edge)) {
				face.edges[j]=edge_indices[edge];

			} else {
				face.edges[j]=edge_indices.size();
				edge_indices[edge]=face.edges[j];
				Edge e;
				e.vertex[0]=edge.x;
				e.vertex[1]=edge.y;
				edges.push_back(e);
			}

			edges[face.edges[j]].faces.push_back(fidx);
			v[j]->faces.push_back(fidx);
			v[j]->edges.push_back(face.edges[j]);
		}


		faces.push_back(face);
	}


	return OK;
}
Ejemplo n.º 25
0
Error VariantParser::parse_value(Token& token,Variant &value,Stream *p_stream,int &line,String &r_err_str,ResourceParser *p_res_parser) {



/*	{
		Error err = get_token(p_stream,token,line,r_err_str);
		if (err)
			return err;
	}*/


	if (token.type==TK_CURLY_BRACKET_OPEN) {

		Dictionary d;
		Error err = _parse_dictionary(d,p_stream,line,r_err_str,p_res_parser);
		if (err)
			return err;
		value=d;
		return OK;
	} else if (token.type==TK_BRACKET_OPEN) {

		Array a;
		Error err = _parse_array(a,p_stream,line,r_err_str,p_res_parser);
		if (err)
			return err;
		value=a;
		return OK;

	} else if (token.type==TK_IDENTIFIER) {
/*
		VECTOR2,		// 5
		RECT2,
		VECTOR3,
		MATRIX32,
		PLANE,
		QUAT,			// 10
		_AABB, //sorry naming convention fail :( not like it's used often
		MATRIX3,
		TRANSFORM,

		// misc types
		COLOR,
		IMAGE,			// 15
		NODE_PATH,
		_RID,
		OBJECT,
		INPUT_EVENT,
		DICTIONARY,		// 20
		ARRAY,

		// arrays
		RAW_ARRAY,
		INT_ARRAY,
		REAL_ARRAY,
		STRING_ARRAY,	// 25
		VECTOR2_ARRAY,
		VECTOR3_ARRAY,
		COLOR_ARRAY,

		VARIANT_MAX

*/
		String id = token.value;
		if (id=="true")
			value=true;
		else if (id=="false")
			value=false;
		else if (id=="null" || id=="nil")
			value=Variant();
		else if (id=="Vector2"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=2) {
				r_err_str="Expected 2 arguments for constructor";
			}

			value=Vector2(args[0],args[1]);
			return OK;
		} else if (id=="Rect2"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=4) {
				r_err_str="Expected 4 arguments for constructor";
			}

			value=Rect2(args[0],args[1],args[2],args[3]);
			return OK;
		} else if (id=="Vector3"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=3) {
				r_err_str="Expected 3 arguments for constructor";
			}

			value=Vector3(args[0],args[1],args[2]);
			return OK;
		} else if (id=="Matrix32"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=6) {
				r_err_str="Expected 6 arguments for constructor";
			}
			Matrix32 m;
			m[0]=Vector2(args[0],args[1]);
			m[1]=Vector2(args[2],args[3]);
			m[2]=Vector2(args[4],args[5]);
			value=m;
			return OK;
		} else if (id=="Plane") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=4) {
				r_err_str="Expected 4 arguments for constructor";
			}

			value=Plane(args[0],args[1],args[2],args[3]);
			return OK;
		} else if (id=="Quat") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=4) {
				r_err_str="Expected 4 arguments for constructor";
			}

			value=Quat(args[0],args[1],args[2],args[3]);
			return OK;

		} else if (id=="AABB"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=6) {
				r_err_str="Expected 6 arguments for constructor";
			}

			value=AABB(Vector3(args[0],args[1],args[2]),Vector3(args[3],args[4],args[5]));
			return OK;

		} else if (id=="Matrix3"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=9) {
				r_err_str="Expected 9 arguments for constructor";
			}

			value=Matrix3(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8]);
			return OK;
		} else if (id=="Transform"){

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=12) {
				r_err_str="Expected 12 arguments for constructor";
			}

			value=Transform(Matrix3(args[0],args[1],args[2],args[3],args[4],args[5],args[6],args[7],args[8]),Vector3(args[9],args[10],args[11]));
			return OK;

		} else if (id=="Color") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			if (args.size()!=4) {
				r_err_str="Expected 4 arguments for constructor";
			}

			value=Color(args[0],args[1],args[2],args[3]);
			return OK;

		} else if (id=="Image") {

			//:|

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}


			get_token(p_stream,token,line,r_err_str);
			if (token.type==TK_PARENTHESIS_CLOSE) {
				value=Image(); // just an Image()
				return OK;
			} else if (token.type!=TK_NUMBER) {
				r_err_str="Expected number (width)";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);

			int width=token.value;
			if (token.type!=TK_COMMA) {
				r_err_str="Expected ','";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_NUMBER) {
				r_err_str="Expected number (height)";
				return ERR_PARSE_ERROR;
			}

			int height=token.value;

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_COMMA) {
				r_err_str="Expected ','";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_NUMBER) {
				r_err_str="Expected number (mipmaps)";
				return ERR_PARSE_ERROR;
			}

			int mipmaps=token.value;

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_COMMA) {
				r_err_str="Expected ','";
				return ERR_PARSE_ERROR;
			}


			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_IDENTIFIER) {
				r_err_str="Expected identifier (format)";
				return ERR_PARSE_ERROR;
			}


			String sformat=token.value;

			Image::Format format;

			if (sformat=="GRAYSCALE") format=Image::FORMAT_GRAYSCALE;
			else if (sformat=="INTENSITY") format=Image::FORMAT_INTENSITY;
			else if (sformat=="GRAYSCALE_ALPHA") format=Image::FORMAT_GRAYSCALE_ALPHA;
			else if (sformat=="RGB") format=Image::FORMAT_RGB;
			else if (sformat=="RGBA") format=Image::FORMAT_RGBA;
			else if (sformat=="INDEXED") format=Image::FORMAT_INDEXED;
			else if (sformat=="INDEXED_ALPHA") format=Image::FORMAT_INDEXED_ALPHA;
			else if (sformat=="BC1") format=Image::FORMAT_BC1;
			else if (sformat=="BC2") format=Image::FORMAT_BC2;
			else if (sformat=="BC3") format=Image::FORMAT_BC3;
			else if (sformat=="BC4") format=Image::FORMAT_BC4;
			else if (sformat=="BC5") format=Image::FORMAT_BC5;
			else if (sformat=="PVRTC2") format=Image::FORMAT_PVRTC2;
			else if (sformat=="PVRTC2_ALPHA") format=Image::FORMAT_PVRTC2_ALPHA;
			else if (sformat=="PVRTC4") format=Image::FORMAT_PVRTC4;
			else if (sformat=="PVRTC4_ALPHA") format=Image::FORMAT_PVRTC4_ALPHA;
			else if (sformat=="ATC") format=Image::FORMAT_ATC;
			else if (sformat=="ATC_ALPHA_EXPLICIT") format=Image::FORMAT_ATC_ALPHA_EXPLICIT;
			else if (sformat=="ATC_ALPHA_INTERPOLATED") format=Image::FORMAT_ATC_ALPHA_INTERPOLATED;
			else if (sformat=="CUSTOM") format=Image::FORMAT_CUSTOM;
			else {
				r_err_str="Invalid image format: '"+sformat+"'";
				return ERR_PARSE_ERROR;
			};

			int len = Image::get_image_data_size(width,height,format,mipmaps);

			DVector<uint8_t> buffer;
			buffer.resize(len);

			if (buffer.size()!=len) {
				r_err_str="Couldn't allocate image buffer of size: "+itos(len);
			}

			{
				DVector<uint8_t>::Write w=buffer.write();

				for(int i=0;i<len;i++) {
					get_token(p_stream,token,line,r_err_str);
					if (token.type!=TK_COMMA) {
						r_err_str="Expected ','";
						return ERR_PARSE_ERROR;
					}

					get_token(p_stream,token,line,r_err_str);
					if (token.type!=TK_NUMBER) {
						r_err_str="Expected number";
						return ERR_PARSE_ERROR;
					}

					w[i]=int(token.value);

				}
			}


			Image img(width,height,mipmaps,format,buffer);

			value=img;

			return OK;


		} else if (id=="NodePath") {



			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_STRING) {
				r_err_str="Expected string as argument for NodePath()";
				return ERR_PARSE_ERROR;
			}

			value=NodePath(String(token.value));

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_CLOSE) {
				r_err_str="Expected ')'";
				return ERR_PARSE_ERROR;
			}

		} else if (id=="RID") {



			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_NUMBER) {
				r_err_str="Expected number as argument";
				return ERR_PARSE_ERROR;
			}

			value=token.value;

			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_CLOSE) {
				r_err_str="Expected ')'";
				return ERR_PARSE_ERROR;
			}


			return OK;

		} else if (id=="Resource" || id=="SubResource" || id=="ExtResource") {



			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}


			if (p_res_parser && id=="Resource" && p_res_parser->func){

				RES res;
				Error err = p_res_parser->func(p_res_parser->userdata,p_stream,res,line,r_err_str);
				if (err)
					return err;

				value=res;

				return OK;
			} else if (p_res_parser && id=="ExtResource" && p_res_parser->ext_func){

				RES res;
				Error err = p_res_parser->ext_func(p_res_parser->userdata,p_stream,res,line,r_err_str);
				if (err)
					return err;

				value=res;

				return OK;
			} else if (p_res_parser && id=="SubResource" && p_res_parser->sub_func){

				RES res;
				Error err = p_res_parser->sub_func(p_res_parser->userdata,p_stream,res,line,r_err_str);
				if (err)
					return err;

				value=res;

				return OK;
			} else {

				get_token(p_stream,token,line,r_err_str);
				if (token.type==TK_STRING) {
					String path=token.value;
					RES res = ResourceLoader::load(path);
					if (res.is_null()) {
						r_err_str="Can't load resource at path: '"+path+"'.";
						return ERR_PARSE_ERROR;
					}

					get_token(p_stream,token,line,r_err_str);
					if (token.type!=TK_PARENTHESIS_CLOSE) {
						r_err_str="Expected ')'";
						return ERR_PARSE_ERROR;
					}

					value=res;
					return OK;

				} else {
					r_err_str="Expected string as argument for Resource().";
					return ERR_PARSE_ERROR;
				}
			}

			return OK;


		} else if (id=="InputEvent") {



			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}

			get_token(p_stream,token,line,r_err_str);

			if (token.type!=TK_IDENTIFIER) {
				r_err_str="Expected identifier";
				return ERR_PARSE_ERROR;
			}


			String id = token.value;

			InputEvent ie;

			if (id=="KEY") {

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_COMMA) {
					r_err_str="Expected ','";
					return ERR_PARSE_ERROR;
				}

				ie.type=InputEvent::KEY;


				get_token(p_stream,token,line,r_err_str);
				if (token.type==TK_IDENTIFIER) {
					String name=token.value;
					ie.key.scancode=find_keycode(name);
				} else if (token.type==TK_NUMBER) {

					ie.key.scancode=token.value;
				} else {

					r_err_str="Expected string or integer for keycode";
					return ERR_PARSE_ERROR;
				}

				get_token(p_stream,token,line,r_err_str);

				if (token.type==TK_COMMA) {

					get_token(p_stream,token,line,r_err_str);

					if (token.type!=TK_IDENTIFIER) {
						r_err_str="Expected identifier with modifier flas";
						return ERR_PARSE_ERROR;
					}

					String mods=token.value;

					if (mods.findn("C")!=-1)
						ie.key.mod.control=true;
					if (mods.findn("A")!=-1)
						ie.key.mod.alt=true;
					if (mods.findn("S")!=-1)
						ie.key.mod.shift=true;
					if (mods.findn("M")!=-1)
						ie.key.mod.meta=true;

					get_token(p_stream,token,line,r_err_str);
					if (token.type!=TK_PARENTHESIS_CLOSE) {
						r_err_str="Expected ')'";
						return ERR_PARSE_ERROR;
					}

				} else if (token.type!=TK_PARENTHESIS_CLOSE) {

					r_err_str="Expected ')' or modifier flags.";
					return ERR_PARSE_ERROR;
				}


			} else if (id=="MBUTTON") {

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_COMMA) {
					r_err_str="Expected ','";
					return ERR_PARSE_ERROR;
				}

				ie.type=InputEvent::MOUSE_BUTTON;

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_NUMBER) {
					r_err_str="Expected button index";
					return ERR_PARSE_ERROR;
				}

				ie.mouse_button.button_index = token.value;

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_PARENTHESIS_CLOSE) {
					r_err_str="Expected ')'";
					return ERR_PARSE_ERROR;
				}

			} else if (id=="JBUTTON") {

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_COMMA) {
					r_err_str="Expected ','";
					return ERR_PARSE_ERROR;
				}

				ie.type=InputEvent::JOYSTICK_BUTTON;

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_NUMBER) {
					r_err_str="Expected button index";
					return ERR_PARSE_ERROR;
				}

				ie.joy_button.button_index = token.value;

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_PARENTHESIS_CLOSE) {
					r_err_str="Expected ')'";
					return ERR_PARSE_ERROR;
				}

			} else if (id=="JAXIS") {

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_COMMA) {
					r_err_str="Expected ','";
					return ERR_PARSE_ERROR;
				}

				ie.type=InputEvent::JOYSTICK_MOTION;

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_NUMBER) {
					r_err_str="Expected axis index";
					return ERR_PARSE_ERROR;
				}

				ie.joy_motion.axis = token.value;

				get_token(p_stream,token,line,r_err_str);

				if (token.type!=TK_COMMA) {
					r_err_str="Expected ',' after axis index";
					return ERR_PARSE_ERROR;
				}

				get_token(p_stream,token,line,r_err_str);
				if (token.type!=TK_NUMBER) {
					r_err_str="Expected axis sign";
					return ERR_PARSE_ERROR;
				}

				ie.joy_motion.axis_value = token.value;

				get_token(p_stream,token,line,r_err_str);

				if (token.type!=TK_PARENTHESIS_CLOSE) {
					r_err_str="Expected ')' for jaxis";
					return ERR_PARSE_ERROR;
				}

			} else {

				r_err_str="Invalid input event type.";
				return ERR_PARSE_ERROR;
			}

			value=ie;

			return OK;

		} else if (id=="ByteArray") {

			Vector<uint8_t> args;
			Error err = _parse_construct<uint8_t>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<uint8_t> arr;
			{
				int len=args.size();
				arr.resize(len);
				DVector<uint8_t>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=args[i];
				}
			}

			value=arr;

			return OK;

		} else if (id=="IntArray") {

			Vector<int32_t> args;
			Error err = _parse_construct<int32_t>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<int32_t> arr;
			{
				int len=args.size();
				arr.resize(len);
				DVector<int32_t>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=int(args[i]);
				}
			}

			value=arr;

			return OK;

		} else if (id=="FloatArray") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<float> arr;
			{
				int len=args.size();
				arr.resize(len);
				DVector<float>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=args[i];
				}
			}

			value=arr;

			return OK;
		} else if (id=="StringArray") {


			get_token(p_stream,token,line,r_err_str);
			if (token.type!=TK_PARENTHESIS_OPEN) {
				r_err_str="Expected '('";
				return ERR_PARSE_ERROR;
			}

			Vector<String> cs;

			bool first=true;
			while(true) {

				if (!first) {
					get_token(p_stream,token,line,r_err_str);
					if (token.type==TK_COMMA) {
						//do none
					} else if (token.type==TK_PARENTHESIS_CLOSE) {
						break;
					} else {
						r_err_str="Expected ',' or ')'";
						return ERR_PARSE_ERROR;

					}
				}
				get_token(p_stream,token,line,r_err_str);

				if (token.type!=TK_STRING) {
					r_err_str="Expected string";
					return ERR_PARSE_ERROR;
				}

				first=false;
				cs.push_back(token.value);
			}


			DVector<String> arr;
			{
				int len=cs.size();
				arr.resize(len);
				DVector<String>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=cs[i];
				}
			}

			value=arr;

			return OK;


		} else if (id=="Vector2Array") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<Vector2> arr;
			{
				int len=args.size()/2;
				arr.resize(len);
				DVector<Vector2>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=Vector2(args[i*2+0],args[i*2+1]);
				}
			}

			value=arr;

			return OK;

		} else if (id=="Vector3Array") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<Vector3> arr;
			{
				int len=args.size()/3;
				arr.resize(len);
				DVector<Vector3>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=Vector3(args[i*3+0],args[i*3+1],args[i*3+2]);
				}
			}

			value=arr;

			return OK;

		} else if (id=="ColorArray") {

			Vector<float> args;
			Error err = _parse_construct<float>(p_stream,args,line,r_err_str);
			if (err)
				return err;

			DVector<Color> arr;
			{
				int len=args.size()/4;
				arr.resize(len);
				DVector<Color>::Write w = arr.write();
				for(int i=0;i<len;i++) {
					w[i]=Color(args[i*4+0],args[i*4+1],args[i*4+2],args[i*4+3]);
				}
			}

			value=arr;

			return OK;
		} else if (id=="key") { // compatibility with engine.cfg

			Vector<String> params;
			Error err = _parse_enginecfg(p_stream,params,line,r_err_str);
			if (err)
				return err;
			ERR_FAIL_COND_V(params.size()!=1 && params.size()!=2,ERR_PARSE_ERROR);

			int scode=0;

			if (params[0].is_numeric()) {
				scode=params[0].to_int();
				if (scode < 10) {
					scode=KEY_0+scode;
				}
			} else
				scode=find_keycode(params[0]);

			InputEvent ie;
			ie.type=InputEvent::KEY;
			ie.key.scancode=scode;

			if (params.size()==2) {
				String mods=params[1];
				if (mods.findn("C")!=-1)
					ie.key.mod.control=true;
				if (mods.findn("A")!=-1)
					ie.key.mod.alt=true;
				if (mods.findn("S")!=-1)
					ie.key.mod.shift=true;
				if (mods.findn("M")!=-1)
					ie.key.mod.meta=true;
			}
			value=ie;
			return OK;

		} else if (id=="mbutton") {  // compatibility with engine.cfg

			Vector<String> params;
			Error err = _parse_enginecfg(p_stream,params,line,r_err_str);
			if (err)
				return err;
			ERR_FAIL_COND_V(params.size()!=2,ERR_PARSE_ERROR);

			InputEvent ie;
			ie.type=InputEvent::MOUSE_BUTTON;
			ie.device=params[0].to_int();
			ie.mouse_button.button_index=params[1].to_int();

			value=ie;
			return OK;
		} else if (id=="jbutton") {  // compatibility with engine.cfg

			Vector<String> params;
			Error err = _parse_enginecfg(p_stream,params,line,r_err_str);
			if (err)
				return err;
			ERR_FAIL_COND_V(params.size()!=2,ERR_PARSE_ERROR);
			InputEvent ie;
			ie.type=InputEvent::JOYSTICK_BUTTON;
			ie.device=params[0].to_int();
			ie.joy_button.button_index=params[1].to_int();

			value=ie;

			return OK;
		} else if (id=="jaxis") {  // compatibility with engine.cfg

			Vector<String> params;
			Error err = _parse_enginecfg(p_stream,params,line,r_err_str);
			if (err)
				return err;
			ERR_FAIL_COND_V(params.size()!=2,ERR_PARSE_ERROR);

			InputEvent ie;
			ie.type=InputEvent::JOYSTICK_MOTION;
			ie.device=params[0].to_int();
			int axis=params[1].to_int();
			ie.joy_motion.axis=axis>>1;
			ie.joy_motion.axis_value=axis&1?1:-1;

			value= ie;

			return OK;
		} else if (id=="img") {  // compatibility with engine.cfg
Ejemplo n.º 26
0
void i_vti_v(RBlackbox& Res, DenseMatrix<Rationals >& M, DVector& den, Integer& detPrec)
{
	detPrec=1;
	Rationals Q;
	int n = M.coldim();
	//DVector denV(n,1);
	for (int i=0; i < den.size();++i) den[i]=1;
	for (int i=0; i < n; ++i) {
		for (int j=0; j <=i ; ++j) {
			Integer q_num =0;
			Integer q_den =1;
			for (int k=0; k < n; ++k) {
				Integer deno_ik, nume_ik, deno_jk, nume_jk, deno, nume;
				Q.get_den (deno_ik, M.getEntry(k,i));
				Q.get_num (nume_ik, M.getEntry(k,i));
				Q.get_den (deno_jk, M.getEntry(k,j));
				Q.get_num (nume_jk, M.getEntry(k,j));

				if (i==k) {
					nume_ik = deno_ik-nume_ik;
				}
				else {
					nume_ik = -nume_ik;
				}

				if (j==k) {
					nume_jk = deno_jk-nume_jk;
				}
				else {
					nume_jk = -nume_jk;
				}
				//cout << nume_ik << nume_jk;

				deno = deno_ik*deno_jk;
				nume = nume_ik*nume_jk;
				//cout << q_num << "/" << q_den << " " ;
				//cout << nume << "/" << deno << " " ;
				if (deno==q_den) q_num+=nume;
				else {
					if (nume != 0) {
						Integer g = gcd(q_den, deno);
						q_num = q_num*deno/g+nume*q_den/g;
						q_den = q_den*deno/g;
					}
				}
				//cout << q_num << "/" << q_den << " " ;
			}
			if (q_num != 0) {
				Quotient q(q_num,q_den);
				if (i!=j) {
					den[i]=lcm(den[i], q_den);
					den[j]=lcm(den[j], q_den);
					Res.setEntry(i,j,q);
					Res.setEntry(j,i,q);
					cout << i << " " << j << " " << q_num << "/" << q_den << "\n";
					cout << j << " " << i << " " << q_num << "/" << q_den << "\n";
				}
				else {
					den[i]=lcm(den[i], q_den);
					Res.setEntry(i,j,q);
					cout << i << " " << j << " " << q_num << "/" << q_den << "\n";
				}
			}
		}
	}
	Integer d = 1;
	for (int i=0; i < den.size(); ++i) {
		detPrec *=den[i];
		d = lcm(d, den[i]);
	}
	den[den.size()-1]=d;
	for (int i=den.size()-2; i >=0; --i) {
		den[i]=d*den[i+1];
	}

}
Ejemplo n.º 27
0
void TriangleMesh::create(const DVector<Vector3>& p_faces) {

	valid=false;

	int fc=p_faces.size();
	ERR_FAIL_COND(!fc || ((fc%3) != 0));
	fc/=3;
	triangles.resize(fc);

	bvh.resize(fc*3); //will never be larger than this (todo make better)
	DVector<BVH>::Write bw = bvh.write();

	{

		//create faces and indices and base bvh
		//except for the Set for repeated triangles, everything
		//goes in-place.

		DVector<Vector3>::Read r = p_faces.read();
		DVector<Triangle>::Write w = triangles.write();
		Map<Vector3,int> db;

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

			Triangle&f=w[i];
			const Vector3 *v=&r[i*3];

			for(int j=0;j<3;j++) {

				int vidx=-1;
				Vector3 vs=v[j].snapped(0.0001);
				Map<Vector3,int>::Element *E=db.find(vs);
				if (E) {
					vidx=E->get();
				} else {
					vidx=db.size();
					db[vs]=vidx;
				}

				f.indices[j]=vidx;
				if (j==0)
					bw[i].aabb.pos=vs;
				else
					bw[i].aabb.expand_to(vs);
			}

			f.normal=Face3(r[i*3+0],r[i*3+1],r[i*3+2]).get_plane().get_normal();

			bw[i].left=-1;
			bw[i].right=-1;
			bw[i].face_index=i;
			bw[i].center=bw[i].aabb.pos+bw[i].aabb.size*0.5;
		}

		vertices.resize(db.size());
		DVector<Vector3>::Write vw = vertices.write();
		for (Map<Vector3,int>::Element *E=db.front();E;E=E->next()) {
			vw[E->get()]=E->key();
		}

	}

	DVector<BVH*> bwptrs;
	bwptrs.resize(fc);
	DVector<BVH*>::Write bwp = bwptrs.write();
	for(int i=0;i<fc;i++) {

		bwp[i]=&bw[i];
	}

	max_depth=0;
	int max_alloc=fc;
	int max=_create_bvh(bw.ptr(),bwp.ptr(),0,fc,1,max_depth,max_alloc);

	bw=DVector<BVH>::Write(); //clearup
	bvh.resize(max_alloc); //resize back

	valid=true;

}
Ejemplo n.º 28
0
void generate_precRatMat(string& filename, RMatrix& M, DVector& den, Integer& denPrec)
{
	int prec=10;
	denPrec = 1;
	ifstream is(filename.c_str(), std::ios::in);
	int m,n;
	char c;
	is >> m >> n;
	do is >> c; while (isspace (c));
	if ((m > M.rowdim()) || (n > M.coldim())) {
		cout << m << " " << n << " " ;
		cout << "Wrong matrix size\n";
		return;
	}

	cout << "Reading matrix\n";

	den.resize(m,1);
	while (1) {//! @todo temp fix
#if 0
		while (is >> m) //temp fix
			if (m==0) break;//temp fix
#endif
		is >> m;//temp fix
		is >> n;
#if 0
		cout << m << n << "\n";
		long double x;
		is >> x;
#endif
		char xstr[500];
		char numstr[500];
#if 0
		cout << x << " ";
		sprintf(xstr, "%100f", x);
		cout << xstr << " " ;
		is >> c; int i=0;
		while (c!= '\n') {
			xstr[i]=c;
			++i;
			is >> c;
			if (i>=199) {
				xstr[i]=0;
				break;
			}
		}
		is >> c;
#endif
		is.getline(xstr,500);

		Integer ten=1;
		if (strchr(xstr, '/') != NULL) {
			//cout << "xstr " << xstr << "\n";
			//! @bug non reentrant strtok
			strcpy(numstr, strtok(xstr, "/"));
			char tenstr[500];
			strcpy(tenstr, strtok(NULL, "/"));
			if (prec < strlen(tenstr)) {
				int cut = strlen(tenstr)-prec;
				tenstr[prec]=0;
				//c = numstr[strlen(numstr)-2];
				numstr[strlen(numstr)-cut]=0;//temp round down
			}
			Integer tmp(tenstr);
			ten = tmp;
			//cout << numstr << "/"  << ten << "\n";
		}
		else
		{

			//    cout << "xstr" << xstr << " " ;
			int i=0;
			int j=0;
			c=xstr[i]; ++i;
			while (isspace (c)) {
				if (i >=strlen(xstr)) break;
				c=xstr[i];
				++i;
			}
			if (c=='-') {
				numstr[j]=c;++j;
				if (i < strlen(xstr)) {
					c = xstr[i];
					++i;
				}
			}
			if (c=='0') {
				//cout << "zero";
				if (i < strlen(xstr)) {
					c = xstr[i];
					++i;
				}
			} //else cout << " not 0" << c;
			while (strchr("0123456789",c) != NULL) {
				//cout << "number";
				numstr[j]=c; ++j;
				if (i >=strlen(xstr)) break;
				c=xstr[i];
				++i;
			}
			if (c=='.') {
				if (i < strlen(xstr)) {
					c = xstr[i];
					//cout << "c" << c ;
					++i;
					while (strchr("0123456789",c) != NULL) {
						numstr[j]=c;++j;
						if (i >=strlen(xstr)) break;
						c=xstr[i];
						++i;
					}
				}
				else {
					cout << "wrong number format at .";
					break;
				}
			}
			numstr[j]=0;
			//cout << "num" << numstr << " " ;

			size_t dplaces=0;
			int exp=0;
			j=0;
			c = xstr[j]; ++j;
			while (c != '.') {
				if (j >= strlen(xstr)) break;
				c = xstr[j];
				++j;
			}
			if (j < strlen(xstr)) {
				c = xstr[j]; ++j;
				while (c != 'e') {
					++dplaces;
					ten *= 10;
					if (j >= strlen(xstr)) break;
					c = xstr[j];
					++j;
				}
			}
			if (j < strlen(xstr)) {
				sscanf(xstr+j, "%d", &exp);
				j=j-2;c = xstr[j];
				while (c=='0') {
					ten/=10;
					--j;
					c = xstr[j];
				}
			}

			dplaces -=exp;
			if (exp > 0) {
				for (int i=0; i < exp; ++i) ten /=10;
			}
			else if (exp < 0) {
				for (int i=0; i < exp; ++i) ten *=10;
			}
			//double nume = x * (double)ten;
		}
		Integer num (numstr);
		Integer g;

#ifdef _LB_CONT_FR
		double epsi = 1/(double)ten*10;
		size_t s=10;
		continuedFractionIn(num, ten, epsi, s, ten);
#endif
		//cout << m << " " << n << " " << num << "/" << ten << "\n";
		g = gcd(num,ten);
		//g =1;
		Quotient q(num/g,ten/g);
		if ((m==0)&&(n==0)&&(num==0)) break;//temp fix
		//M.setEntry(m-1,n-1,q);//temp fix
		M.setEntry(m,n,q);
		den[m-1] = lcm(den[m-1],ten/g);
	}
	Integer d = 1;
	for (int i=0; i < den.size(); ++i) {
		denPrec *=den[i];
		d = lcm(d, den[i]);
	}
	den[den.size()-1]=d;
	cout << d << "\n";
	for (int i=den.size()-2; i >=0; --i) {
		den[i]=d*den[i+1];
		cout << den[i] << "\n";
	}
}
Error EditorSampleImportPlugin::import(const String& p_path, const Ref<ResourceImportMetadata>& p_from){

	ERR_FAIL_COND_V(p_from->get_source_count()!=1,ERR_INVALID_PARAMETER);

	Ref<ResourceImportMetadata> from=p_from;

	String src_path=EditorImportPlugin::expand_source_path(from->get_source_path(0));
	Ref<Sample> smp = ResourceLoader::load(src_path);
	ERR_FAIL_COND_V(smp.is_null(),ERR_CANT_OPEN);


	float rate = smp->get_mix_rate();
	bool is16 = smp->get_format()==Sample::FORMAT_PCM16;
	int chans = smp->is_stereo()?2:1;
	int len = smp->get_length();
	Sample::LoopFormat loop= smp->get_loop_format();
	int loop_beg = smp->get_loop_begin();
	int loop_end = smp->get_loop_end();

	print_line("Input Sample: ");
	print_line("\tlen: "+itos(len));
	print_line("\tchans: "+itos(chans));
	print_line("\t16bits: "+itos(is16));
	print_line("\trate: "+itos(rate));
	print_line("\tloop: "+itos(loop));
	print_line("\tloop begin: "+itos(loop_beg));
	print_line("\tloop end: "+itos(loop_end));
	Vector<float> data;
	data.resize(len*chans);

	{
		DVector<uint8_t> src_data = smp->get_data();
		DVector<uint8_t>::Read sr = src_data.read();


		for(int i=0;i<len*chans;i++) {

			float s=0;
			if (is16) {

				int16_t i16 = decode_uint16(&sr[i*2]);
				s=i16/32767.0;
			} else {

				int8_t i8 = sr[i];
				s=i8/127.0;
			}
			data[i]=s;
		}
	}

	//apply frequency limit

	bool limit_rate = from->get_option("force/max_rate");
	int limit_rate_hz = from->get_option("force/max_rate_hz");
	if (limit_rate && rate > limit_rate_hz) {
		//resampleeee!!!
		int new_data_len = len * limit_rate_hz / rate;
		Vector<float> new_data;
		new_data.resize( new_data_len * chans );
		for(int c=0;c<chans;c++) {

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

				//simple cubic interpolation should be enough.
				float pos = float(i) * len / new_data_len;
				float mu = pos-Math::floor(pos);
				int ipos = int(Math::floor(pos));

				float y0=data[MAX(0,ipos-1)*chans+c];
				float y1=data[ipos*chans+c];
				float y2=data[MIN(len-1,ipos+1)*chans+c];
				float y3=data[MIN(len-1,ipos+2)*chans+c];

				float mu2 = mu*mu;
				float a0 = y3 - y2 - y0 + y1;
				float a1 = y0 - y1 - a0;
				float a2 = y2 - y0;
				float a3 = y1;

				float res=(a0*mu*mu2+a1*mu2+a2*mu+a3);

				new_data[i*chans+c]=res;
			}
		}

		if (loop) {

			loop_beg=loop_beg*new_data_len/len;
			loop_end=loop_end*new_data_len/len;
		}
		data=new_data;
		rate=limit_rate_hz;
		len=new_data_len;
	}


	bool normalize = from->get_option("edit/normalize");

	if (normalize) {

		float max=0;
		for(int i=0;i<data.size();i++) {

			float amp = Math::abs(data[i]);
			if (amp>max)
				max=amp;
		}

		if (max>0) {

			float mult=1.0/max;
			for(int i=0;i<data.size();i++) {

				data[i]*=mult;
			}

		}
	}

	bool trim = from->get_option("edit/trim");

	if (trim && !loop) {

		int first=0;
		int last=(len*chans)-1;
		bool found=false;
		float limit = Math::db2linear(-30);
		for(int i=0;i<data.size();i++) {
			float amp = Math::abs(data[i]);

			if (!found && amp > limit) {
				first=i;
				found=true;
			}

			if (found && amp > limit) {
				last=i;
			}
		}

		first/=chans;
		last/=chans;

		if (first<last) {

			Vector<float> new_data;
			new_data.resize((last-first+1)*chans);
			for(int i=first*chans;i<=last*chans;i++) {
				new_data[i-first*chans]=data[i];
			}

			data=new_data;
			len=data.size()/chans;
		}

	}

	bool make_loop = from->get_option("edit/loop");

	if (make_loop && !loop) {

		loop=Sample::LOOP_FORWARD;
		loop_beg=0;
		loop_end=len;
	}

	int compression = from->get_option("compress/mode");
	bool force_mono = from->get_option("force/mono");


	if (force_mono && chans==2) {

		Vector<float> new_data;
		new_data.resize(data.size()/2);
		for(int i=0;i<len;i++) {
			new_data[i]=(data[i*2+0]+data[i*2+1])/2.0;
		}

		data=new_data;
		chans=1;
	}

	bool force_8_bit = from->get_option("force/8_bit");
	if (force_8_bit) {

		is16=false;
	}


	DVector<uint8_t> dst_data;
	Sample::Format dst_format;

	if ( compression == _EditorSampleImportOptions::COMPRESS_MODE_RAM) {

		dst_format=Sample::FORMAT_IMA_ADPCM;
		if (chans==1) {
			_compress_ima_adpcm(data,dst_data);
		} else {

			print_line("INTERLEAAVE!");



			//byte interleave
			Vector<float> left;
			Vector<float> right;

			int tlen = data.size()/2;
			left.resize(tlen);
			right.resize(tlen);

			for(int i=0;i<tlen;i++) {
				left[i]=data[i*2+0];
				right[i]=data[i*2+1];
			}

			DVector<uint8_t> bleft;
			DVector<uint8_t> bright;

			_compress_ima_adpcm(left,bleft);
			_compress_ima_adpcm(right,bright);

			int dl = bleft.size();
			dst_data.resize( dl *2 );

			DVector<uint8_t>::Write w=dst_data.write();
			DVector<uint8_t>::Read rl=bleft.read();
			DVector<uint8_t>::Read rr=bright.read();

			for(int i=0;i<dl;i++) {
				w[i*2+0]=rl[i];
				w[i*2+1]=rr[i];
			}
		}

//		print_line("compressing ima-adpcm, resulting buffersize is "+itos(dst_data.size())+" from "+itos(data.size()));

	} else {

		dst_format=is16?Sample::FORMAT_PCM16:Sample::FORMAT_PCM8;
		dst_data.resize( data.size() * (is16?2:1));
		{
			DVector<uint8_t>::Write w = dst_data.write();

			int ds=data.size();
			for(int i=0;i<ds;i++) {

				if (is16) {
					int16_t v = CLAMP(data[i]*32767,-32768,32767);
					encode_uint16(v,&w[i*2]);
				} else {
					int8_t v = CLAMP(data[i]*127,-128,127);
					w[i]=v;
				}
			}
		}
	}


	Ref<Sample> target;

	if (ResourceCache::has(p_path)) {

		target = Ref<Sample>( ResourceCache::get(p_path)->cast_to<Sample>() );
	} else {

		target = smp;
	}

	target->create(dst_format,chans==2?true:false,len);
	target->set_data(dst_data);
	target->set_mix_rate(rate);
	target->set_loop_format(loop);
	target->set_loop_begin(loop_beg);
	target->set_loop_end(loop_end);

	from->set_source_md5(0,FileAccess::get_md5(src_path));
	from->set_editor(get_name());
	target->set_import_metadata(from);


	Error err = ResourceSaver::save(p_path,smp);

	return err;

}
Ejemplo n.º 30
0
Error ResourceInteractiveLoaderBinary::parse_variant(Variant& r_v)  {


	uint32_t type = f->get_32();
	print_bl("find property of type: "+itos(type));


	switch(type) {

		case VARIANT_NIL: {

			r_v=Variant();
		} break;
		case VARIANT_BOOL: {

			r_v=bool(f->get_32());
		} break;
		case VARIANT_INT: {

			r_v=int(f->get_32());
		} break;
		case VARIANT_REAL: {

			r_v=f->get_real();
		} break;
		case VARIANT_STRING: {

			r_v=get_unicode_string();
		} break;
		case VARIANT_VECTOR2: {

			Vector2 v;
			v.x=f->get_real();
			v.y=f->get_real();
			r_v=v;

		} break;
		case VARIANT_RECT2: {

			Rect2 v;
			v.pos.x=f->get_real();
			v.pos.y=f->get_real();
			v.size.x=f->get_real();
			v.size.y=f->get_real();
			r_v=v;

		} break;
		case VARIANT_VECTOR3: {

			Vector3 v;
			v.x=f->get_real();
			v.y=f->get_real();
			v.z=f->get_real();
			r_v=v;
		} break;
		case VARIANT_PLANE: {

			Plane v;
			v.normal.x=f->get_real();
			v.normal.y=f->get_real();
			v.normal.z=f->get_real();
			v.d=f->get_real();
			r_v=v;
		} break;
		case VARIANT_QUAT: {
			Quat v;
			v.x=f->get_real();
			v.y=f->get_real();
			v.z=f->get_real();
			v.w=f->get_real();
			r_v=v;

		} break;
		case VARIANT_AABB: {

			AABB v;
			v.pos.x=f->get_real();
			v.pos.y=f->get_real();
			v.pos.z=f->get_real();
			v.size.x=f->get_real();
			v.size.y=f->get_real();
			v.size.z=f->get_real();
			r_v=v;

		} break;
		case VARIANT_MATRIX32: {

			Matrix32 v;
			v.elements[0].x=f->get_real();
			v.elements[0].y=f->get_real();
			v.elements[1].x=f->get_real();
			v.elements[1].y=f->get_real();
			v.elements[2].x=f->get_real();
			v.elements[2].y=f->get_real();
			r_v=v;

		} break;
		case VARIANT_MATRIX3: {

			Matrix3 v;
			v.elements[0].x=f->get_real();
			v.elements[0].y=f->get_real();
			v.elements[0].z=f->get_real();
			v.elements[1].x=f->get_real();
			v.elements[1].y=f->get_real();
			v.elements[1].z=f->get_real();
			v.elements[2].x=f->get_real();
			v.elements[2].y=f->get_real();
			v.elements[2].z=f->get_real();
			r_v=v;

		} break;
		case VARIANT_TRANSFORM: {

			Transform v;
			v.basis.elements[0].x=f->get_real();
			v.basis.elements[0].y=f->get_real();
			v.basis.elements[0].z=f->get_real();
			v.basis.elements[1].x=f->get_real();
			v.basis.elements[1].y=f->get_real();
			v.basis.elements[1].z=f->get_real();
			v.basis.elements[2].x=f->get_real();
			v.basis.elements[2].y=f->get_real();
			v.basis.elements[2].z=f->get_real();
			v.origin.x=f->get_real();
			v.origin.y=f->get_real();
			v.origin.z=f->get_real();
			r_v=v;
		} break;
		case VARIANT_COLOR: {

			Color v;
			v.r=f->get_real();
			v.g=f->get_real();
			v.b=f->get_real();
			v.a=f->get_real();
			r_v=v;

		} break;
		case VARIANT_IMAGE: {


			uint32_t encoding = f->get_32();
			if (encoding==IMAGE_ENCODING_EMPTY) {
				r_v=Variant();
				break;
			} else if (encoding==IMAGE_ENCODING_RAW) {
				uint32_t width = f->get_32();
				uint32_t height = f->get_32();
				uint32_t mipmaps = f->get_32();
				uint32_t format = f->get_32();
				Image::Format fmt;
				switch(format) {

					case IMAGE_FORMAT_GRAYSCALE: { fmt=Image::FORMAT_GRAYSCALE; } break;
					case IMAGE_FORMAT_INTENSITY: { fmt=Image::FORMAT_INTENSITY; } break;
					case IMAGE_FORMAT_GRAYSCALE_ALPHA: { fmt=Image::FORMAT_GRAYSCALE_ALPHA; } break;
					case IMAGE_FORMAT_RGB: { fmt=Image::FORMAT_RGB; } break;
					case IMAGE_FORMAT_RGBA: { fmt=Image::FORMAT_RGBA; } break;
					case IMAGE_FORMAT_INDEXED: { fmt=Image::FORMAT_INDEXED; } break;
					case IMAGE_FORMAT_INDEXED_ALPHA: { fmt=Image::FORMAT_INDEXED_ALPHA; } break;
					case IMAGE_FORMAT_BC1: { fmt=Image::FORMAT_BC1; } break;
					case IMAGE_FORMAT_BC2: { fmt=Image::FORMAT_BC2; } break;
					case IMAGE_FORMAT_BC3: { fmt=Image::FORMAT_BC3; } break;
					case IMAGE_FORMAT_BC4: { fmt=Image::FORMAT_BC4; } break;
					case IMAGE_FORMAT_BC5: { fmt=Image::FORMAT_BC5; } break;
					case IMAGE_FORMAT_PVRTC2: { fmt=Image::FORMAT_PVRTC2; } break;
					case IMAGE_FORMAT_PVRTC2_ALPHA: { fmt=Image::FORMAT_PVRTC2_ALPHA; } break;
					case IMAGE_FORMAT_PVRTC4: { fmt=Image::FORMAT_PVRTC4; } break;
					case IMAGE_FORMAT_PVRTC4_ALPHA: { fmt=Image::FORMAT_PVRTC4_ALPHA; } break;
					case IMAGE_FORMAT_ETC: { fmt=Image::FORMAT_ETC; } break;
					case IMAGE_FORMAT_CUSTOM: { fmt=Image::FORMAT_CUSTOM; } break;
					default: {

						ERR_FAIL_V(ERR_FILE_CORRUPT);
					}

				}


				uint32_t datalen = f->get_32();

				DVector<uint8_t> imgdata;
				imgdata.resize(datalen);
				DVector<uint8_t>::Write w = imgdata.write();
				f->get_buffer(w.ptr(),datalen);
				_advance_padding(datalen);
				w=DVector<uint8_t>::Write();

				r_v=Image(width,height,mipmaps,fmt,imgdata);

			} else {
				//compressed
				DVector<uint8_t> data;
				data.resize(f->get_32());
				DVector<uint8_t>::Write w = data.write();
				f->get_buffer(w.ptr(),data.size());
				w = DVector<uint8_t>::Write();

				Image img;

				if (encoding==IMAGE_ENCODING_LOSSY && Image::lossy_unpacker) {

					img = Image::lossy_unpacker(data);
				} else if (encoding==IMAGE_ENCODING_LOSSLESS && Image::lossless_unpacker) {

					img = Image::lossless_unpacker(data);
				}
				_advance_padding(data.size());


				r_v=img;

			}

		} break;
		case VARIANT_NODE_PATH: {

			Vector<StringName> names;
			Vector<StringName> subnames;
			StringName property;
			bool absolute;

			int name_count = f->get_16();
			uint32_t subname_count = f->get_16();
			absolute=subname_count&0x8000;
			subname_count&=0x7FFF;


			for(int i=0;i<name_count;i++)
				names.push_back(string_map[f->get_32()]);
			for(uint32_t i=0;i<subname_count;i++)
				subnames.push_back(string_map[f->get_32()]);
			property=string_map[f->get_32()];

			NodePath np = NodePath(names,subnames,absolute,property);
			//print_line("got path: "+String(np));

			r_v=np;

		} break;
		case VARIANT_RID: {

			r_v=f->get_32();
		} break;
		case VARIANT_OBJECT: {

			uint32_t type=f->get_32();

			switch(type) {

				case OBJECT_EMPTY: {
					//do none

				} break;
				case OBJECT_INTERNAL_RESOURCE: {
					uint32_t index=f->get_32();
					String path = res_path+"::"+itos(index);
					RES res = ResourceLoader::load(path);
					if (res.is_null()) {
						WARN_PRINT(String("Couldn't load resource: "+path).utf8().get_data());
					}
					r_v=res;

				} break;
				case OBJECT_EXTERNAL_RESOURCE: {

					String type = get_unicode_string();
					String path = get_unicode_string();

					if (path.find("://")==-1 && path.is_rel_path()) {
						// path is relative to file being loaded, so convert to a resource path
						path=Globals::get_singleton()->localize_path(res_path.get_base_dir()+"/"+path);

					}

					RES res=ResourceLoader::load(path,type);

					if (res.is_null()) {
						WARN_PRINT(String("Couldn't load resource: "+path).utf8().get_data());
					}
					r_v=res;

				} break;
				default: {

					ERR_FAIL_V(ERR_FILE_CORRUPT);
				} break;
			}

		} break;
		case VARIANT_INPUT_EVENT: {

		} break;
		case VARIANT_DICTIONARY: {

            uint32_t len=f->get_32();
            Dictionary d(len&0x80000000); //last bit means shared
            len&=0x7FFFFFFF;
            for(uint32_t i=0;i<len;i++) {
				Variant key;
				Error err = parse_variant(key);
				ERR_FAIL_COND_V(err,ERR_FILE_CORRUPT);
				Variant value;
				err = parse_variant(value);
				ERR_FAIL_COND_V(err,ERR_FILE_CORRUPT);
				d[key]=value;
			}
			r_v=d;
		} break;
		case VARIANT_ARRAY: {

            uint32_t len=f->get_32();
            Array a(len&0x80000000); //last bit means shared
            len&=0x7FFFFFFF;
			a.resize(len);
            for(uint32_t i=0;i<len;i++) {
				Variant val;
				Error err = parse_variant(val);
				ERR_FAIL_COND_V(err,ERR_FILE_CORRUPT);
				a[i]=val;
			}
			r_v=a;

		} break;
		case VARIANT_RAW_ARRAY: {

			uint32_t len = f->get_32();

			DVector<uint8_t> array;
			array.resize(len);
			DVector<uint8_t>::Write w = array.write();
			f->get_buffer(w.ptr(),len);
			_advance_padding(len);
			w=DVector<uint8_t>::Write();
			r_v=array;

		} break;
		case VARIANT_INT_ARRAY: {

			uint32_t len = f->get_32();

			DVector<int> array;
			array.resize(len);
			DVector<int>::Write w = array.write();
			f->get_buffer((uint8_t*)w.ptr(),len*4);
#ifdef BIG_ENDIAN_ENABLED
			{
				uint32_t *ptr=(uint32_t*)w.ptr();
				for(int i=0;i<len;i++) {

					ptr[i]=BSWAP32(ptr[i]);
				}
			}

#endif
			w=DVector<int>::Write();
			r_v=array;
		} break;
		case VARIANT_REAL_ARRAY: {

			uint32_t len = f->get_32();

			DVector<real_t> array;
			array.resize(len);
			DVector<real_t>::Write w = array.write();
			f->get_buffer((uint8_t*)w.ptr(),len*sizeof(real_t));
#ifdef BIG_ENDIAN_ENABLED
			{
				uint32_t *ptr=(uint32_t*)w.ptr();
				for(int i=0;i<len;i++) {

					ptr[i]=BSWAP32(ptr[i]);
				}
			}

#endif

			w=DVector<real_t>::Write();
			r_v=array;
		} break;
		case VARIANT_STRING_ARRAY: {

			uint32_t len = f->get_32();
			DVector<String> array;
			array.resize(len);
			DVector<String>::Write w = array.write();
			for(uint32_t i=0;i<len;i++)
				w[i]=get_unicode_string();
			w=DVector<String>::Write();
			r_v=array;


		} break;
		case VARIANT_VECTOR2_ARRAY: {

			uint32_t len = f->get_32();

			DVector<Vector2> array;
			array.resize(len);
			DVector<Vector2>::Write w = array.write();
			if (sizeof(Vector2)==8) {
				f->get_buffer((uint8_t*)w.ptr(),len*sizeof(real_t)*2);
#ifdef BIG_ENDIAN_ENABLED
			{
				uint32_t *ptr=(uint32_t*)w.ptr();
				for(int i=0;i<len*2;i++) {

					ptr[i]=BSWAP32(ptr[i]);
				}
			}

#endif

			} else {
				ERR_EXPLAIN("Vector2 size is NOT 8!");
				ERR_FAIL_V(ERR_UNAVAILABLE);
			}
			w=DVector<Vector2>::Write();
			r_v=array;

		} break;
		case VARIANT_VECTOR3_ARRAY: {

			uint32_t len = f->get_32();

			DVector<Vector3> array;
			array.resize(len);
			DVector<Vector3>::Write w = array.write();
			if (sizeof(Vector3)==12) {
				f->get_buffer((uint8_t*)w.ptr(),len*sizeof(real_t)*3);
#ifdef BIG_ENDIAN_ENABLED
				{
					uint32_t *ptr=(uint32_t*)w.ptr();
					for(int i=0;i<len*3;i++) {

						ptr[i]=BSWAP32(ptr[i]);
					}
				}

#endif

			} else {
				ERR_EXPLAIN("Vector3 size is NOT 12!");
				ERR_FAIL_V(ERR_UNAVAILABLE);
			}
			w=DVector<Vector3>::Write();
			r_v=array;

		} break;
		case VARIANT_COLOR_ARRAY: {

			uint32_t len = f->get_32();

			DVector<Color> array;
			array.resize(len);
			DVector<Color>::Write w = array.write();
			if (sizeof(Color)==16) {
				f->get_buffer((uint8_t*)w.ptr(),len*sizeof(real_t)*4);
#ifdef BIG_ENDIAN_ENABLED
			{
				uint32_t *ptr=(uint32_t*)w.ptr();
				for(int i=0;i<len*4;i++) {

					ptr[i]=BSWAP32(ptr[i]);
				}
			}

#endif

			} else {
				ERR_EXPLAIN("Color size is NOT 16!");
				ERR_FAIL_V(ERR_UNAVAILABLE);
			}
			w=DVector<Color>::Write();
			r_v=array;
		} break;

		default: {
			ERR_FAIL_V(ERR_FILE_CORRUPT);
		} break;
	}



	return OK; //never reach anyway

}