Beispiel #1
0
        void AddLoadTask(LoadTask t)
        {
            if (tileLoadQueue4Tasks == null)
            {
                lock (tileLoadQueue4)
                {
                    if (tileLoadQueue4Tasks == null)
                    {
                        tileLoadQueue4Tasks = new List <Task>();

                        while (tileLoadQueue4Tasks.Count < GThreadPoolSize)
                        {
                            Debug.WriteLine("creating ProcessLoadTask: " + tileLoadQueue4Tasks.Count);

                            tileLoadQueue4Tasks.Add(Task.Factory.StartNew(delegate()
                            {
                                string ctid = "ProcessLoadTask[" + Thread.CurrentThread.ManagedThreadId + "]";
                                Thread.CurrentThread.Name = ctid;

                                Debug.WriteLine(ctid + ": started");
                                do
                                {
                                    if (tileLoadQueue4.Count == 0)
                                    {
                                        Debug.WriteLine(ctid + ": ready");

                                        if (Interlocked.Increment(ref loadWaitCount) >= GThreadPoolSize)
                                        {
                                            Interlocked.Exchange(ref loadWaitCount, 0);
                                            OnLoadComplete(ctid);
                                        }
                                    }
                                    Interlocked.Increment(ref loadOnWaitTake);
                                    var task = tileLoadQueue4.Take();
                                    Interlocked.Decrement(ref loadOnWaitTake);
                                    ProcessLoadTask(task, ctid);
                                }while (!tileLoadQueue4.IsAddingCompleted);

                                Debug.WriteLine(ctid + ": exit");
                            }, TaskCreationOptions.LongRunning));
                        }
                    }
                }
            }
            tileLoadQueue4.Add(t);
        }
Beispiel #2
0
        /// <summary>
        /// updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            tileDrawingListLock.AcquireWriterLock();
            try
            {
                FindTilesAround();

                lock (tileLoadQueue)
                {
                    foreach (Point p in tileDrawingList)
                    {
                        LoadTask task = new LoadTask(p, Zoom);
                        {
                            if (!tileLoadQueue.Contains(task))
                            {
                                tileLoadQueue.Enqueue(task);
                            }
                        }
                    }
                    EnsureLoaderThreads();
                }
            }
            finally
            {
                tileDrawingListLock.ReleaseWriterLock();

                if (OnTileLoadStart != null)
                {
                    OnTileLoadStart();
                }

                LastTileLoadStart = DateTime.Now;
                Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);

                waitForTileLoad.Set();
            }
        }
      /// <summary>
      /// updates map bounds
      /// </summary>
      void UpdateBounds()
      {
         if(!IsStarted || Provider.Equals(EmptyProvider.Instance))
         {
            return;
         }

         updatingBounds = true;

         tileDrawingListLock.AcquireWriterLock();
         try
         {
            #region -- find tiles around --
            tileDrawingList.Clear();

            for(long i = (int)Math.Floor(-sizeOfMapArea.Width * scaleX), countI = (int)Math.Ceiling(sizeOfMapArea.Width * scaleX); i <= countI; i++)
            {
               for (long j = (int)Math.Floor(-sizeOfMapArea.Height * scaleY), countJ = (int)Math.Ceiling(sizeOfMapArea.Height * scaleY); j <= countJ; j++)
               {
                  GPoint p = centerTileXYLocation;
                  p.X += i;
                  p.Y += j;

#if ContinuesMap
               // ----------------------------
               if(p.X < minOfTiles.Width)
               {
                  p.X += (maxOfTiles.Width + 1);
               }

               if(p.X > maxOfTiles.Width)
               {
                  p.X -= (maxOfTiles.Width + 1);
               }
               // ----------------------------
#endif

                  if(p.X >= minOfTiles.Width && p.Y >= minOfTiles.Height && p.X <= maxOfTiles.Width && p.Y <= maxOfTiles.Height)
                  {
                     DrawTile dt = new DrawTile()
                     {
                        PosXY = p,
                        PosPixel = new GPoint(p.X * tileRect.Width, p.Y * tileRect.Height),
                        DistanceSqr = (centerTileXYLocation.X - p.X) * (centerTileXYLocation.X - p.X) + (centerTileXYLocation.Y - p.Y) * (centerTileXYLocation.Y - p.Y)
                     };

                     if(!tileDrawingList.Contains(dt))
                     {
                        tileDrawingList.Add(dt);
                     }
                  }
               }
            }

            if(GMaps.Instance.ShuffleTilesOnLoad)
            {
               Stuff.Shuffle<DrawTile>(tileDrawingList);
            }
            else
            {
               tileDrawingList.Sort();
            }
            #endregion
         }
         finally
         {
            tileDrawingListLock.ReleaseWriterLock();
         }

         Monitor.Enter(tileLoadQueue);
         try
         {
            tileDrawingListLock.AcquireReaderLock();
            try
            {
               foreach(DrawTile p in tileDrawingList)
               {
                  LoadTask task = new LoadTask(p.PosXY, Zoom);
                  {
                     if(!tileLoadQueue.Contains(task))
                     {
                        tileLoadQueue.Push(task);
                     }
                  }
               }
            }
            finally
            {
               tileDrawingListLock.ReleaseReaderLock();
            }

            #region -- starts loader threads if needed --

            lock(GThreadPool)
            {
               while(GThreadPool.Count < GThreadPoolSize)
               {
                  Thread t = new Thread(new ThreadStart(ProcessLoadTask));
                  {
                     t.Name = "TileLoader: " + GThreadPool.Count;
                     t.IsBackground = true;
                     t.Priority = ThreadPriority.BelowNormal;
                  }
                  GThreadPool.Add(t);

                  Debug.WriteLine("add " + t.Name + " to GThreadPool");

                  t.Start();
               }
            }
            #endregion

            {
               LastTileLoadStart = DateTime.Now;
               Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);
            }

            loadWaitCount = 0;
            Monitor.PulseAll(tileLoadQueue);
         }
         finally
         {
            Monitor.Exit(tileLoadQueue);
         }

         updatingBounds = false;

         if(OnTileLoadStart != null)
         {
            OnTileLoadStart();
         }
      }
Beispiel #4
0
        /// <summary>
        /// updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            if (!IsStarted || Provider.Equals(EmptyProvider.Instance))
            {
                return;
            }

            updatingBounds = true;

            tileDrawingListLock.AcquireWriterLock();
            try
            {
                #region -- find tiles around --
                tileDrawingList.Clear();

                for (long i = (int)Math.Floor(-sizeOfMapArea.Width * scaleX), countI = (int)Math.Ceiling(sizeOfMapArea.Width * scaleX); i <= countI; i++)
                {
                    for (long j = (int)Math.Floor(-sizeOfMapArea.Height * scaleY), countJ = (int)Math.Ceiling(sizeOfMapArea.Height * scaleY); j <= countJ; j++)
                    {
                        GPoint p = centerTileXYLocation;
                        p.X += i;
                        p.Y += j;

#if ContinuesMap
                        // ----------------------------
                        if (p.X < minOfTiles.Width)
                        {
                            p.X += (maxOfTiles.Width + 1);
                        }

                        if (p.X > maxOfTiles.Width)
                        {
                            p.X -= (maxOfTiles.Width + 1);
                        }
                        // ----------------------------
#endif

                        if (p.X >= minOfTiles.Width && p.Y >= minOfTiles.Height && p.X <= maxOfTiles.Width && p.Y <= maxOfTiles.Height)
                        {
                            DrawTile dt = new DrawTile()
                            {
                                PosXY       = p,
                                PosPixel    = new GPoint(p.X * tileRect.Width, p.Y * tileRect.Height),
                                DistanceSqr = (centerTileXYLocation.X - p.X) * (centerTileXYLocation.X - p.X) + (centerTileXYLocation.Y - p.Y) * (centerTileXYLocation.Y - p.Y)
                            };

                            if (!tileDrawingList.Contains(dt))
                            {
                                tileDrawingList.Add(dt);
                            }
                        }
                    }
                }

                if (GMaps.Instance.ShuffleTilesOnLoad)
                {
                    Stuff.Shuffle <DrawTile>(tileDrawingList);
                }
                else
                {
                    tileDrawingList.Sort();
                }
                #endregion
            }
            finally
            {
                tileDrawingListLock.ReleaseWriterLock();
            }

            Monitor.Enter(tileLoadQueue);
            try
            {
                tileDrawingListLock.AcquireReaderLock();
                try
                {
                    foreach (DrawTile p in tileDrawingList)
                    {
                        LoadTask task = new LoadTask(p.PosXY, Zoom);
                        {
                            if (!tileLoadQueue.Contains(task))
                            {
                                tileLoadQueue.Push(task);
                            }
                        }
                    }
                }
                finally
                {
                    tileDrawingListLock.ReleaseReaderLock();
                }

                #region -- starts loader threads if needed --

                lock (GThreadPool)
                {
                    while (GThreadPool.Count < GThreadPoolSize)
                    {
                        Thread t = new Thread(new ThreadStart(ProcessLoadTask));
                        {
                            t.Name         = "TileLoader: " + GThreadPool.Count;
                            t.IsBackground = true;
                            t.Priority     = ThreadPriority.BelowNormal;
                        }
                        GThreadPool.Add(t);

                        Debug.WriteLine("add " + t.Name + " to GThreadPool");

                        t.Start();
                    }
                }
                #endregion

                {
                    LastTileLoadStart = DateTime.Now;
                    Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);
                }

                loadWaitCount = 0;
                Monitor.PulseAll(tileLoadQueue);
            }
            finally
            {
                Monitor.Exit(tileLoadQueue);
            }

            updatingBounds = false;

            if (OnTileLoadStart != null)
            {
                OnTileLoadStart();
            }
        }
Beispiel #5
0
      /// <summary>
      /// render map in WPF
      /// </summary>
      /// <param name="g"></param>
      void DrawMap(DrawingContext g)
      {
         if(MapProvider == EmptyProvider.Instance || MapProvider == null)
         {
            return;
         }

         Core.tileDrawingListLock.AcquireReaderLock();
         Core.Matrix.EnterReadLock();
         try
         {
            foreach(var tilePoint in Core.tileDrawingList)
            {
               Core.tileRect.Location = tilePoint.PosPixel;
               Core.tileRect.OffsetNegative(Core.compensationOffset);

               //if(region.IntersectsWith(Core.tileRect) || IsRotated)
               {
                  bool found = false;

                  Tile t = Core.Matrix.GetTileWithNoLock(Core.Zoom, tilePoint.PosXY);
                  if(t.NotEmpty)
                  {
                     foreach(GMapImage img in t.Overlays)
                     {
                        if(img != null && img.Img != null)
                        {
                           if(!found)
                              found = true;

                           var imgRect = new Rect(Core.tileRect.X + 0.6, Core.tileRect.Y + 0.6, Core.tileRect.Width + 0.6, Core.tileRect.Height + 0.6);
                           if(!img.IsParent)
                           {
                              g.DrawImage(img.Img, imgRect);
                           }
                           else
                           {
                              // TODO: move calculations to loader thread
                              var geometry = new RectangleGeometry(imgRect);
                              var parentImgRect = new Rect(Core.tileRect.X - Core.tileRect.Width * img.Xoff + 0.6, Core.tileRect.Y - Core.tileRect.Height * img.Yoff + 0.6, Core.tileRect.Width * img.Ix + 0.6, Core.tileRect.Height * img.Ix + 0.6);

                              g.PushClip(geometry);
                              g.DrawImage(img.Img, parentImgRect);
                              g.Pop();
                              geometry = null;
                           }
                        }
                     }
                  }
                  else if(FillEmptyTiles && MapProvider.Projection is MercatorProjection)
                  {
                     #region -- fill empty tiles --
                     int zoomOffset = 1;
                     Tile parentTile = Tile.Empty;
                     long Ix = 0;

                     while(!parentTile.NotEmpty && zoomOffset < Core.Zoom && zoomOffset <= LevelsKeepInMemmory)
                     {
                        Ix = (long)Math.Pow(2, zoomOffset);
                        parentTile = Core.Matrix.GetTileWithNoLock(Core.Zoom - zoomOffset++, new GMap.NET.GPoint((int)(tilePoint.PosXY.X / Ix), (int)(tilePoint.PosXY.Y / Ix)));
                     }

                     if(parentTile.NotEmpty)
                     {
                        long Xoff = Math.Abs(tilePoint.PosXY.X - (parentTile.Pos.X * Ix));
                        long Yoff = Math.Abs(tilePoint.PosXY.Y - (parentTile.Pos.Y * Ix));

                        var geometry = new RectangleGeometry(new Rect(Core.tileRect.X + 0.6, Core.tileRect.Y + 0.6, Core.tileRect.Width + 0.6, Core.tileRect.Height + 0.6));
                        var parentImgRect = new Rect(Core.tileRect.X - Core.tileRect.Width * Xoff + 0.6, Core.tileRect.Y - Core.tileRect.Height * Yoff + 0.6, Core.tileRect.Width * Ix + 0.6, Core.tileRect.Height * Ix + 0.6);

                        // render tile 
                        {
                           foreach(GMapImage img in parentTile.Overlays)
                           {
                              if(img != null && img.Img != null && !img.IsParent)
                              {
                                 if(!found)
                                    found = true;

                                 g.PushClip(geometry);
                                 g.DrawImage(img.Img, parentImgRect);
                                 g.DrawRectangle(SelectedAreaFill, null, geometry.Bounds);
                                 g.Pop();
                              }
                           }
                        }

                        geometry = null;
                     }
                     #endregion
                  }

                  // add text if tile is missing
                  if(!found)
                  {
                     lock(Core.FailedLoads)
                     {
                        var lt = new LoadTask(tilePoint.PosXY, Core.Zoom);

                        if(Core.FailedLoads.ContainsKey(lt))
                        {
                           g.DrawRectangle(EmptytileBrush, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                           var ex = Core.FailedLoads[lt];
                           FormattedText TileText = new FormattedText("Exception: " + ex.Message, System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 14, Brushes.Red);
                           TileText.MaxTextWidth = Core.tileRect.Width - 11;

                           g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + 11, Core.tileRect.Y + 11));

                           g.DrawText(EmptyTileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - EmptyTileText.Height / 2));
                        }
                     }
                  }

                  if(ShowTileGridLines)
                  {
                     g.DrawRectangle(null, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                     if(tilePoint.PosXY == Core.centerTileXYLocation)
                     {
                        FormattedText TileText = new FormattedText("CENTER:" + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        TileText.MaxTextWidth = Core.tileRect.Width;
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                     else
                     {
                        FormattedText TileText = new FormattedText("TILE: " + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        TileText.MaxTextWidth = Core.tileRect.Width;
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                  }
               }
            }
         }
         finally
         {
            Core.Matrix.LeaveReadLock();
            Core.tileDrawingListLock.ReleaseReaderLock();
         }
      }
Beispiel #6
0
        /// <summary>
        /// updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            if (MapType == NET.MapType.None)
            {
                return;
            }

            lock (tileLoadQueue)
            {
                tileDrawingListLock.AcquireWriterLock();
                try
                {
                    #region -- find tiles around --
                    tileDrawingList.Clear();

                    for (int i = -sizeOfMapArea.Width; i <= sizeOfMapArea.Width; i++)
                    {
                        for (int j = -sizeOfMapArea.Height; j <= sizeOfMapArea.Height; j++)
                        {
                            Point p = centerTileXYLocation;
                            p.X += i;
                            p.Y += j;

#if ContinuesMap
                            // ----------------------------
                            if (p.X < minOfTiles.Width)
                            {
                                p.X += (maxOfTiles.Width + 1);
                            }

                            if (p.X > maxOfTiles.Width)
                            {
                                p.X -= (maxOfTiles.Width + 1);
                            }
                            // ----------------------------
#endif

                            if (p.X >= minOfTiles.Width && p.Y >= minOfTiles.Height && p.X <= maxOfTiles.Width && p.Y <= maxOfTiles.Height)
                            {
                                if (!tileDrawingList.Contains(p))
                                {
                                    tileDrawingList.Add(p);
                                }
                            }
                        }
                    }

                    if (GMaps.Instance.ShuffleTilesOnLoad)
                    {
                        Stuff.Shuffle <Point>(tileDrawingList);
                    }
                    #endregion

                    foreach (Point p in tileDrawingList)
                    {
                        LoadTask task = new LoadTask(p, Zoom);
                        {
                            if (!tileLoadQueue.Contains(task))
                            {
                                tileLoadQueue.Enqueue(task);
                            }
                        }
                    }
                }
                finally
                {
                    tileDrawingListLock.ReleaseWriterLock();
                }

                #region -- starts loader threads if needed --
#if !PocketPC
                while (GThreadPool.Count < GThreadPoolSize)
#else
                while (GThreadPool.Count < GThreadPoolSize)
#endif
                {
                    Thread t = new Thread(new ThreadStart(ProcessLoadTask));
                    {
                        t.Name         = "GMap.NET TileLoader: " + GThreadPool.Count;
                        t.IsBackground = true;
                        t.Priority     = ThreadPriority.BelowNormal;
                    }
                    GThreadPool.Add(t);

                    Debug.WriteLine("add " + t.Name + " to GThreadPool");

                    t.Start();
                }
                #endregion

                lock (LastTileLoadStartEndLock)
                {
                    LastTileLoadStart = DateTime.Now;
                    Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);
                }

                loadWaitCount = 0;

#if !PocketPC
                Monitor.PulseAll(tileLoadQueue);
#else
                wait.PulseAll();
#endif
            }

            if (OnTileLoadStart != null)
            {
                OnTileLoadStart();
            }
        }
Beispiel #7
0
        static void ProcessLoadTask(LoadTask task, string ctid)
        {
            try
            {
                #region -- execute --

                var m = task.Core.Matrix.GetTileWithReadLock(task.Zoom, task.Pos);
                if (!m.NotEmpty)
                {
                    Debug.WriteLine(ctid + " - try load: " + task);

                    Tile t = new Tile(task.Zoom, task.Pos);

                    foreach (var tl in task.Core.provider.Overlays)
                    {
                        int retry = 0;
                        do
                        {
                            PureImage img = null;
                            Exception ex  = null;

                            if (task.Zoom >= task.Core.provider.MinZoom && (!task.Core.provider.MaxZoom.HasValue || task.Zoom <= task.Core.provider.MaxZoom))
                            {
                                if (task.Core.skipOverZoom == 0 || task.Zoom <= task.Core.skipOverZoom)
                                {
                                    // tile number inversion(BottomLeft -> TopLeft)
                                    if (tl.InvertedAxisY)
                                    {
                                        img = GMaps.Instance.GetImageFrom(tl, new GPoint(task.Pos.X, task.Core.maxOfTiles.Height - task.Pos.Y), task.Zoom, out ex);
                                    }
                                    else // ok
                                    {
                                        img = GMaps.Instance.GetImageFrom(tl, task.Pos, task.Zoom, out ex);
                                    }
                                }
                            }

                            if (img != null && ex == null)
                            {
                                if (task.Core.okZoom < task.Zoom)
                                {
                                    task.Core.okZoom       = task.Zoom;
                                    task.Core.skipOverZoom = 0;
                                    Debug.WriteLine("skipOverZoom disabled, okZoom: " + task.Core.okZoom);
                                }
                            }
                            else if (ex != null)
                            {
                                if ((task.Core.skipOverZoom != task.Core.okZoom) && (task.Zoom > task.Core.okZoom))
                                {
                                    if (ex.Message.Contains("(404) Not Found"))
                                    {
                                        task.Core.skipOverZoom = task.Core.okZoom;
                                        Debug.WriteLine("skipOverZoom enabled: " + task.Core.skipOverZoom);
                                    }
                                }
                            }

                            // check for parent tiles if not found
                            if (img == null && task.Core.okZoom > 0 && task.Core.fillEmptyTiles && task.Core.Provider.Projection is MercatorProjection)
                            {
                                int    zoomOffset = task.Zoom > task.Core.okZoom ? task.Zoom - task.Core.okZoom : 1;
                                long   Ix         = 0;
                                GPoint parentTile = GPoint.Empty;

                                while (img == null && zoomOffset < task.Zoom)
                                {
                                    Ix         = (long)Math.Pow(2, zoomOffset);
                                    parentTile = new GMap.NET.GPoint((task.Pos.X / Ix), (task.Pos.Y / Ix));
                                    img        = GMaps.Instance.GetImageFrom(tl, parentTile, task.Zoom - zoomOffset++, out ex);
                                }

                                if (img != null)
                                {
                                    // offsets in quadrant
                                    long Xoff = Math.Abs(task.Pos.X - (parentTile.X * Ix));
                                    long Yoff = Math.Abs(task.Pos.Y - (parentTile.Y * Ix));

                                    img.IsParent = true;
                                    img.Ix       = Ix;
                                    img.Xoff     = Xoff;
                                    img.Yoff     = Yoff;

                                    // wpf
                                    //var geometry = new RectangleGeometry(new Rect(Core.tileRect.X + 0.6, Core.tileRect.Y + 0.6, Core.tileRect.Width + 0.6, Core.tileRect.Height + 0.6));
                                    //var parentImgRect = new Rect(Core.tileRect.X - Core.tileRect.Width * Xoff + 0.6, Core.tileRect.Y - Core.tileRect.Height * Yoff + 0.6, Core.tileRect.Width * Ix + 0.6, Core.tileRect.Height * Ix + 0.6);

                                    // gdi+
                                    //System.Drawing.Rectangle dst = new System.Drawing.Rectangle((int)Core.tileRect.X, (int)Core.tileRect.Y, (int)Core.tileRect.Width, (int)Core.tileRect.Height);
                                    //System.Drawing.RectangleF srcRect = new System.Drawing.RectangleF((float)(Xoff * (img.Img.Width / Ix)), (float)(Yoff * (img.Img.Height / Ix)), (img.Img.Width / Ix), (img.Img.Height / Ix));
                                }
                            }

                            if (img != null)
                            {
                                Debug.WriteLine(ctid + " - tile loaded: " + img.Data.Length / 1024 + "KB, " + task);
                                {
                                    t.AddOverlay(img);
                                }
                                break;
                            }
                            else
                            {
                                if (ex != null)
                                {
                                    lock (task.Core.FailedLoads)
                                    {
                                        if (!task.Core.FailedLoads.ContainsKey(task))
                                        {
                                            task.Core.FailedLoads.Add(task, ex);

                                            if (task.Core.OnEmptyTileError != null)
                                            {
                                                if (!task.Core.RaiseEmptyTileError)
                                                {
                                                    task.Core.RaiseEmptyTileError = true;
                                                    task.Core.OnEmptyTileError(task.Zoom, task.Pos);
                                                }
                                            }
                                        }
                                    }
                                }

                                if (task.Core.RetryLoadTile > 0)
                                {
                                    Debug.WriteLine(ctid + " - ProcessLoadTask: " + task + " -> empty tile, retry " + retry);
                                    {
                                        Thread.Sleep(1111);
                                    }
                                }
                            }
                        }while (++retry < task.Core.RetryLoadTile);
                    }

                    if (t.HasAnyOverlays && task.Core.IsStarted)
                    {
                        task.Core.Matrix.SetTile(t);
                    }
                    else
                    {
                        t.Dispose();
                    }
                }

                #endregion
            }
            catch (Exception ex)
            {
                Debug.WriteLine(ctid + " - ProcessLoadTask: " + ex.ToString());
            }
            finally
            {
                if (task.Core.Refresh != null)
                {
                    task.Core.Refresh.Set();
                }
            }
        }
Beispiel #8
0
        /// <summary>
        /// updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            if (MapType == NET.MapType.None)
            {
                return;
            }

            lock (tileLoadQueue)
            {
                tileDrawingListLock.AcquireWriterLock();
                try
                {
                    #region -- find tiles around --
                    tileDrawingList.Clear();

                    for (int i = -sizeOfMapArea.Width; i <= sizeOfMapArea.Width; i++)
                    {
                        for (int j = -sizeOfMapArea.Height; j <= sizeOfMapArea.Height; j++)
                        {
                            Point p = centerTileXYLocation;
                            p.X += i;
                            p.Y += j;

            #if ContinuesMap
               // ----------------------------
               if(p.X < minOfTiles.Width)
               {
                  p.X += (maxOfTiles.Width + 1);
               }

               if(p.X > maxOfTiles.Width)
               {
                  p.X -= (maxOfTiles.Width + 1);
               }
               // ----------------------------
            #endif

                            if (p.X >= minOfTiles.Width && p.Y >= minOfTiles.Height && p.X <= maxOfTiles.Width && p.Y <= maxOfTiles.Height)
                            {
                                if (!tileDrawingList.Contains(p))
                                {
                                    tileDrawingList.Add(p);
                                }
                            }
                        }
                    }

                    if (GMaps.Instance.ShuffleTilesOnLoad)
                    {
                        Stuff.Shuffle<Point>(tileDrawingList);
                    }
                    #endregion

                    foreach (Point p in tileDrawingList)
                    {
                        LoadTask task = new LoadTask(p, Zoom);
                        {
                            if (!tileLoadQueue.Contains(task))
                            {
                                tileLoadQueue.Enqueue(task);
                            }
                        }
                    }
                }
                finally
                {
                    tileDrawingListLock.ReleaseWriterLock();
                }

                #region -- starts loader threads if needed --
            #if !PocketPC
                while (GThreadPool.Count < GThreadPoolSize)
            #else
            while(GThreadPool.Count < GThreadPoolSize)
            #endif
                {
                    Thread t = new Thread(new ThreadStart(ProcessLoadTask));
                    {
                        t.Name = "GMap.NET TileLoader: " + GThreadPool.Count;
                        t.IsBackground = true;
                        t.Priority = ThreadPriority.BelowNormal;
                    }
                    GThreadPool.Add(t);

                    Debug.WriteLine("add " + t.Name + " to GThreadPool");

                    t.Start();
                }
                #endregion

                lock (LastTileLoadStartEndLock)
                {
                    LastTileLoadStart = DateTime.Now;
                    Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);
                }

                loadWaitCount = 0;

                Monitor.PulseAll(tileLoadQueue);
            }

            if (OnTileLoadStart != null)
            {
                OnTileLoadStart();
            }
        }
        /// <summary>
        ///     updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            if (!IsStarted || Provider.Equals(EmptyProvider.Instance))
            {
                return;
            }

            UpdatingBounds = true;

            TileDrawingListLock.AcquireWriterLock();
            try
            {
                #region -- find tiles around --

                TileDrawingList.Clear();

                for (long i = (int)Math.Floor(-_sizeOfMapArea.Width * ScaleX),
                     countI = (int)Math.Ceiling(_sizeOfMapArea.Width * ScaleX);
                     i <= countI;
                     i++)
                {
                    for (long j = (int)Math.Floor(-_sizeOfMapArea.Height * ScaleY),
                         countJ = (int)Math.Ceiling(_sizeOfMapArea.Height * ScaleY);
                         j <= countJ;
                         j++)
                    {
                        var p = CenterTileXYLocation;
                        p.X += i;
                        p.Y += j;

#if ContinuesMap
                        // ----------------------------
                        if (p.X < minOfTiles.Width)
                        {
                            p.X += (maxOfTiles.Width + 1);
                        }

                        if (p.X > maxOfTiles.Width)
                        {
                            p.X -= (maxOfTiles.Width + 1);
                        }
                        // ----------------------------
#endif

                        if (p.X >= _minOfTiles.Width && p.Y >= _minOfTiles.Height && p.X <= _maxOfTiles.Width &&
                            p.Y <= _maxOfTiles.Height)
                        {
                            var dt = new DrawTile()
                            {
                                PosXY       = p,
                                PosPixel    = new GPoint(p.X * TileRect.Width, p.Y * TileRect.Height),
                                DistanceSqr = (CenterTileXYLocation.X - p.X) * (CenterTileXYLocation.X - p.X) +
                                              (CenterTileXYLocation.Y - p.Y) * (CenterTileXYLocation.Y - p.Y)
                            };

                            if (!TileDrawingList.Contains(dt))
                            {
                                TileDrawingList.Add(dt);
                            }
                        }
                    }
                }

                if (GMaps.Instance.ShuffleTilesOnLoad)
                {
                    Stuff.Shuffle(TileDrawingList);
                }
                else
                {
                    TileDrawingList.Sort();
                }

                #endregion
            }
            finally
            {
                TileDrawingListLock.ReleaseWriterLock();
            }

#if NET46
            Interlocked.Exchange(ref _loadWaitCount, 0);
#else
            Monitor.Enter(TileLoadQueue);
            try
            {
#endif
            TileDrawingListLock.AcquireReaderLock();
            try
            {
                foreach (var p in TileDrawingList)
                {
                    var task = new LoadTask(p.PosXY, Zoom, this);
#if NET46
                    AddLoadTask(task);
#else
                    {
                        if (!TileLoadQueue.Contains(task))
                        {
                            TileLoadQueue.Push(task);
                        }
                    }
#endif
                }
            }
            finally
            {
                TileDrawingListLock.ReleaseReaderLock();
            }

#if !NET46
            #region -- starts loader threads if needed --

            lock (_gThreadPool)
            {
                while (_gThreadPool.Count < GThreadPoolSize)
                {
                    var t = new Thread(TileLoadThread);
                    {
                        t.Name         = "TileLoader: " + _gThreadPool.Count;
                        t.IsBackground = true;
                        t.Priority     = ThreadPriority.BelowNormal;
                    }

                    _gThreadPool.Add(t);

                    Debug.WriteLine("add " + t.Name + " to GThreadPool");

                    t.Start();
                }
            }
            #endregion
#endif
            {
                _lastTileLoadStart = DateTime.Now;
                Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + _lastTileLoadStart.TimeOfDay);
            }
#if !NET46
            _loadWaitCount = 0;
            Monitor.PulseAll(TileLoadQueue);
        }

        finally
        {
            Monitor.Exit(TileLoadQueue);
        }
#endif
            UpdatingBounds = false;

            if (OnTileLoadStart != null)
            {
                OnTileLoadStart();
            }
        }
Beispiel #10
0
        /// <summary>
        /// updates map bounds
        /// </summary>
        void UpdateBounds()
        {
            if (!IsStarted || Provider.Equals(EmptyProvider.Instance))
            {
                return;
            }

            updatingBounds = true;

            tileDrawingListLock.AcquireWriterLock();
            try
            {
                #region -- find tiles around --
                tileDrawingList.Clear();

                for (long i = (int)Math.Floor(-sizeOfMapArea.Width * scaleX), countI = (int)Math.Ceiling(sizeOfMapArea.Width * scaleX); i <= countI; i++)
                {
                    for (long j = (int)Math.Floor(-sizeOfMapArea.Height * scaleY), countJ = (int)Math.Ceiling(sizeOfMapArea.Height * scaleY); j <= countJ; j++)
                    {
                        GPoint p = centerTileXYLocation;
                        p.X += i;
                        p.Y += j;

#if ContinuesMap
                        // ----------------------------
                        if (p.X < minOfTiles.Width)
                        {
                            p.X += (maxOfTiles.Width + 1);
                        }

                        if (p.X > maxOfTiles.Width)
                        {
                            p.X -= (maxOfTiles.Width + 1);
                        }
                        // ----------------------------
#endif

                        if (p.X >= minOfTiles.Width && p.Y >= minOfTiles.Height && p.X <= maxOfTiles.Width && p.Y <= maxOfTiles.Height)
                        {
                            DrawTile dt = new DrawTile()
                            {
                                PosXY       = p,
                                PosPixel    = new GPoint(p.X * tileRect.Width, p.Y * tileRect.Height),
                                DistanceSqr = (centerTileXYLocation.X - p.X) * (centerTileXYLocation.X - p.X) + (centerTileXYLocation.Y - p.Y) * (centerTileXYLocation.Y - p.Y)
                            };

                            if (!tileDrawingList.Contains(dt))
                            {
                                tileDrawingList.Add(dt);
                            }
                        }
                    }
                }

                if (GMaps.Instance.ShuffleTilesOnLoad)
                {
                    Stuff.Shuffle <DrawTile>(tileDrawingList);
                }
                else
                {
                    tileDrawingList.Sort();
                }
                #endregion
            }
            finally
            {
                tileDrawingListLock.ReleaseWriterLock();
            }

            Interlocked.Exchange(ref loadWaitCount, 0);

            tileDrawingListLock.AcquireReaderLock();
            try
            {
                foreach (DrawTile p in tileDrawingList)
                {
                    LoadTask task = new LoadTask(p.PosXY, Zoom, this);

                    AddLoadTask(task);
                }
            }
            finally
            {
                tileDrawingListLock.ReleaseReaderLock();
            }

            {
                LastTileLoadStart = DateTime.Now;
                Debug.WriteLine("OnTileLoadStart - at zoom " + Zoom + ", time: " + LastTileLoadStart.TimeOfDay);
            }

            updatingBounds = false;

            OnTileLoadStart?.Invoke();
        }
Beispiel #11
0
        /// <summary>
        /// render map in GDI+
        /// </summary>
        /// <param name="g"></param>
        void DrawMapGDIplus(Graphics g)
        {
            if (MapType == NET.MapType.None)
            {
                return;
            }

            Core.Matrix.EnterReadLock();
            Core.tileDrawingListLock.AcquireReaderLock();
            try
            {
                foreach (var tilePoint in Core.tileDrawingList)
                {
                    {
                        Core.tileRect.X = tilePoint.X * Core.tileRect.Width;
                        Core.tileRect.Y = tilePoint.Y * Core.tileRect.Height;
                        Core.tileRect.Offset(Core.renderOffset);

                        if (Core.currentRegion.IntersectsWith(Core.tileRect) || IsRotated)
                        {
                            bool found = false;
                            Tile t = Core.Matrix.GetTileWithNoLock(Core.Zoom, tilePoint);
                            if (t != null)
                            {
                                // render tile
                                lock (t.Overlays)
                                {
                                    foreach (WindowsFormsImage img in t.Overlays)
                                    {
                                        if (img != null && img.Img != null)
                                        {
                                            if (!found)
                                                found = true;

                                            g.DrawImage(img.Img, Core.tileRect.X, Core.tileRect.Y, Core.tileRectBearing.Width, Core.tileRectBearing.Height);
                                        }
                                    }
                                }
                            }
                            else // testing smooth zooming
                            {
                                int ZoomOffset = 0;
                                Tile ParentTile = null;
                                int Ix = 0;

                                while (ParentTile == null && (Core.Zoom - ZoomOffset) >= 1 && ZoomOffset <= LevelsKeepInMemmory)
                                {
                                    Ix = (int)Math.Pow(2, ++ZoomOffset);
                                    ParentTile = Core.Matrix.GetTileWithNoLock(Core.Zoom - ZoomOffset, new Point((int)(tilePoint.X / Ix), (int)(tilePoint.Y / Ix)));
                                }

                                if (ParentTile != null)
                                {
                                    int Xoff = Math.Abs(tilePoint.X - (ParentTile.Pos.X * Ix));
                                    int Yoff = Math.Abs(tilePoint.Y - (ParentTile.Pos.Y * Ix));

                                    // render tile
                                    lock (ParentTile.Overlays)
                                    {
                                        foreach (WindowsFormsImage img in ParentTile.Overlays)
                                        {
                                            if (img != null && img.Img != null)
                                            {
                                                if (!found)
                                                    found = true;

                                                System.Drawing.RectangleF srcRect = new System.Drawing.RectangleF((float)(Xoff * (img.Img.Width / Ix)), (float)(Yoff * (img.Img.Height / Ix)), (img.Img.Width / Ix), (img.Img.Height / Ix));
                                                System.Drawing.Rectangle dst = new System.Drawing.Rectangle(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height);

                                                g.DrawImage(img.Img, dst, srcRect.X, srcRect.Y, srcRect.Width, srcRect.Height, GraphicsUnit.Pixel, TileFlipXYAttributes);
                                                g.FillRectangle(SelectedAreaFill, dst);
                                            }
                                        }
                                    }
                                }
                            }

                            // add text if tile is missing
                            if (!found)
                            {
                                lock (Core.FailedLoads)
                                {
                                    var lt = new LoadTask(tilePoint, Core.Zoom);
                                    if (Core.FailedLoads.ContainsKey(lt))
                                    {
                                        var ex = Core.FailedLoads[lt];
                                        g.FillRectangle(EmptytileBrush, new RectangleF(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                                        g.DrawString("Exception: " + ex.Message, MissingDataFont, Brushes.Red, new RectangleF(Core.tileRect.X + 11, Core.tileRect.Y + 11, Core.tileRect.Width - 11, Core.tileRect.Height - 11));

                                        g.DrawString(EmptyTileText, MissingDataFont, Brushes.Blue, new RectangleF(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height), CenterFormat);

                                        g.DrawRectangle(EmptyTileBorders, Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height);
                                    }
                                }
                            }

                            if (ShowTileGridLines)
                            {
                                g.DrawRectangle(EmptyTileBorders, Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height);
                                {
                                    g.DrawString((tilePoint == Core.centerTileXYLocation ? "CENTER: " : "TILE: ") + tilePoint, MissingDataFont, Brushes.Red, new RectangleF(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height), CenterFormat);
                                }
                            }
                        }
                    }
                }
            }
            finally
            {
                Core.tileDrawingListLock.ReleaseReaderLock();
                Core.Matrix.LeaveReadLock();
            }
        }
      /// <summary>
      /// render map in WPF
      /// </summary>
      /// <param name="g"></param>
      void DrawMapWPF(DrawingContext g)
      {
         if(MapType == NET.MapType.None)
         {
            return;
         }

         Core.Matrix.EnterReadLock();
         Core.tileDrawingListLock.AcquireReaderLock();
         try
         {
            foreach(var tilePoint in Core.tileDrawingList)
            {
               Core.tileRect.X = tilePoint.X * Core.tileRect.Width;
               Core.tileRect.Y = tilePoint.Y * Core.tileRect.Height;
               Core.tileRect.Offset(Core.renderOffset);

               if(region.IntersectsWith(Core.tileRect) || IsRotated)
               {
                  bool found = false;

                  Tile t = Core.Matrix.GetTileWithNoLock(Core.Zoom, tilePoint);
                  if(t != null)
                  {
                     lock(t.Overlays)
                     {
                        foreach(WindowsPresentationImage img in t.Overlays)
                        {
                           if(img != null && img.Img != null)
                           {
                              if(!found)
                                 found = true;

                              g.DrawImage(img.Img, new Rect(Core.tileRect.X + 0.6, Core.tileRect.Y + 0.6, Core.tileRect.Width + 0.6, Core.tileRect.Height + 0.6));
                           }
                        }
                     }
                  }
                  //else // testing smooth zooming
                  //{
                  //   int ZoomOffset = 0;
                  //   Tile ParentTile = null;
                  //   int Ix = 0;

                  //   while(ParentTile == null && (Core.Zoom - ZoomOffset) >= 1 && ZoomOffset <= LevelsKeepInMemmory)
                  //   {
                  //      Ix = (int) Math.Pow(2, ++ZoomOffset);
                  //      ParentTile = Core.Matrix.GetTileWithNoLock(Core.Zoom - ZoomOffset, new GMap.NET.Point((int) (tilePoint.X / Ix), (int) (tilePoint.Y / Ix)));
                  //   }

                  //   if(ParentTile != null)
                  //   {
                  //      int Xoff = Math.Abs(tilePoint.X - (ParentTile.Pos.X * Ix));
                  //      int Yoff = Math.Abs(tilePoint.Y - (ParentTile.Pos.Y * Ix));

                  //      // render tile 
                  //      lock(ParentTile.Overlays)
                  //      {
                  //         foreach(WindowsPresentationImage img in ParentTile.Overlays)
                  //         {
                  //            if(img != null && img.Img != null)
                  //            {
                  //               if(!found)
                  //                  found = true;

                  //               //System.Drawing.RectangleF srcRect = new System.Drawing.RectangleF((float) (Xoff * (img.Img.Width / Ix)), (float) (Yoff * (img.Img.Height / Ix)), (img.Img.Width / Ix), (img.Img.Height / Ix));
                  //               //System.Drawing.Rectangle dst = new System.Drawing.Rectangle(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height);

                  //               //g.DrawImage(img.Img, new Rect(

                  //               //g.DrawImage(img.Img, dst, srcRect.X, srcRect.Y, srcRect.Width, srcRect.Height, GraphicsUnit.Pixel, TileFlipXYAttributes);
                  //               //g.FillRectangle(SelectedAreaFill, dst);
                  //            }
                  //         }
                  //      }
                  //   }
                  //}

                  // add text if tile is missing
                  if(!found)
                  {
                     lock(Core.FailedLoads)
                     {
                        var lt = new LoadTask(tilePoint, Core.Zoom);

                        if(Core.FailedLoads.ContainsKey(lt))
                        {
                           g.DrawRectangle(EmptytileBrush, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                           var ex = Core.FailedLoads[lt];
                           FormattedText TileText = new FormattedText("Exception: " + ex.Message, System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 14, Brushes.Red);
                           TileText.MaxTextWidth = Core.tileRect.Width - 11;

                           g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + 11, Core.tileRect.Y + 11));

                           g.DrawText(EmptyTileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - EmptyTileText.Height / 2));
                        }
                     }
                  }

                  if(ShowTileGridLines)
                  {
                     g.DrawRectangle(null, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                     if(tilePoint == Core.centerTileXYLocation)
                     {
                        FormattedText TileText = new FormattedText("CENTER:" + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                     else
                     {
                        FormattedText TileText = new FormattedText("TILE: " + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                  }
               }
            }
         }
         finally
         {
            Core.tileDrawingListLock.ReleaseReaderLock();
            Core.Matrix.LeaveReadLock();
         }
      }
Beispiel #13
0
        /// <summary>
        /// render map in WPF
        /// </summary>
        /// <param name="g"></param>
        void DrawMapWPF(DrawingContext g)
        {
            Core.Matrix.EnterReadLock();
             Core.tileDrawingListLock.AcquireReaderLock();
             try
             {
            foreach(var tilePoint in Core.tileDrawingList)
            {
               Core.tileRect.X = tilePoint.X * Core.tileRect.Width;
               Core.tileRect.Y = tilePoint.Y * Core.tileRect.Height;
               Core.tileRect.Offset(Core.renderOffset);

               if(region.IntersectsWith(Core.tileRect))
               {
                  bool found = false;

                  Tile t = Core.Matrix.GetTileWithNoLock(Core.Zoom, tilePoint);
                  if(t != null)
                  {
                     lock(t.Overlays)
                     {
                        foreach(WindowsPresentationImage img in t.Overlays)
                        {
                           if(img != null && img.Img != null)
                           {
                              if(!found)
                                 found = true;

                              g.DrawImage(img.Img, new Rect(Core.tileRect.X+0.6, Core.tileRect.Y+0.6, Core.tileRect.Width+0.6, Core.tileRect.Height+0.6));
                           }
                        }
                     }
                  }

                  // add text if tile is missing
                  if(!found)
                  {
                     lock(Core.FailedLoads)
                     {
                        var lt = new LoadTask(tilePoint, Core.Zoom);

                        if(Core.FailedLoads.ContainsKey(lt))
                        {
                           g.DrawRectangle(EmptytileBrush, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                           var ex = Core.FailedLoads[lt];
                           FormattedText TileText = new FormattedText("Exception: " + ex.Message, System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 14, Brushes.Red);
                           TileText.MaxTextWidth = Core.tileRect.Width - 11;

                           g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + 11, Core.tileRect.Y + 11));

                           g.DrawText(EmptyTileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - EmptyTileText.Height / 2));
                        }
                     }
                  }

                  if(ShowTileGridLines)
                  {
                     g.DrawRectangle(null, EmptyTileBorders, new Rect(Core.tileRect.X, Core.tileRect.Y, Core.tileRect.Width, Core.tileRect.Height));

                     if(tilePoint == Core.centerTileXYLocation)
                     {
                        FormattedText TileText = new FormattedText("CENTER:" + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                     else
                     {
                        FormattedText TileText = new FormattedText("TILE: " + tilePoint.ToString(), System.Globalization.CultureInfo.CurrentUICulture, FlowDirection.LeftToRight, tileTypeface, 16, Brushes.Red);
                        g.DrawText(TileText, new System.Windows.Point(Core.tileRect.X + Core.tileRect.Width / 2 - EmptyTileText.Width / 2, Core.tileRect.Y + Core.tileRect.Height / 2 - TileText.Height / 2));
                     }
                  }
               }
            }
             }
             finally
             {
            Core.tileDrawingListLock.ReleaseReaderLock();
            Core.Matrix.LeaveReadLock();
             }
        }
Beispiel #14
0
        static void ProcessLoadTask(LoadTask task, string ctid)
        {
            try
            {
                #region -- execute --

                var m = task.Core.Matrix.GetTileWithReadLock(task.Zoom, task.Pos);
                if (!m.NotEmpty)
                {
                    Debug.WriteLine(ctid + " - try load: " + task);

                    Tile t = new Tile(task.Zoom, task.Pos);

                    foreach (var tl in task.Core.provider.Overlays)
                    {
                        int retry = 0;
                        do
                        {
                            PureImage img = null;
                            Exception ex = null;

                            if (task.Zoom >= task.Core.provider.MinZoom && (!task.Core.provider.MaxZoom.HasValue || task.Zoom <= task.Core.provider.MaxZoom))
                            {
                                if (task.Core.skipOverZoom == 0 || task.Zoom <= task.Core.skipOverZoom)
                                {
                                    // tile number inversion(BottomLeft -> TopLeft)
                                    if (tl.InvertedAxisY)
                                    {
                                        img = GMaps.Instance.GetImageFrom(tl, new GPoint(task.Pos.X, task.Core.maxOfTiles.Height - task.Pos.Y), task.Zoom, out ex);
                                    }
                                    else // ok
                                    {
                                        img = GMaps.Instance.GetImageFrom(tl, task.Pos, task.Zoom, out ex);
                                    }
                                }
                            }

                            if (img != null && ex == null)
                            {
                                if (task.Core.okZoom < task.Zoom)
                                {
                                    task.Core.okZoom = task.Zoom;
                                    task.Core.skipOverZoom = 0;
                                    Debug.WriteLine("skipOverZoom disabled, okZoom: " + task.Core.okZoom);
                                }
                            }
                            else if (ex != null)
                            {
                                if ((task.Core.skipOverZoom != task.Core.okZoom) && (task.Zoom > task.Core.okZoom))
                                {
                                    if (ex.Message.Contains("(404) Not Found"))
                                    {
                                        task.Core.skipOverZoom = task.Core.okZoom;
                                        Debug.WriteLine("skipOverZoom enabled: " + task.Core.skipOverZoom);
                                    }
                                }
                            }

                            // check for parent tiles if not found
                            if (img == null && task.Core.okZoom > 0 && task.Core.fillEmptyTiles && task.Core.Provider.Projection is MercatorProjection)
                            {
                                int zoomOffset = task.Zoom > task.Core.okZoom ? task.Zoom - task.Core.okZoom : 1;
                                long Ix = 0;
                                GPoint parentTile = GPoint.Empty;

                                while (img == null && zoomOffset < task.Zoom)
                                {
                                    Ix = (long)Math.Pow(2, zoomOffset);
                                    parentTile = new GMap.NET.GPoint((task.Pos.X / Ix), (task.Pos.Y / Ix));
                                    img = GMaps.Instance.GetImageFrom(tl, parentTile, task.Zoom - zoomOffset++, out ex);
                                }

                                if (img != null)
                                {
                                    // offsets in quadrant
                                    long Xoff = Math.Abs(task.Pos.X - (parentTile.X * Ix));
                                    long Yoff = Math.Abs(task.Pos.Y - (parentTile.Y * Ix));

                                    img.IsParent = true;
                                    img.Ix = Ix;
                                    img.Xoff = Xoff;
                                    img.Yoff = Yoff;

                                    // wpf
                                    //var geometry = new RectangleGeometry(new Rect(Core.tileRect.X + 0.6, Core.tileRect.Y + 0.6, Core.tileRect.Width + 0.6, Core.tileRect.Height + 0.6));
                                    //var parentImgRect = new Rect(Core.tileRect.X - Core.tileRect.Width * Xoff + 0.6, Core.tileRect.Y - Core.tileRect.Height * Yoff + 0.6, Core.tileRect.Width * Ix + 0.6, Core.tileRect.Height * Ix + 0.6);

                                    // gdi+
                                    //System.Drawing.Rectangle dst = new System.Drawing.Rectangle((int)Core.tileRect.X, (int)Core.tileRect.Y, (int)Core.tileRect.Width, (int)Core.tileRect.Height);
                                    //System.Drawing.RectangleF srcRect = new System.Drawing.RectangleF((float)(Xoff * (img.Img.Width / Ix)), (float)(Yoff * (img.Img.Height / Ix)), (img.Img.Width / Ix), (img.Img.Height / Ix));
                                }
                            }

                            if (img != null)
                            {
                                Debug.WriteLine(ctid + " - tile loaded: " + img.Data.Length / 1024 + "KB, " + task);
                                {
                                    t.AddOverlay(img);
                                }
                                break;
                            }
                            else
                            {
                                if (ex != null)
                                {
                                    lock (task.Core.FailedLoads)
                                    {
                                        if (!task.Core.FailedLoads.ContainsKey(task))
                                        {
                                            task.Core.FailedLoads.Add(task, ex);

                                            if (task.Core.OnEmptyTileError != null)
                                            {
                                                if (!task.Core.RaiseEmptyTileError)
                                                {
                                                    task.Core.RaiseEmptyTileError = true;
                                                    task.Core.OnEmptyTileError(task.Zoom, task.Pos);
                                                }
                                            }
                                        }
                                    }
                                }

                                if (task.Core.RetryLoadTile > 0)
                                {
                                    Debug.WriteLine(ctid + " - ProcessLoadTask: " + task + " -> empty tile, retry " + retry);
                                    {
                                        Thread.Sleep(1111);
                                    }
                                }
                            }
                        }
                        while (++retry < task.Core.RetryLoadTile);
                    }

                    if (t.HasAnyOverlays && task.Core.IsStarted)
                    {
                        task.Core.Matrix.SetTile(t);
                    }
                    else
                    {
                        t.Dispose();
                    }
                }

                #endregion
            }
            catch (Exception ex)
            {
                Debug.WriteLine(ctid + " - ProcessLoadTask: " + ex.ToString());
            }
            finally
            {
                if (task.Core.Refresh != null)
                {
                    task.Core.Refresh.Set();
                }
            }
        }
Beispiel #15
0
        void AddLoadTask(LoadTask t)
        {
            if (tileLoadQueue4Tasks == null)
            {
                lock (tileLoadQueue4)
                {
                    if (tileLoadQueue4Tasks == null)
                    {
                        tileLoadQueue4Tasks = new List<Task>();

                        while (tileLoadQueue4Tasks.Count < GThreadPoolSize)
                        {
                            Debug.WriteLine("creating ProcessLoadTask: " + tileLoadQueue4Tasks.Count);

                            tileLoadQueue4Tasks.Add(Task.Factory.StartNew(delegate ()
                            {
                                string ctid = "ProcessLoadTask[" + Thread.CurrentThread.ManagedThreadId + "]";
                                Thread.CurrentThread.Name = ctid;

                                Debug.WriteLine(ctid + ": started");
                                do
                                { 
                                    if (tileLoadQueue4.Count == 0)
                                    {
                                        Debug.WriteLine(ctid + ": ready");

                                        if (Interlocked.Increment(ref loadWaitCount) >= GThreadPoolSize)
                                        {
                                            Interlocked.Exchange(ref loadWaitCount, 0);
                                            OnLoadComplete(ctid);
                                        }
                                    }
                                    ProcessLoadTask(tileLoadQueue4.Take(), ctid);
                                }
                                while (!tileLoadQueue4.IsAddingCompleted);

                                Debug.WriteLine(ctid + ": exit");

                            }, TaskCreationOptions.LongRunning));
                        }
                    }
                }
            }
            tileLoadQueue4.Add(t);
        }