private void InitialiseThumbnail(IntPtr source) { if (IntPtr.Zero != thumb) { // release the old thumbnail ReleaseThumbnail(); } if (IntPtr.Zero != source) { // find our parent hwnd target = (HwndSource)HwndSource.FromVisual(this); // if we have one, we can attempt to register the thumbnail if (target != null && 0 == DWM.DwmRegisterThumbnail(target.Handle, source, out this.thumb)) { DWM.ThumbnailProperties props = new DWM.ThumbnailProperties(); props.Visible = false; props.SourceClientAreaOnly = this.ClientAreaOnly; props.Opacity = (byte)(255 * this.Opacity); props.Flags = DWM.ThumbnailFlags.Visible | DWM.ThumbnailFlags.SourceClientAreaOnly | DWM.ThumbnailFlags.Opacity; DWM.DwmUpdateThumbnailProperties(thumb, ref props); } } }
protected override Size MeasureOverride(Size availableSize) { try { DWM.Size size; DWM.DwmQueryThumbnailSourceSize(this.thumb, out size); double scale = 1; // our preferred size is the thumbnail source size // if less space is available, we scale appropriately if (size.Width > availableSize.Width) { scale = availableSize.Width / size.Width; } if (size.Height > availableSize.Height) { scale = Math.Min(scale, availableSize.Height / size.Height); } return(new Size(size.Width * scale, size.Height * scale)); } catch (DllNotFoundException) { } return(new Size()); }
// this is where the magic happens private void Thumbnail_LayoutUpdated(object sender, EventArgs e) { if (IntPtr.Zero == thumb) { InitialiseThumbnail(this.Source); } if (IntPtr.Zero != thumb) { if (!target.RootVisual.IsAncestorOf(this)) { //we are no longer in the visual tree ReleaseThumbnail(); return; } GeneralTransform transform = TransformToAncestor(target.RootVisual); Point a = transform.Transform(new Point(0, 0)); Point b = transform.Transform(new Point(this.ActualWidth, this.ActualHeight)); DWM.ThumbnailProperties props = new DWM.ThumbnailProperties(); props.Visible = true; props.Destination = new DWM.Rect( (int)Math.Ceiling(a.X), (int)Math.Ceiling(a.Y), (int)Math.Ceiling(b.X), (int)Math.Ceiling(b.Y)); props.Flags = DWM.ThumbnailFlags.Visible | DWM.ThumbnailFlags.RectDetination; DWM.DwmUpdateThumbnailProperties(thumb, ref props); } }
private void UpdateThumbnail() { if (IntPtr.Zero != thumb) { DWM.ThumbnailProperties props = new DWM.ThumbnailProperties(); props.SourceClientAreaOnly = this.ClientAreaOnly; props.Opacity = (byte)(255 * this.Opacity); props.Flags = DWM.ThumbnailFlags.SourceClientAreaOnly | DWM.ThumbnailFlags.Opacity; DWM.DwmUpdateThumbnailProperties(thumb, ref props); } }
protected override Size ArrangeOverride(Size finalSize) { try { DWM.Size size; DWM.DwmQueryThumbnailSourceSize(this.thumb, out size); // scale to fit whatever size we were allocated double scale = finalSize.Width / size.Width; scale = Math.Min(scale, finalSize.Height / size.Height); return(new Size(size.Width * scale, size.Height * scale)); } catch (DllNotFoundException) { return(default(Size)); } }
private void ReleaseThumbnail() { DWM.DwmUnregisterThumbnail(thumb); this.thumb = IntPtr.Zero; this.target = null; }