public ProgressMapper(IProgressListener parent, double min, double range, string message) { Parent = parent; MinRange = min; MaxRange = min + range; Message = message; }
private IEnumerator notifyCompleted(IProgressListener listener) { yield return(2); this.enabled = false; listener.onComplete(); }
public void Read(IProgressListener progress) { Stopwatch watch = new Stopwatch(); watch.Start(); try { if (!File.Exists(name)) { return; } DateTime tim = File.GetLastWriteTime(name); if (tim == timestamp) { return; } timestamp = tim; if (reader == null) { reader = new LogFileReader(name); } ReadLogFile(progress); } catch (Exception ex) { Console.WriteLine(ex); } finally { watch.Stop(); Console.WriteLine("ObjectMapFileReader.Read (): Completed in {0} s", watch.ElapsedMilliseconds / (double)1000); } }
public async Task FetchFullDownloadableDataIntoDatabase( string exhibitId, int idForRestApi, CancellationToken token, IProgressListener listener) { double totalSteps = await FetchNeededMediaForFullExhibit(idForRestApi); if (token.IsCancellationRequested) { return; } listener.SetMaxProgress(totalSteps); // We need to attach all images since the quiz download may download existing images var itemsToTrack = DbManager .DataAccess .GetItems <Image>() .Where(image => image.Id != BackupData.BackupImage.Id && image.Id != BackupData.BackupImageTag.Id); await mediaDataFetcher.FetchMedias(requiredMedia, token, listener); var quizzes = await DownloadQuizes(idForRestApi, token); var mediaToFilePath = await mediaDataFetcher.WriteMediaToDiskAsync(); DbManager.InTransaction(itemsToTrack, transaction => { ProcessPages(exhibitId, token, transaction.DataAccess, mediaToFilePath); transaction.DataAccess.Quizzes().Add(quizzes); if (token.IsCancellationRequested) { transaction.Rollback(); } }); }
private void Remesh(ref Mesh mesh, int toRemove, IProgressListener progress = null) { if (!(toRemove > mesh.Triangles.Count && mesh.Triangles.Count > 10)) { throw new ArgumentOutOfRangeException("toRemove", toRemove, "Invalid triangle count"); } var vertices = mesh.Vertices; progress.OnStart("Started remeshing"); int totalVertices = mesh.Vertices.Count; Debug.Assert(toRemove > 0); Random random = new Random(); while (toRemove > 0) { //vertices.ran var element = vertices.ElementAt(random.Next(0, vertices.Count - 1)); mesh.JoinToNearestByDistance(element); toRemove -= 2; progress.OnProgress(toRemove, totalVertices); } progress.OnComplete("Ended remeshing"); }
private void ProcessUpdatedExhibits(IProgressListener listener, FetchedMediaData fetchedMedia, ITransactionDataAccess dataAccess) { var exhibits = dataAccess.Exhibits().GetExhibits().ToDictionary(x => x.IdForRestApi); foreach (var exhibitDto in updatedExhibits) { var dbExhibit = exhibits[exhibitDto.Id]; ExhibitConverter.Convert(exhibitDto, dbExhibit); AddImageToExhibit(dbExhibit, exhibitDto.Image, fetchedMedia); //TODO: Check if exhibit was already downloaded //if(dbExhibit.DetailsDataLoaded) //{ // IoCManager.Resolve<INewDataCenter>().AddExhibitToBeUpdated(dbExhibit); //} var removedPages = dbExhibit.Pages.Where(x => !exhibitDto.Pages.Contains(x.IdForRestApi)); foreach (var page in removedPages) { dbExhibit.Pages.Remove(page); } listener.ProgressOneStep(); } }
public void ProcessExhibits(IProgressListener listener, ITransactionDataAccess dataAccess, Dictionary <MediaDto, string> mediaToFilePath) { var fetchedMedia = mediaDataFetcher.CombineMediasAndFiles(dataAccess, mediaToFilePath); ProcessUpdatedExhibits(listener, fetchedMedia, dataAccess); ProcessNewExhibits(listener, fetchedMedia, dataAccess); }
public void downlod(List <Bundle> bundles, IProgressListener progressListener = null) { this.pendingBundles = bundles; this.progressListener = progressListener; this.completed = false; this.downloading = false; this.currentBundle = null; for (int i = pendingBundles.Count - 1; i > -1; i--) { Bundle bundle = pendingBundles[i]; if (downloadedBundles.ContainsKey(bundle.name)) { pendingBundles.RemoveAt(i); } else { bundle.completed = false; bundle.started = false; bundle.error = null; bundle.version = versions[bundle.name]; } } totalCount = pendingBundles.Count; completedCount = 0; if (totalCount > 0) { this.enabled = true; } }
public PushAttachmentData(String contentType, Stream data, long dataSize, IOutputStreamFactory outputStreamFactory, IProgressListener listener) { ContentType = contentType; Data = data; DataSize = dataSize; OutputFactory = outputStreamFactory; Listener = listener; }
protected override bool SubscribeProgressIfWaiterAndContinueLoop(ref IProgressListener progressListener, out Promise previous, ref ValueLinkedStack <PromisePassThrough> passThroughs) { if (_state != State.Pending) { previous = null; return(false); } return(SubscribeProgressAndContinueLoop(ref progressListener, out previous)); }
public async Task FetchFullDownloadableDataIntoDatabase( string routeId, int idForRestApi, CancellationToken token, IProgressListener listener) { routeDto = (await routesApiAccess.GetRoutes(new List <int> { idForRestApi })).Items.First(); if (token.IsCancellationRequested) { return; } route = DbManager.DataAccess.Routes().GetRoute(routeId); pagesAndMediaForMissingExhibits = new List <ExhibitPagesAndMediaContainer>(); var allMissingExhibits = DbManager.DataAccess.Exhibits().GetExhibits().ToList().FindAll(x => !x.DetailsDataLoaded); // Exhibits not fully loaded yet missingExhibitsForRoute = allMissingExhibits.ToList().FindAll(x => routeDto.Exhibits.Contains(x.IdForRestApi)); // Select those part of the route double totalSteps = FetchNeededMediaForFullRoute(); foreach (var exhibit in missingExhibitsForRoute) // Fetch media for missing exhibits and save them for later download { var pagesAndRequiredMediaForExhibit = await fullExhibitDataFetcher.FetchPagesAndMediaForExhibitFromRouteFetcher(exhibit.IdForRestApi); if (token.IsCancellationRequested) { return; } pagesAndMediaForMissingExhibits.Add(pagesAndRequiredMediaForExhibit); totalSteps += pagesAndRequiredMediaForExhibit.RequiredMedia.Count; } listener.SetMaxProgress(totalSteps); await AddFullExhibitsToRoute(route, token, listener); // Download all missing exhibits if (token.IsCancellationRequested) { return; } await FetchMediaData(token, listener); var mediaToFilePath = await mediaDataFetcher.WriteMediaToDiskAsync(); DbManager.InTransaction(transaction => { var dataAccess = transaction.DataAccess; ProcessRoute(token, dataAccess, mediaToFilePath); // Download audio if (token.IsCancellationRequested) { transaction.Rollback(); } }); }
private void ProcessNewExhibits(IProgressListener listener, FetchedMediaData fetchedMedia, ITransactionDataAccess dataAccess) { foreach (var exhibitDto in newExhibits) { var dbExhibit = ExhibitConverter.Convert(exhibitDto); AddImageToExhibit(dbExhibit, exhibitDto.Image, fetchedMedia); dataAccess.Exhibits().AddExhibit(dbExhibit); listener.ProgressOneStep(); } }
public void Process(ref Mesh mesh, double targetRatio, IProgressListener listener = null) { if ((targetRatio <= 0.0) || (targetRatio > 1.0)) { throw new ArgumentOutOfRangeException("targetRatio"); } int targetTriangles = (int)(mesh.Faces.Count * targetRatio); Process(ref mesh, targetTriangles, listener); }
public SignalServiceAttachmentStream(Stream inputStream, String contentType, long length, string fileName, bool voiceNote, byte[] preview, int width, int height, IProgressListener listener) : base(contentType) { InputStream = inputStream; Length = length; FileName = fileName; Listener = listener; VoiceNote = voiceNote; Preview = preview; Width = width; Height = height; }
/// <summary> /// Remeshes specified mesh. /// </summary> /// <param name="mesh">The mesh to remesh</param> /// <param name="toRemove">The number of triangles to remove.</param> /// <param name="progress">The progress listener.</param> private void Remesh(ref Mesh mesh, int toRemove, IProgressListener progress = null) { if (!(toRemove > mesh.Triangles.Count && mesh.Triangles.Count > 10)) { throw new ArgumentOutOfRangeException("toRemove", toRemove, "Invalid triangle count"); } progress.OnStart("Remeshing using AngleSum Error Metric"); var triangles = mesh.Triangles; var vertices = mesh.Vertices; if (triangles.Count <= toRemove) { progress.OnComplete("Failed. Too many triangles to remove"); } //int toRemove = (int)((m_Removed) * triangles.Count); int triangleLimit = triangles.Count - toRemove; foreach (var v in vertices) { UpdateVertexCost(v); } #if false // Adding mesh border penalty. foreach (var v in vertices) { // Border vertices has no more that 5 neighbors if (v.Neighbors.Count <= 4) { v.Cost += 1.0; } } #endif int index = 0; while (triangles.Count > triangleLimit) { var min = mesh.Vertices.Min(); if (mesh.JoinToNearestByCost(min, Mesh.JoinPositionType.Source)) { UpdateVertexCost(min); UpdateVertexNeighborsCost(min); progress.OnProgress(vertices.Count, triangles.Count); index += 2; } } progress.OnComplete("End of remeshing using AngleSum Error Metric"); }
/// <summary> /// Updates vertex normals and face planes. /// </summary> public void Invalidate(IProgressListener listener = null, InvalidateFlags invalidate = InvalidateFlags.All) { if (invalidate.HasFlag(InvalidateFlags.Faces)) { if (listener != null) { listener.OnStarted("Invalidating mesh faces"); } foreach (var face in m_Faces) { var v0 = m_Vertices[face[0]].Position; var v1 = m_Vertices[face[1]].Position; var v2 = m_Vertices[face[2]].Position; face.Plane = new Plane(v0, v1, v2); } if (listener != null) { listener.OnComplete("Invalidating mesh faces"); } } if (invalidate.HasFlag(InvalidateFlags.Vertices)) { if (listener != null) { listener.OnStarted("Invalidating mesh vertices"); } int i = 0; foreach (var vertex in m_Vertices) { foreach (var face in m_Faces) { if (face.HasVertex(vertex.Key)) { vertex.Value.Normal += face.Plane.Normal; } } if (listener != null) { listener.OnStep(++i, m_Vertices.Count); } vertex.Value.Normal.Normalize(); } if (listener != null) { listener.OnComplete("Invalidating mesh vertices"); } } }
public ProgressMeter(long totalAmount, IProgressListener progressListener) { this.totalAmount = totalAmount; this.progressListener = progressListener; // Corrige(seta o valor default) caso o valor fornecido seja inválido if (totalAmount <= 0) { this.totalAmount = 100; } progressListener.ProgressInitialized(); // Avisa o listener }
public ReferenceNode GetRootReferenceTree(IProgressListener listener, int type) { PathTree ptree = GetRoots(listener, type); if (ptree == null) { return(null); } ReferenceNode nod = new ReferenceNode(this, type, ptree); nod.Flush(); return(nod); }
private void ProcessNewRoutes(IProgressListener listener, ITransactionDataAccess dataAccess) { foreach (var routeDto in newRoutes) { var dbRoute = RouteConverter.Convert(routeDto); AddImageToRoute(dbRoute, routeDto.Image, fetchedMedia); AddTagsToRoute(dbRoute, routeDto, fetchedMedia); AddExhibitsToRoute(dbRoute, routeDto, dataAccess); dataAccess.Routes().AddRoute(dbRoute); listener.ProgressOneStep(); } }
public UpdateRunner(ReaderManager reader, UpdateConfig config, IProgressListener progressListener) { // Check that pilot tag selection is valid if (config.PilotSelectionStrategy == PilotTagSelection.FixedTag) { if (config.TargetTags.Values.First(a => a.TagId == 0xAA00) == null) { throw new Exception("`Fixed tag` used for Pilot tag selection, but no fixed tag was found"); } } this.reader = reader; this.config = config; this.progress = progressListener; this.tagStates = new TagStateUpdater(reader); }
public void WriteMesh(ref Mesh mesh, IProgressListener listener = null) { long current = 0; long total = mesh.Vertices.Count + mesh.Faces.Count; listener.OnStarted("Mesh write"); foreach (var vertex in mesh.Vertices) { m_Writer.WriteLine(string.Format( CultureInfo.InvariantCulture, "v {0} {1} {2}", vertex.Value.Position.X.ToString("0.000000", CultureInfo.InvariantCulture), vertex.Value.Position.Y.ToString("0.000000", CultureInfo.InvariantCulture), vertex.Value.Position.Z.ToString("0.000000", CultureInfo.InvariantCulture))); ++current; if (listener != null) { listener.OnStep(current, total); } } int count = 0; foreach (var face in mesh.Faces) { m_Writer.WriteLine(string.Format(CultureInfo.InvariantCulture, "f {0} {1} {2}", face[0], face[1], face[2])); ++count; ++current; if (listener != null) { listener.OnStep(current, total); } } if (listener != null) { listener.OnComplete("Mesh write"); } m_Writer.Close(); }
// Returns a list of paths. Each path is a sequence of objects, starting // on an object of type 'type' and ending on a root. public PathTree GetRoots(IProgressListener listener, int type) { RootInfo rootInfo = new RootInfo(); PathTree pathTree = new PathTree(this); foreach (int obj in GetObjectsByType(type)) { rootInfo.BaseObjects [obj] = obj; } int nc = 0; foreach (int obj in GetObjectsByType(type)) { if (listener.Cancelled) { return(null); } rootInfo.nc = 0; FindRoot(rootInfo, pathTree, obj); // Register partial paths to the root, to avoid having to // recalculate them again // if (nc % 100 == 0) // Console.WriteLine ("NC: " + nc + " " + rootInfo.Roots.Count); pathTree.AddBaseObject(obj); foreach (KeyValuePair <int, int[]> e in rootInfo.Roots) { pathTree.AddPath(e.Value); } rootInfo.Visited.Clear(); rootInfo.Roots.Clear(); nc++; double newp = (double)nc / (double)rootInfo.BaseObjects.Count; listener.ReportProgress("Looking for roots", newp); } pathTree.Flush(); return(pathTree); }
public void Process(ref Mesh mesh, int targetTriangles, IProgressListener listener = null) { if ((targetTriangles <= 0) || (targetTriangles > mesh.Faces.Count)) { throw new ArgumentOutOfRangeException("targetTriangles"); } Clear(); m_Vertices = mesh.Vertices; m_Faces = mesh.Faces; ComputeInitialQuadrics(); Contract(targetTriangles, listener); mesh.Vertices = m_Vertices; mesh.Faces = m_Faces; }
public static void UpdateDatabase(IProgressListener listener = null) { if (DataAccess.GetVersion() < DbDummyDataFiller.DatabaseVersion) { DataAccess.DeleteDatabase(); DataAccess.CreateDatabase(DbDummyDataFiller.DatabaseVersion); DbDummyDataFiller dbDataFiller = new DbDummyDataFiller(); if (listener != null) { dbDataFiller.ProgressChanged += listener.UpdateProgress; } dbDataFiller.InsertData(); Settings.DatabaseVersion = DbDummyDataFiller.DatabaseVersion; if (listener != null) { dbDataFiller.ProgressChanged -= listener.UpdateProgress; } } }
protected override bool SubscribeProgressAndContinueLoop(ref IProgressListener progressListener, out Promise previous) { // This is guaranteed to be pending. bool firstSubscribe = _progressListeners.IsEmpty; progressListener.Retain(); _progressListeners.Push(progressListener); previous = _valueOrPrevious as Promise; if (_secondPrevious) { if (!firstSubscribe) { return(false); } // Subscribe this to the returned promise. progressListener = this; } return(previous != null); }
private async Task AddFullExhibitsToRoute(Route r, CancellationToken token, IProgressListener listener) { foreach (var waypoint in r.Waypoints) { var dbExhibit = missingExhibitsForRoute.SingleOrDefault(x => x.IdForRestApi == waypoint.Exhibit.IdForRestApi); if (dbExhibit == null) { continue; } var pagesAndMediaContainerForExhibit = pagesAndMediaForMissingExhibits.SingleOrDefault(x => x.ExhibitIdForRestApi == dbExhibit.IdForRestApi); await fullExhibitDataFetcher.FetchFullExhibitDataIntoDatabaseWithFetchedPagesAndMedia(dbExhibit.Id, pagesAndMediaContainerForExhibit, token, listener, dbExhibit.IdForRestApi); if (token.IsCancellationRequested) { return; } pagesAndMediaForMissingExhibits.Remove(pagesAndMediaContainerForExhibit); } }
private void ProcessUpdatedRoutes(IProgressListener listener, ITransactionDataAccess dataAccess) { var routes = dataAccess.Routes().GetRoutes().ToList(); foreach (var routeDto in updatedRoutes) { var dbRoute = routes.First(x => x.IdForRestApi == routeDto.Id); RouteConverter.Convert(routeDto, dbRoute); AddImageToRoute(dbRoute, routeDto.Image, fetchedMedia); AddTagsToRoute(dbRoute, routeDto, fetchedMedia); AddExhibitsToRoute(dbRoute, routeDto, dataAccess); if (dbRoute.DetailsDataLoaded) { IoCManager.Resolve <INewDataCenter>().AddRouteToBeUpdated(dbRoute); } listener.ProgressOneStep(); } }
public void Apply(ref VoxelModel model, IProgressListener progress) { var m = model; progress?.Report("Analyzing structure"); var ext = new ExteriorAnalyzer() { Model = m }.Analyze(new ProgressMapper(progress, 0.0, 1.0 / 3.0, null)); progress?.Report("Creating shell"); var extexpanded = new DilationFilter() { Distance = Distance, DistanceType = DistanceType }.Apply(ext, new ProgressMapper(progress, 1.0 / 3.0, 1.0 / 3.0, null)); progress?.Report("Removing invisible voxels"); int d1 = m.Width; int d2 = m.Height; int d3 = m.Depth; int d = IsExteriorSolid ? 0 : Distance; for (int x = d; x < d1 - d; ++x) { for (int y = d; y < d2 - d; ++y) { for (int z = d; z < d3 - d; ++z) { if (!extexpanded[x, y, z]) { m[x, y, z] = VoxelModel.EmptyVoxel; } } } progress?.Report((double)(x - d) / (d1 - d * 2) * (1.0 / 3.0) + 2.0 / 3.0); } }
public void RunAll(String scriptsDirectory, IProgressListener progressListener) { listener.NotifyObject("Origem: [DatabaseScripts] Destino(database): " + sqlConnection.Database); String path = PathFormat.Adjust(scriptsDirectory); List <String> scriptList = new List <String>(); TextReader textReader = new StreamReader(path + "ExecutionOrder.txt"); String line = ""; while (line != null) { line = textReader.ReadLine(); if (line != null) { scriptList.Add(line); } } textReader.Close(); scriptsExecuted = 0; progressMeter = new ProgressMeter(scriptList.Count, progressListener); foreach (String script in scriptList) { currentScript = script; ContainedFile file = containerHandler.ExtractFromContainer(path + "ScriptFiles.xml", script); if (file == null) { throw new Exception("Script não encontrado no XML: " + script); } ExecuteQuery(file.fileContent); scriptsExecuted++; progressMeter.IncreaseProgress(1); } }
/// <summary> /// Download a file given its blob ID. /// </summary> /// <param name="blobId">The blob ID of the file</param> /// <param name="progressListener">An object that will receive progress information, or null</param> /// <returns>Encrypted file data</returns> public byte[] DownloadFile(byte[] blobId, IProgressListener progressListener) { string queryString = MakeUrlEncoded(MakeRequestParams()); Uri blobUrl = new Uri(string.Format(this.apiUrl + "blobs/{0}?{1}", DataUtils.ByteArrayToHexString(blobId), queryString)); byte[] blob; WebRequest request = WebRequest.CreateHttp(blobUrl); request.Method = "GET"; request.Timeout = 20 * 1000; using (WebResponse response = request.GetResponse()) using (Stream stream = response.GetResponseStream()) { blob = DataUtils.StreamToBytes(stream, progressListener); stream.Close(); response.Close(); } return(blob); }
private void Contract(int targetTriangles, IProgressListener listener = null) { SelectValidPairs(); if (listener != null) { listener.OnStarted("Compacting"); } int totalTriangles = m_Faces.Count - targetTriangles; int currentTriangle = 0; while (m_Faces.Count > targetTriangles) { if (listener != null) { listener.OnStep(currentTriangle, totalTriangles); } ++currentTriangle; double minError = (double)int.MaxValue; //KeyValuePair<VertexPair, double> min; VertexPair minPair = new VertexPair() { First = 0, Second = 0 }; foreach (KeyValuePair<VertexPair, double> e in m_Errors) { if (e.Value < minError) { minError = e.Value; minPair = e.Key; } } Vector3 error; ComputeError(minPair.First, minPair.Second, out error); #if false VertexSplit split = new VertexSplit(); //var fv split.First.Position = m_Vertices[minPair.First].Position; split.Second.Position = m_Vertices[minPair.Second].Position; split.Target.Position = error; m_Splits.Add(split); #endif var vertex = m_Vertices[minPair.First]; vertex.Position = error; m_Quadrics[minPair.First] = m_Quadrics[minPair.First] + m_Quadrics[minPair.Second]; for (int i = m_Faces.Count - 1; i != 0; ) { var face = m_Faces[i]; for (int j = 0; j < 3; ++j) { if (face[j] == minPair.Second) { if (face[0] == minPair.First || face[1] == minPair.First || face[2] == minPair.First) { m_Faces.Remove(face); } else { face[j] = minPair.First; } --i; break; } else if (j == 2) { --i; } } } m_Vertices.Remove(minPair.Second); KeyValuePair<VertexPair, double> pair; #if false for (int iter = m_Errors.Count - 1; iter != 0; ) { pair = m_Errors.ElementAt(iter); if (pair.Key.First == minPair.Second && pair.Key.Second != minPair.First) { m_Errors.Remove(m_Errors.ElementAt(iter).Key); m_Errors.Add( new VertexPair() { First = Math.Min(minPair.First, pair.Key.Second), Second = Math.Max(minPair.First, pair.Key.Second) }, 0.0); --iter; } else if (pair.Key.Second == minPair.Second && pair.Key.First != minPair.First) { m_Errors.Remove(m_Errors.ElementAt(iter).Key); m_Errors.Add( new VertexPair() { First = Math.Min(minPair.First, pair.Key.First), Second = Math.Max(minPair.First, pair.Key.First) }, 0.0); --iter; } else { --iter; } } #else for (int it = 0; it < m_Errors.Count; ++it) { pair = m_Errors.ElementAt(it); if (pair.Key.First == minPair.Second && pair.Key.Second != minPair.First) { m_Errors.Remove(m_Errors.ElementAt(it).Key); var key = new VertexPair() { First = Math.Min(minPair.First, pair.Key.Second), Second = Math.Max(minPair.First, pair.Key.Second) }; if (!m_Errors.ContainsKey(key)) { m_Errors.Add( key, 0.0); } } else if (pair.Key.Second == minPair.Second && pair.Key.First != minPair.First) { m_Errors.Remove(m_Errors.ElementAt(it).Key); var key = new VertexPair() { First = Math.Min(minPair.First, pair.Key.First), Second = Math.Max(minPair.First, pair.Key.First) }; if (!m_Errors.ContainsKey(key)) { m_Errors.Add( key, 0.0); } } } #endif m_Errors.Remove(minPair); for (int it = 0; it < m_Errors.Count; ++it) { var key = m_Errors.ElementAt(it).Key; if (key.First == minPair.First) { m_Errors[key] = ComputeError(minPair.First, key.Second); } if (key.Second == minPair.First) { m_Errors[key] = ComputeError(minPair.First, key.First); } } /*foreach (var e in m_Errors) { var p = e.Key; if (p.First == minPair.First) { m_Errors[p] = ComputeError(minPair.First, p.Second); } if (p.Second == minPair.First) { m_Errors[p] = ComputeError(minPair.First, p.First); } }*/ } if (listener != null) { listener.OnComplete("Compacting"); } }
// // Code to read the log files generated at runtime // private void ReadLogFile(IProgressListener progress) { BufferHeader bheader; long start_position = reader.Position; long last_pct = 0; if (header == null) header = Header.Read (reader); if (header == null) return; reader.Header = header; while (!reader.IsEof) { // We check if we must cancel before reading more data (and after processing all the data we've read). // This way we don't cancel in the middle of event processing (since we store data at class level // we may end up with corruption the next time we read the same buffer otherwise). if (progress != null) { if (progress.Cancelled) return; long pct = (reader.Position - start_position) * 100 / (reader.Length - start_position); if (pct != last_pct) { last_pct = pct; progress.ReportProgress ("Loading profiler log", pct / 100.0f); } } bheader = BufferHeader.Read (reader); if (bheader == null) { // entire buffer isn't available (yet) return; } //Console.WriteLine ("BUFFER ThreadId: " + bheader.ThreadId + " Len:" + bheader.Length); currentObjBase = bheader.ObjBase; currentPtrBase = bheader.PtrBase; while (!reader.IsBufferEmpty) { MetadataEvent me; HeapEvent he; GcEvent ge; Event e = Event.Read (reader); if ((me = e as MetadataEvent) != null) ReadLogFileChunk_Type (me); else if ((he = e as HeapEvent) != null) ReadLogFileChunk_Object (he); else if ((ge = e as GcEvent) != null) ReadGcEvent (ge); } } }
public void Save(MeshSlices slices, Bitmap texture, string path, IProgressListener progress) { var name = System.IO.Path.GetFileNameWithoutExtension(path); var mtlname = name + ".mtl"; var imgname = name + ".png"; var dirname = System.IO.Path.GetDirectoryName(System.IO.Path.GetFullPath(path)); progress?.Report("Opening the output file"); progress?.Report(0); using (var writer = System.IO.File.CreateText(path)) { progress?.Report("Writing headers"); writer.WriteLine($"mtllib {mtlname}"); writer.WriteLine("o Object"); progress?.Report("Writing position"); int numTotalSlices = slices.Select((slicelist) => slicelist.Length).Sum(); int sliceIndex = 0; foreach (var slicelist in slices) { foreach (var slice in slicelist) { foreach (var vt in slice.Positions) { // Usually Y is the upward direction for OBJs writer.WriteLine($"v {vt.X} {-vt.Z} {vt.Y}"); } ++sliceIndex; progress?.Report((double)sliceIndex / numTotalSlices * (1.0 / 3.0)); } } progress?.Report("Writing UV coordinates"); sliceIndex = 0; foreach (var slicelist in slices) { foreach (var slice in slicelist) { foreach (var uv in slice.UVs) { writer.WriteLine($"vt {uv.X / texture.Width} {1f - uv.Y / texture.Height}"); } ++sliceIndex; progress?.Report((double)sliceIndex / numTotalSlices * (1.0 / 3.0) + (1.0 / 3.0)); } } writer.WriteLine("usemtl Material"); writer.WriteLine("s off"); progress?.Report("Writing faces"); int vtxidx = 1; sliceIndex = 0; foreach (var slicelist in slices) { foreach (var slice in slicelist) { foreach (var f in slice.MeshSliceFaces) { writer.Write("f"); for (int i = f.StartIndex; i < f.EndIndex; ++i) { writer.Write($" {vtxidx + i}/{vtxidx + i}"); } writer.WriteLine(); } vtxidx += slice.Positions.Length; ++sliceIndex; progress?.Report((double)sliceIndex / numTotalSlices * (1.0 / 3.0) + (2.0 / 3.0)); } } } // using writer progress?.Report("Saving material"); using (var writer = System.IO.File.CreateText(System.IO.Path.Combine(dirname, mtlname))) { writer.WriteLine("newmtl Material"); writer.WriteLine("Ka 0 0 0"); writer.WriteLine("Kd 1 1 1"); writer.WriteLine("Ks 0.2 0.2 0.2"); writer.WriteLine("Ni 1"); writer.WriteLine("d 1"); writer.WriteLine("illum 2"); writer.WriteLine($"map_Kd {imgname}"); } progress?.Report("Saving texture"); texture.Save(System.IO.Path.Combine(dirname, imgname), System.Drawing.Imaging.ImageFormat.Png); }
public void GenerateTextureAndUV(VoxelModel model, MeshSlices slices, out Bitmap bitmap, IProgressListener progress) { // Collect colors var colors = new List<int>(); // Marshal.Copy doesn't support uint[] lol int totalSlices = 0; foreach (var slicelist in slices) { totalSlices += slicelist.Length; } int sliceIndex = 0; progress?.Report("Collecting colors"); foreach (var slicelist in slices) { foreach (var slice in slicelist) { ++sliceIndex; progress?.Report((double)sliceIndex / totalSlices); var verts = slice.Positions; Axis3 paxis1, paxis2; GetPerpendicularAxises(slice.Axis, out paxis1, out paxis2); var pt = new IntVector3(); pt[slice.Axis] = slice.Layer; foreach (var face in slice.MeshSliceFaces) { var scoord = FindSliceCoordForFace(slice, face, slice.Axis, paxis1, paxis2); pt[paxis1] = scoord.X; pt[paxis2] = scoord.Y; colors.Add((int) (model[pt] | 0xff000000)); } } } // Determine the dimensions of the texture int texwidth = (int)Math.Ceiling(Math.Sqrt(colors.Count)); int texheight = (colors.Count + texwidth - 1) / texwidth; // And then create the texture bitmap = new Bitmap(texwidth * 2, texheight * 2, System.Drawing.Imaging.PixelFormat.Format32bppRgb); var bmpdata = bitmap.LockBits(new Rectangle(0, 0, bitmap.Width, bitmap.Height), System.Drawing.Imaging.ImageLockMode.WriteOnly, System.Drawing.Imaging.PixelFormat.Format32bppRgb); System.Runtime.InteropServices.Marshal.Copy(Scale2x(colors.ToArray(), texwidth, texheight), 0, bmpdata.Scan0, colors.Count * 4); bitmap.UnlockBits(bmpdata); // Assign UVs int faceu = 0, facev = 0; sliceIndex = 0; progress?.Report("Assigning UV coordinates"); foreach (var slicelist in slices) { foreach (var slice in slicelist) { ++sliceIndex; progress?.Report((double)sliceIndex / totalSlices); var verts = slice.Positions; var uvs = slice.UVs = new Vector2[slice.Positions.Length]; Axis3 paxis1, paxis2; GetPerpendicularAxises(slice.Axis, out paxis1, out paxis2); foreach (var face in slice.MeshSliceFaces) { var scoord = FindSliceCoordForFace(slice, face, slice.Axis, paxis1, paxis2); var uv = new Vector2((float) (faceu << 1) + 0.5f, (float) (facev << 1) + 0.5f); for (int i = face.StartIndex; i < face.EndIndex; ++i) { var vt = verts[i]; float u = uv.X + (float)(vt[paxis1] - scoord.X); float v = uv.Y + (float)(vt[paxis2] - scoord.Y); uvs[i] = new Vector2(u, v); } faceu += 1; if (faceu == texwidth) { faceu = 0; facev += 1; } } } } }
public void Process(ref Mesh mesh, double ratio, IProgressListener listener = null) { Process(ref mesh, (int)(mesh.Triangles.Count * (1.0 - ratio)), listener); }
public void Apply(ref VoxelModel model, IProgressListener progress) { var m = model; progress?.Report("Analyzing structure"); var ext = new ExteriorAnalyzer() { Model = m }.Analyze(new ProgressMapper(progress, 0, 1.0 / 3.0, null)); // Find the initial points (solid voxels adjacent to interior empty voxels) progress?.Report("Planting seeds"); var queue = new Queue<IntVector3>(); int width = m.Width, height = m.Height, depth = m.Depth; int numVoxelsToProcess = 0; for (int x = 0; x < width; ++x) { for (int y = 0; y < height; ++y) { for (int z = 0; z < depth; ++z) { if (!ext[x, y, z] && !model.IsVoxelSolid(x, y, z)) { ++numVoxelsToProcess; } if (!model.IsVoxelSolid(x, y, z)) { continue; } queue.Enqueue(new IntVector3(x, y, z)); } } progress?.Report((double)(x + 1) / width * (1.0 / 3.0) + (1.0 / 3.0)); } numVoxelsToProcess += queue.Count; progress?.Report("Filling inside"); int numProcessed = 0; while (queue.Count > 0) { ++numProcessed; if ((numProcessed & 2047) == 0) { progress?.Report((double)numProcessed / numVoxelsToProcess * (1.0 / 3.0) + (2.0 / 3.0)); } var p = queue.Dequeue(); uint color = m[p]; if (p.X > 0) { Traverse(p.X - 1, p.Y, p.Z, m, ext, queue, color); } if (p.Y > 0) { Traverse(p.X, p.Y - 1, p.Z, m, ext, queue, color); } if (p.Z > 0) { Traverse(p.X, p.Y, p.Z - 1, m, ext, queue, color); } if (p.X < width - 1) { Traverse(p.X + 1, p.Y, p.Z, m, ext, queue, color); } if (p.Y < height - 1) { Traverse(p.X, p.Y + 1, p.Z, m, ext, queue, color); } if (p.Z < depth - 1) { Traverse(p.X, p.Y, p.Z + 1, m, ext, queue, color); } } }
public VoxelModel LoadVoxelModel(System.IO.Stream stream, out Vector3 pivot, IProgressListener progress) { var reader = new System.IO.BinaryReader(stream); { var buf = new byte[4]; if (stream.Read(buf, 0, 4) < 4) { throw new System.IO.IOException("Magic not read"); } if (buf[0] != 'K' || buf[1] != 'v' || buf[2] != 'x' || buf[3] != 'l') { throw new System.IO.IOException("Invalid magic"); } } int xsiz = reader.ReadInt32(); int ysiz = reader.ReadInt32(); int zsiz = reader.ReadInt32(); float xpivot = reader.ReadSingle(); float ypivot = reader.ReadSingle(); float zpivot = reader.ReadSingle(); int numblocks = reader.ReadInt32(); var blocks = new Kv6Block[numblocks]; progress?.Report("Reading voxels"); for (int i = 0; i < blocks.Length; ++i) { blocks[i].color = reader.ReadUInt32(); blocks[i].zpos = (int) reader.ReadUInt16(); reader.ReadUInt16(); // skip visFaces & lighting if (((i & 8191) == 0)) { progress?.Report((double)i / blocks.Length * 0.5); } } var xyoffset = new int[xsiz * ysiz]; // skip xoffset for (int i = 0; i < xsiz; ++i) { reader.ReadInt32(); } for (int i = 0; i < xyoffset.Length; ++i) { xyoffset[i] = (int) reader.ReadUInt16(); } progress?.Report("Placing voxels"); int pos = 0; var model = new VoxelModel(xsiz, ysiz, zsiz); for (int x = 0; x < xsiz; ++x) { for (int y = 0; y < ysiz; ++y) { int sb = xyoffset[x * ysiz + y]; for (int i = 0; i < sb; ++i) { var b = blocks[pos]; model[x, y, b.zpos] = b.color; pos += 1; } } progress?.Report((double)pos / blocks.Length * 0.5 + 0.5); } pivot = new Vector3(xpivot, ypivot, zpivot); return model; }
public void Update() { if (loading) { //loading into memory process for (int i = loadingBundles.Count - 1; i > -1; i--) { Bundle bundle = loadingBundles[i]; if (bundle.www.isDone) { loadedBundles[bundle.name] = bundle; loadingBundles.RemoveAt(i); if (loadingScene) { bundle.sceneBundle = bundle.www.assetBundle; } } } loading = loadingBundles.Count > 0; if (!loading) { this.enabled = checkPending; if (this.loadingScene) { this.loadingScene = false; OnSceneLoaded callback = this.onSceneLoaded; this.onSceneLoaded = null; if (callback != null) { callback(); } } else { OnBundleLoaded callback = this.onBundleLoaded; this.onBundleLoaded = null; if (callback != null) { callback(); } } if (needNotifyPending) { notifyPending(); } } } else if (checkPending) { checkPending = false; loadPending(); } else { //downloading process if (pendingBundles == null) { return; } if (!downloading) { for (int i = pendingBundles.Count - 1; i > -1; i--) { Bundle bundle = pendingBundles[i]; if (bundle.completed) { pendingBundles.RemoveAt(i); completedCount++; } else if (!bundle.started) { currentBundle = bundle; currentBundle.started = true; downloading = true; StartCoroutine(downloadBundle(currentBundle)); break; } } } completed = pendingBundles.Count == 0; //notify progress listener if any if (progressListener != null) { //current single bundle download progress float currentBundleProgress = 0; if (currentBundle != null && currentBundle.www != null) { currentBundleProgress = currentBundle.www.progress; } else if (completed) { currentBundleProgress = 1f; totalCount = completedCount; } progressListener.onProgress(totalCount, completedCount, currentBundleProgress); if (completed) { IProgressListener listener = progressListener; progressListener = null; StartCoroutine(notifyCompleted(listener)); } } } }
public bool[,,] Analyze(IProgressListener progress) { int width = Model.Width; int height = Model.Height; int depth = Model.Depth; exterior = new bool[width, height, depth]; queue = new Queue<IntVector3>(); var model = this.Model; // Start the scan from the boundary for (int x = 0; x < width; ++x) { for (int y = 0; y < height; ++y) { Traverse(x, y, 0); Traverse(x, y, depth - 1); } } for (int x = 0; x < width; ++x) { for (int z = 0; z < depth; ++z) { Traverse(x, 0, z); Traverse(x, height - 1, z); } } for (int y = 0; y < height; ++y) { for (int z = 0; z < depth; ++z) { Traverse(0, y, z); Traverse(width - 1, y, z); } } int numProcessed = 0; while (queue.Count > 0) { var p = queue.Dequeue(); if (p.X > 0) { Traverse(p.X - 1, p.Y, p.Z); } if (p.X < width - 1) { Traverse(p.X + 1, p.Y, p.Z); } if (p.Y > 0) { Traverse(p.X, p.Y - 1, p.Z); } if (p.Y < height - 1) { Traverse(p.X, p.Y + 1, p.Z); } if (p.Z > 0) { Traverse(p.X, p.Y, p.Z - 1); } if (p.Z < depth - 1) { Traverse(p.X, p.Y, p.Z + 1); } ++numProcessed; // this might move the progress bar in a funny way but // we can't do better since we don't know how many exterior voxels are there yet progress?.Report((double)numProcessed / (numProcessed + queue.Count)); } var ret = exterior; exterior = null; return ret; }
public VoxelModel LoadVoxelModel(byte[] bytes, out Vector3 pivot, IProgressListener progress) { return LoadVoxelModel(new System.IO.MemoryStream(bytes, false), out pivot, progress); }
public void Process(ref Mesh mesh, int toRemove, IProgressListener listener = null) { Remesh(ref mesh, toRemove, listener); }
public void Read(IProgressListener progress) { Stopwatch watch = new Stopwatch (); watch.Start (); try { if (!File.Exists (name)) return; DateTime tim = File.GetLastWriteTime (name); if (tim == timestamp) return; timestamp = tim; if (reader == null) reader = new LogFileReader (name); ReadLogFile (progress); } catch (Exception ex) { Console.WriteLine (ex); } finally { watch.Stop (); Console.WriteLine ("ObjectMapFileReader.Read (): Completed in {0} s", watch.ElapsedMilliseconds / (double) 1000); } }
public virtual void Read(out Mesh mesh, IProgressListener listener = null) { mesh = new Mesh(); Regex r = new Regex(@" |//"); NumberStyles numberStyle = NumberStyles.Float; IFormatProvider numberFormatProvider = CultureInfo.InvariantCulture; if (listener != null) { listener.OnStarted("Load mesh"); } int indicesCount = 0; while (m_Reader.Peek() >= 0) { string line = m_Reader.ReadLine(); String[] elements = r.Split(line); // List<Vertex> normals; switch (elements[0]) { case "v": { float x, y, z; if ( float.TryParse(elements[1], numberStyle, numberFormatProvider, out x) && float.TryParse(elements[2], numberStyle, numberFormatProvider, out y) && float.TryParse(elements[3], numberStyle, numberFormatProvider, out z) ) { mesh.Vertices.Add(++indicesCount, new Vertex(new Vector3(x, y, z))); } else { Trace.WriteLine(line); } break; } case "f": { int f1, f2, f3; int f1Index = 1; int f2Index = 2; int f3Index = 3; switch (elements.Length) { case 7: { //normal indexes in elements[2],elements[4] and elements[6] are ignored; f1Index = 1; f2Index = 3; f3Index = 5; goto case 4; } case 4: { if ( int.TryParse(elements[f1Index], numberStyle, numberFormatProvider, out f1) && int.TryParse(elements[f2Index], numberStyle, numberFormatProvider, out f2) && int.TryParse(elements[f3Index], numberStyle, numberFormatProvider, out f3) ) { mesh.Faces.Add(new Triangle(f1, f2, f3)); } else { Trace.WriteLine(line); throw new NotImplementedException("Only triangles are Implemented. Faces in file are not a triangles.That is bad:("); } } break; default: Trace.WriteLine("Invalid number of components"); break; } break; } case "vn": { break; } default: Trace.WriteLine("Unknown obj specifier."); break; } if (listener != null) { listener.OnStep( m_Reader.BaseStream.Position, m_Reader.BaseStream.Length); } } if (listener != null) { listener.OnComplete("Mesh loaded successfully"); } mesh.Invalidate(listener, Mesh.InvalidateFlags.Faces); }
public async Task FetchMediaData(CancellationToken token, IProgressListener listener) { await mediaDataFetcher.FetchMedias(requiredExhibitImages, token, listener); }
/// <summary> /// Reads raw mesh. /// </summary> /// <param name="vertices">The list of the vertices.</param> /// <param name="indices">The list of the indices.</param> /// <param name="progress">The optional progress listener.</param> public void ReadMesh(out List<Vertex> vertices, out List<int> indices, IProgressListener progress = null) { vertices = new List<Vertex>(); indices = new List<int>(); Regex r = new Regex(@" |//"); NumberStyles numberStyle = NumberStyles.Float; IFormatProvider numberFormatProvider = CultureInfo.InvariantCulture; progress.OnStart("Loading mesh started..."); while (inputReader.Peek() >= 0) { string line = inputReader.ReadLine(); String[] elements = r.Split(line); // List<Vertex> normals; switch (elements[0]) { case "v": { float x, y, z; if ( float.TryParse(elements[1], numberStyle, numberFormatProvider, out x) && float.TryParse(elements[2], numberStyle, numberFormatProvider, out y) && float.TryParse(elements[3], numberStyle, numberFormatProvider, out z) ) { Vertex w = new Vertex(new Vector3(x, y, z)); vertices.Add(w); } else { Trace.WriteLine(line); } break; } case "f": { int f1, f2, f3; int f1Index = 1; int f2Index = 2; int f3Index = 3; switch (elements.Length) { case 7: { //normal indexes in elements[2],elements[4] and elements[6] are ignored; f1Index = 1; f2Index = 3; f3Index = 5; goto case 4; } case 4: { if ( int.TryParse(elements[f1Index], numberStyle, numberFormatProvider, out f1) && int.TryParse(elements[f2Index], numberStyle, numberFormatProvider, out f2) && int.TryParse(elements[f3Index], numberStyle, numberFormatProvider, out f3) ) { indices.Add(f1 -1); indices.Add(f2 -1); indices.Add(f3 -1); } else { Trace.WriteLine(line); throw new NotImplementedException("Only triangles are Implemented. Faces in file are not a triangles.That is bad:("); } } break; default: Trace.WriteLine("Invalid number of components"); break; } break; } case "vn": { break; } default: Trace.WriteLine("Unknown obj specifier."); break; } if (progress != null) { progress.OnProgress( inputReader.BaseStream.Position, inputReader.BaseStream.Length); } } if (progress != null) { progress.OnComplete("Mesh loaded successfully"); } }
public VoxelModel LoadVoxelModel(byte[] bytes, IProgressListener progress) { uint magic = BitConverter.ToUInt32(bytes, 0); // int version = BitConverter.ToInt32(bytes, 4); if (magic != FourCCs.Vox) { throw new System.IO.IOException("Invalid magic number (wrong file format?)."); } // FIXME: should we check the version number? var mainChunk = Chunk.LoadChunk(new ArraySegment<byte>(bytes, 8, bytes.Length - 8)); if (mainChunk.ChunkID != FourCCs.Main) { throw new System.IO.IOException("File is corrupted. Bad root chunk ID (should be MAIN)."); } Chunk sizeChunk = null; Chunk voxelChunk = null; Chunk paletteChunk = null; foreach (var chunk in mainChunk.Children) { if (chunk.ChunkID == FourCCs.Size) { sizeChunk = chunk; } else if (chunk.ChunkID == FourCCs.Xyzi) { voxelChunk = chunk; } else if (chunk.ChunkID == FourCCs.Rgba) { paletteChunk = chunk; } } if (sizeChunk == null) { throw new System.IO.IOException("File is corrupted. SIZE chunk was not found."); } if (voxelChunk == null) { throw new System.IO.IOException("File is corrupted. XYZI chunk was not found."); } if (paletteChunk == null) { throw new System.IO.IOException("VOX file without a palette (RGBA chunk) is currently not supported."); } // Parse size if (sizeChunk.Contents.Count < 12) { throw new System.IO.IOException("File is corrupted. SIZE chunk is too short."); } int dimX = BitConverter.ToInt32(sizeChunk.Contents.Array, sizeChunk.Contents.Offset); int dimY = BitConverter.ToInt32(sizeChunk.Contents.Array, sizeChunk.Contents.Offset + 4); int dimZ = BitConverter.ToInt32(sizeChunk.Contents.Array, sizeChunk.Contents.Offset + 8); if (dimX <= 0 || dimY <= 0 || dimZ <= 0) { throw new System.IO.IOException("File is corrupted. Bad dimensions."); } // Read palette var palette = new uint[256]; { var paldata = paletteChunk.Contents; if (paldata.Count < 256 * 4) { throw new System.IO.IOException("File is corrupted. RGBA chunk is too short."); } for (int i = 0; i < 255; ++i) { uint r = paldata.Array[paldata.Offset + i * 4]; uint g = paldata.Array[paldata.Offset + i * 4 + 1]; uint b = paldata.Array[paldata.Offset + i * 4 + 2]; palette[i + 1] = b | (g << 8) | (r << 16); } } // Read geometry var model = new VoxelModel(dimX, dimY, dimZ); int numVoxels = BitConverter.ToInt32(voxelChunk.Contents.Array, voxelChunk.Contents.Offset); if (voxelChunk.Contents.Count / 4 < numVoxels + 1) { throw new System.IO.IOException("File is corrupted. XYZI chunk is too short."); } progress?.Report("Reading voxels"); { var data = voxelChunk.Contents; int end = data.Offset + 4 + numVoxels * 4; for (int i = data.Offset + 4; i < end; i += 4) { int x = data.Array[i]; int y = data.Array[i + 1]; int z = data.Array[i + 2]; int color = data.Array[i + 3]; if (x < 0 || x >= dimX || y < 0 || y >= dimY || z < 0 || z >= dimZ) { throw new System.IO.IOException("File is corrupted. Voxel location is out of bounds."); } model[x, y, z] = palette[color]; if (((i & 8191) == 0)) { progress?.Report((double)(i - data.Offset) / (double)(numVoxels * 4)); } } } return model; }
public VoxelModel LoadVoxelModel(byte[] bytes, IProgressListener progress) { int w = Width, h = Height, d = Depth; var model = new VoxelModel(w, h, d); var r = new Random(); int pos = 0; progress?.Report("Reading voxels"); for (int y = 0; y < h; ++y) { for (int x = 0; x < w; ++x) { int z = 0; uint color = 0; // fill with brownish color for (; z < d; ++z) { uint col = 0x284067; col ^= 0x070707 & (uint) r.Next(); model[x, y, z] = col; } z = 0; while (true) { int number_4byte_chunks = bytes[pos]; int top_color_start = bytes[pos + 1]; int top_color_end = bytes[pos + 2]; int bottom_color_start; int bottom_color_end; int len_top; int len_bottom; for (; z < top_color_start; ++z) { model[x, y, z] = VoxelModel.EmptyVoxel; } int colorpos = pos + 4; for (; z <= top_color_end; z++) { color = BitConverter.ToUInt32(bytes, colorpos); colorpos += 4; model[x, y, z] = color; } if (top_color_end == d - 2) { model[x, y, d - 1] = model[x, y, d - 2]; } len_bottom = top_color_end - top_color_start + 1; if (number_4byte_chunks == 0) { pos += 4 * (len_bottom + 1); break; } len_top = (number_4byte_chunks - 1) - len_bottom; pos += (int) bytes[pos] * 4; bottom_color_end = bytes[pos + 3]; bottom_color_start = bottom_color_end - len_top; for (z = bottom_color_start; z < bottom_color_end; z++) { color = BitConverter.ToUInt32(bytes, colorpos); colorpos += 4; model[x, y, z] = color; } if (bottom_color_end == d - 1) { model[x, y, d - 1] = model[x, y, d - 2]; } } // while (true) } // for x progress?.Report((double)(y + 1) / h); } // for y return model; }
public void Remesh(ref Mesh mesh, IProgressListener progress = null) { var triangles = mesh.Triangles; var vertices = mesh.Vertices; // Compute K matrices for initial triangles. foreach (var t in triangles) { t.UpdateGeometricData(); t.Tag = new ErrorMetric(t); } // Compute Q for intiial vertices. foreach (var v in vertices) { ComputeErrorMetricForVertex(v); } // Compute initial edge QEM-s foreach (var t in triangles) { ComputeErrorMetricForEdges(t); } foreach (var t in triangles) { ComputeEdgeCost(t); } // Compute number of triangles after we stop int toRemove = (int)((m_Removed) * triangles.Count); int triangleLimit = triangles.Count - toRemove; #if TRACE_NANS int nansCount = 0; #endif int index = 0; while (triangleLimit < triangles.Count) { Vertex v1, v2; Triangle.Edge edge; if (SearchBestCandidate(ref mesh, out v1, out v2, out edge)) { if (edge != null) { ErrorMetric em = (ErrorMetric)edge.Tag; Vector3 v = em.ProposedPoint; #if false if (v.IsNaN()) { #if TRACE_NANS ++nansCount; #endif v = Vector3Extension.Mean(v1.Position, v2.Position); } #endif if (mesh.JoinVertices(v1, v2, v)) { // V1, since v2 is removed from now. UpdateVertexNeighbors(v1); } progress.OnProgress(index, toRemove); index += 2; } else { Trace.WriteLine("If you see this message more than once per second, I can't find any matching edge"); } } } #if TRACE_NANS Trace.WriteLine(string.Format("NaNs count: {0}", nansCount)); #endif }
/// <summary> /// Writes raw mesh to stream. /// </summary> /// <param name="vertices">The list of the vertices.</param> /// <param name="indices">The list of the indices.</param> /// <param name="progress">The optional progress listener.</param> public void WriteMesh(ref List<Vertex> vertices, ref List<int> indices, IProgressListener progress = null) { long current = 0; long total = vertices.Count + indices.Count; progress.OnStart("Mesh writing started..."); foreach (var vertex in vertices) { m_Writer.WriteLine(string.Format( CultureInfo.InvariantCulture, "v {0} {1} {2}", vertex.Position.X.ToString("0.000000", CultureInfo.InvariantCulture), vertex.Position.Y.ToString("0.000000", CultureInfo.InvariantCulture), vertex.Position.Z.ToString("0.000000", CultureInfo.InvariantCulture))); ++current; if (progress != null) { progress.OnProgress(current, total); } } int count = 0; foreach (var index in indices) { switch (count % 3) { case 0: { m_Writer.Write(string.Format(CultureInfo.InvariantCulture, "f {0} ", index + 1)); break; } case 1: { m_Writer.Write(string.Format(CultureInfo.InvariantCulture, "{0} ", index + 1)); break; } case 2: { m_Writer.WriteLine(string.Format(CultureInfo.InvariantCulture, "{0}", index + 1)); break; } default: { Trace.WriteLine("Not supported"); break; } } ++count; ++current; if (progress != null) { progress.OnProgress(current, total); } } if (progress != null) { progress.OnComplete("Mesh writing complete"); } m_Writer.Close(); }
public static IEnumerator<object> FromFile(string filename, IProgressListener progress) { progress.Status = "Loading diff..."; Future<string> fText; // We could stream the lines in from the IO thread while we parse them, but this // part of the load is usually pretty quick even on a regular hard disk, and // loading the whole diff at once eliminates some context switches using (var fda = new FileDataAdapter( filename, FileMode.Open, FileAccess.Read, FileShare.Read, 1024 * 128 )) { var fBytes = fda.ReadToEnd(); yield return fBytes; fText = Future.RunInThread( () => Encoding.ASCII.GetString(fBytes.Result) ); yield return fText; } yield return fText; var lr = new LineReader(fText.Result); LineReader.Line line; progress.Status = "Parsing diff..."; var frames = new List<TracebackFrame>(); var moduleNames = new NameTable(StringComparer.Ordinal); var symbolTypes = new NameTable(StringComparer.Ordinal); var functionNames = new NameTable(StringComparer.Ordinal); var deltas = new List<DeltaInfo>(); var tracebacks = new Dictionary<UInt32, TracebackInfo>(); var regexes = new Regexes(); // Regex.Groups[string] does an inefficient lookup, so we do that lookup once here int groupModule = regexes.DiffModule.GroupNumberFromName("module"); int groupSymbolType = regexes.DiffModule.GroupNumberFromName("symbol_type"); int groupTraceId = regexes.BytesDelta.GroupNumberFromName("trace_id"); int groupType = regexes.BytesDelta.GroupNumberFromName("type"); int groupDeltaBytes = regexes.BytesDelta.GroupNumberFromName("delta_bytes"); int groupNewBytes = regexes.BytesDelta.GroupNumberFromName("new_bytes"); int groupOldBytes = regexes.BytesDelta.GroupNumberFromName("old_bytes"); int groupNewCount = regexes.BytesDelta.GroupNumberFromName("new_count"); int groupOldCount = regexes.CountDelta.GroupNumberFromName("old_count"); int groupCountDelta = regexes.CountDelta.GroupNumberFromName("delta_count"); int groupTracebackModule = regexes.TracebackFrame.GroupNumberFromName("module"); int groupTracebackFunction = regexes.TracebackFrame.GroupNumberFromName("function"); int groupTracebackOffset = regexes.TracebackFrame.GroupNumberFromName("offset"); int groupTracebackOffset2 = regexes.TracebackFrame.GroupNumberFromName("offset2"); int groupTracebackPath = regexes.TracebackFrame.GroupNumberFromName("path"); int groupTracebackLine = regexes.TracebackFrame.GroupNumberFromName("line"); int i = 0; while (lr.ReadLine(out line)) { if (i % ProgressInterval == 0) { progress.Maximum = lr.Length; progress.Progress = lr.Position; // Suspend processing until any messages in the windows message queue have been processed yield return new Yield(); } retryFromHere: Match m; if (regexes.DiffModule.TryMatch(ref line, out m)) { moduleNames.Add(m.Groups[groupModule].Value); } else if (regexes.BytesDelta.TryMatch(ref line, out m)) { var traceId = UInt32.Parse(m.Groups[groupTraceId].Value, NumberStyles.HexNumber); var info = new DeltaInfo { Added = (m.Groups[groupType].Value == "+"), BytesDelta = int.Parse(m.Groups[groupDeltaBytes].Value, NumberStyles.HexNumber), NewBytes = int.Parse(m.Groups[groupNewBytes].Value, NumberStyles.HexNumber), OldBytes = int.Parse(m.Groups[groupOldBytes].Value, NumberStyles.HexNumber), NewCount = int.Parse(m.Groups[groupNewCount].Value, NumberStyles.HexNumber), }; if (lr.ReadLine(out line)) { if (regexes.CountDelta.TryMatch(ref line, out m)) { info.OldCount = int.Parse(m.Groups[groupOldCount].Value, NumberStyles.HexNumber); info.CountDelta = int.Parse(m.Groups[groupCountDelta].Value, NumberStyles.HexNumber); } } bool readingLeadingWhitespace = true, doRetry = false; frames.Clear(); var itemModules = new NameTable(StringComparer.Ordinal); var itemFunctions = new NameTable(StringComparer.Ordinal); while (lr.ReadLine(out line)) { if (line.ToString().Trim().Length == 0) { if (readingLeadingWhitespace) continue; else break; } else if (regexes.TracebackFrame.TryMatch(ref line, out m)) { readingLeadingWhitespace = false; var moduleName = moduleNames[m.Groups[groupTracebackModule].Value]; itemModules.Add(moduleName); var functionName = functionNames[m.Groups[groupTracebackFunction].Value]; itemFunctions.Add(functionName); var frame = new TracebackFrame { Module = moduleName, Function = functionName, Offset = UInt32.Parse(m.Groups[groupTracebackOffset].Value, NumberStyles.HexNumber) }; if (m.Groups[groupTracebackOffset2].Success) frame.Offset2 = UInt32.Parse(m.Groups[groupTracebackOffset2].Value, NumberStyles.HexNumber); if (m.Groups[groupTracebackPath].Success) frame.SourceFile = m.Groups[groupTracebackPath].Value; if (m.Groups[groupTracebackLine].Success) frame.SourceLine = int.Parse(m.Groups[groupTracebackLine].Value); frames.Add(frame); } else { // We hit the beginning of a new allocation, so make sure it gets parsed doRetry = true; break; } } if (tracebacks.ContainsKey(traceId)) { info.Traceback = tracebacks[traceId]; Console.WriteLine("Duplicate traceback for id {0}!", traceId); } else { var frameArray = ImmutableArrayPool<TracebackFrame>.Allocate(frames.Count); frames.CopyTo(frameArray.Array, frameArray.Offset); info.Traceback = tracebacks[traceId] = new TracebackInfo { TraceId = traceId, Frames = frameArray, Modules = itemModules, Functions = itemFunctions }; } deltas.Add(info); if (doRetry) goto retryFromHere; } else if (line.StartsWith("//")) { // Comment, ignore it } else if (line.StartsWith("Total increase") || line.StartsWith("Total decrease")) { // Ignore this too } else if (line.StartsWith(" ") && (line.EndsWith(".pdb"))) { // Symbol path for a module, ignore it } else { Console.WriteLine("Unrecognized diff content: {0}", line.ToString()); } } var result = new HeapDiff( filename, moduleNames, functionNames, deltas, tracebacks ); yield return new Result(result); }
public bool[,,] Apply(bool[,,] field, IProgressListener progress) { int d1 = field.GetLength(0); int d2 = field.GetLength(1); int d3 = field.GetLength(2); bool[,,] ret = new bool[d1, d2, d3]; int dist = Distance; DistanceType type = DistanceType; for (int x = 0; x < d1; ++x) { for (int y = 0; y < d2; ++y) { for (int z = 0; z < d3; ++z) { switch (type) { case DistanceType.Manhattan: for (int s = -dist; s <= dist; ++s) { for (int t = -dist; t <= dist; ++t) { for (int u = -dist; u <= dist; ++u) { if (Math.Abs(s) + Math.Abs(t) + Math.Abs(u) > dist) { continue; } int cx = s + x, cy = t + y, cz = u + z; if (cx < 0 || cy < 0 || cz < 0 || cx >= d1 || cy >= d2 || cz >= d3) { continue; } if (field[cx, cy, cz]) { ret[x, y, z] = true; goto DoneOne; } } } } break; case DistanceType.Chebyshev: for (int s = -dist; s <= dist; ++s) { for (int t = -dist; t <= dist; ++t) { for (int u = -dist; u <= dist; ++u) { int cx = s + x, cy = t + y, cz = u + z; if (cx < 0 || cy < 0 || cz < 0 || cx >= d1 || cy >= d2 || cz >= d3) { continue; } if (field[cx, cy, cz]) { ret[x, y, z] = true; goto DoneOne; } } } } break; default: throw new ArgumentOutOfRangeException(); } DoneOne:; } } progress?.Report((double)(x + 1) / d1); } return ret; }
public MeshSlices GenerateSlices(VoxelModel model, IProgressListener progress) { var slices = new MeshSlices(); var dims = model.Dimensions; int totalsteps = 2 * (model.Width + model.Height + model.Depth); int step = 0; progress?.Report("Generating slices"); for (int iaxis = 0; iaxis < 3; ++iaxis) { for (int iface = 0; iface < 2; ++iface) { var axis = (Axis3) iaxis; var paxis1 = (Axis3) ((iaxis + 1) % 3); var paxis2 = (Axis3) ((iaxis + 2) % 3); bool face = iface != 0; int dim0 = dims[axis]; int dim1 = dims[paxis1]; int dim2 = dims[paxis2]; var slicelist = new MeshSlice[dim0]; slices[axis, face] = slicelist; for (int layer = 0; layer < dim0; ++layer) { ++step; progress?.Report((double)step / totalsteps); var faces = new List<int>(); var ret = new List<IntVector3>(); var pt1 = new IntVector3(); pt1[axis] = layer; for (int x = 0; x < dim1; ++x) { pt1[paxis1] = x; for (int y = 0; y < dim2; ++y) { pt1[paxis2] = y; bool solid1 = model.IsVoxelSolid(pt1); var pt2 = pt1; bool solid2 = false; if (face) { pt2[axis] += 1; if (pt2[axis] < dim0) { solid2 = model.IsVoxelSolid(pt2); } } else { pt2[axis] -= 1; if (pt2[axis] >= 0) { solid2 = model.IsVoxelSolid(pt2); } } if (!solid1 || solid2) { continue; } // Create quad var qpt1 = pt1; if (face) { qpt1[axis] += 1; qpt1[paxis2] += 1; } var qpt2 = qpt1; qpt2[paxis1] += 1; var qpt3 = qpt1; var qpt4 = qpt2; if (face) { qpt3[paxis2] -= 1; qpt4[paxis2] -= 1; } else { qpt3[paxis2] += 1; qpt4[paxis2] += 1; } // Emit polygons faces.Add(ret.Count); ret.Add(qpt3); ret.Add(qpt4); ret.Add(qpt2); ret.Add(qpt1); } // for y } // for x slicelist[layer] = new MeshSlice() { Positions = ret.ToArray(), Faces = faces.ToArray(), Face = face, Axis = axis, Layer = layer }; } // for slice } // iface } // iaxis return slices; }
public VoxelModel LoadVoxelModel(System.IO.Stream stream, IProgressListener progress) { Vector3 dummy; return LoadVoxelModel(stream, out dummy, progress); }