예제 #1
0
파일: Layer.cs 프로젝트: pheepi/WmsViewer
        public virtual void Draw(IViewport view, Graphics canvas, WebRequestsPool pool)
        {
            // Viewport is readonly.
            Debug.Assert(view != null, "Viewport is missing!");
            Debug.Assert(canvas != null, "Canvas is missing!");
            Debug.Assert(pool != null, "WebRequestsPool is necessary for image downloading!");

            var builder = new StringBuilder();

            GetVisibleLayerNames(builder, IsCrsSupportedByParents());

            if (builder.Length > 0)
            {
                var newView = view.Copy();
                newView.ReduceViewBox(Wms.MaxWidth, Wms.MaxHeight);
                var newImage = new MapImage(builder.ToString(), Wms.CRSId, newView, ImageFormat,
                                            IsTransparent, BgColor);

                try
                {
                    // We cannot work with variable directly,
                    // because another thread could rewrite it during the work.
                    var oldImage = ReleaseImage();
                    try
                    {
                        if (IsVisible)
                        {
                            // Are we downloading?
                            if (AutoUpdate && Wms.IsDownloadingEnabled)
                            {
                                if ((oldImage == null) || (!newImage.Equals(oldImage)))
                                {
                                    var requested = newImage;
                                    newImage = null;        // Do not dispose the object
                                    pool.PutRequest(this, requested, requested.GetImageAddress(Wms));
                                    if (oldImage != null)
                                    {
                                        oldImage.Draw(view, canvas);
                                    }
                                }
                                else
                                {
                                    // If the situation changes and there is requested the same image
                                    // that already exists in the layer, outdated downloading is running
                                    // at this moment and it must be interrupted.
                                    pool.RemoveRequest(this);
                                    oldImage.Draw(view, canvas);
                                }
                            }
                            else
                            {
                                // Downloading must be interrupted.
                                pool.RemoveRequest(this);
                                if (oldImage != null)
                                {
                                    // Use an image with different CRS is nonsense.
                                    if (oldImage.CRSEquals(newImage))
                                    {
                                        oldImage.Draw(view, canvas);
                                    }
                                    else
                                    {
                                        oldImage.Dispose();
                                        oldImage = null;        // Erase old image
                                    }
                                }
                            }
                        }
                        else
                        {
                            if ((oldImage != null) && (!newImage.Equals(oldImage)))
                            {
                                oldImage.Dispose();
                                oldImage = null;        // Erase old image
                            }
                        }
                    }
                    finally
                    {
                        // If another thread save new image, we prefer it.
                        SetOrErase(oldImage);
                    }
                }
                finally
                {
                    if (newImage != null)
                    {
                        newImage.Dispose();
                    }
                }
            }
            else
            {
                EraseImage(pool);
            }
        }