Esempio n. 1
0
        /// <summary>
        /// Setup the Bitmap scaling (for icons)
        /// </summary>
        private void SetupBitmapScaleHandler()
        {
            ContextMenuDpiHandler = contextMenu.AttachDpiHandler();

            var dpiChangeSubscription = DpiHandler.OnDpiChangeInfo.Subscribe(info =>
            {
                switch (info.DpiChangeEventType)
                {
                case DpiChangeEventTypes.Before:
                    // Change the ImageScalingSize before setting the bitmaps
                    var width = DpiHandler.ScaleWithDpi(coreConfiguration.IconSize.Width, info.NewDpi);
                    var size  = new Size(width, width);
                    contextMenu.SuspendLayout();
                    contextMenu.ImageScalingSize   = size;
                    contextmenu_quicksettings.Size = new Size(170, width + 8);
                    break;

                case DpiChangeEventTypes.After:
                    // Redraw the form
                    contextMenu.ResumeLayout(true);
                    contextMenu.Refresh();
                    notifyIcon.Icon = GreenshotResources.GetGreenshotIcon();
                    break;
                }
            });

            var contextMenuResourceScaleHandler = BitmapScaleHandler.WithComponentResourceManager(ContextMenuDpiHandler, GetType(), (bitmap, dpi) => bitmap.ScaleIconForDisplaying(dpi));

            contextMenuResourceScaleHandler.AddTarget(contextmenu_capturewindow, "contextmenu_capturewindow.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_capturearea, "contextmenu_capturearea.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_capturelastregion, "contextmenu_capturelastregion.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_capturefullscreen, "contextmenu_capturefullscreen.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_captureclipboard, "contextmenu_captureclipboard.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_openfile, "contextmenu_openfile.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_settings, "contextmenu_settings.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_help, "contextmenu_help.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_donate, "contextmenu_donate.Image");
            contextMenuResourceScaleHandler.AddTarget(contextmenu_exit, "contextmenu_exit.Image");

            // this is special handling, for the icons which come from the executables
            var exeBitmapScaleHandler = BitmapScaleHandler.Create <string>(ContextMenuDpiHandler,
                                                                           (path, dpi) => PluginUtils.GetCachedExeIcon(path, 0, dpi >= 120),
                                                                           (bitmap, dpi) => bitmap.ScaleIconForDisplaying(dpi));

            exeBitmapScaleHandler.AddTarget(contextmenu_captureie, PluginUtils.GetExePath("iexplore.exe"));

            // Add cleanup
            Application.ApplicationExit += (sender, args) =>
            {
                dpiChangeSubscription.Dispose();
                ContextMenuDpiHandler.Dispose();
                contextMenuResourceScaleHandler.Dispose();
                exeBitmapScaleHandler.Dispose();
            };
        }
Esempio n. 2
0
        /// <summary>
        ///     This method will create and show the destination picker menu
        /// </summary>
        /// <param name="addDynamics">Boolean if the dynamic values also need to be added</param>
        /// <param name="surface">The surface which can be exported</param>
        /// <param name="captureDetails">Details for the surface</param>
        /// <param name="destinations">The list of destinations to show</param>
        /// <returns></returns>
        protected ExportInformation ShowPickerMenu(bool addDynamics, ISurface surface, ICaptureDetails captureDetails, IEnumerable <IDestination> destinations)
        {
            var menu = new ContextMenuStrip
            {
                Tag      = null,
                TopLevel = true
            };
            var dpiHandler         = menu.AttachDpiHandler();
            var bitmapScaleHandler = BitmapScaleHandler.Create <IDestination>(
                dpiHandler,
                (destination, dpi) => destination.GetDisplayIcon(dpi),
                (bitmap, d) => bitmap.ScaleIconForDisplaying(d));

            dpiHandler.OnDpiChanged.Subscribe(dpi =>
            {
                var width             = DpiHandler.ScaleWithDpi(CoreConfiguration.IconSize.Width, dpi);
                var size              = new Size(width, width);
                menu.ImageScalingSize = size;
            });

            // Generate an empty ExportInformation object, for when nothing was selected.
            var exportInformation = new ExportInformation("", GreenshotLanguage.SettingsDestinationPicker);

            menu.Closing += (source, eventArgs) =>
            {
                Log.Debug().WriteLine("Close reason: {0}", eventArgs.CloseReason);
                switch (eventArgs.CloseReason)
                {
                case ToolStripDropDownCloseReason.AppFocusChange:
                    if (menu.Tag == null)
                    {
                        // Do not allow the close if the tag is not set, this means the user clicked somewhere else.
                        eventArgs.Cancel = true;
                    }
                    else
                    {
                        Log.Debug().WriteLine("Letting the menu 'close' as the tag is set to '{0}'", menu.Tag);
                    }
                    break;

                case ToolStripDropDownCloseReason.ItemClicked:
                case ToolStripDropDownCloseReason.CloseCalled:
                    // The ContextMenuStrip can be "closed" for these reasons.
                    break;

                case ToolStripDropDownCloseReason.Keyboard:
                    // Dispose as the close is clicked
                    if (!captureDetails.HasDestination("Editor"))
                    {
                        surface.Dispose();
                        surface = null;
                    }
                    break;

                default:
                    eventArgs.Cancel = true;
                    break;
                }
            };
            menu.MouseEnter += (sender, args) =>
            {
                // in case the menu has been unfocused, focus again so that dropdown menus will still open on mouseenter
                if (!menu.ContainsFocus)
                {
                    menu.Focus();
                }
            };
            foreach (var destination in destinations)
            {
                // Fix foreach loop variable for the delegate
                var item = destination.GetMenuItem(addDynamics, menu,
                                                   async(sender, e) =>
                {
                    var toolStripMenuItem  = sender as ToolStripMenuItem;
                    var clickedDestination = (IDestination)toolStripMenuItem?.Tag;
                    if (clickedDestination == null)
                    {
                        return;
                    }
                    menu.Tag = clickedDestination.Designation;
                    // Export
                    exportInformation = await clickedDestination.ExportCaptureAsync(true, surface, captureDetails);
                    if (exportInformation != null && exportInformation.ExportMade)
                    {
                        Log.Info().WriteLine("Export to {0} success, closing menu", exportInformation.DestinationDescription);
                        // close menu
                        menu.Close();
                        menu.Dispose();
                        // Cleanup surface, only if there is no editor in the destinations and we didn't export to the editor
                        if (!captureDetails.HasDestination("Editor") && !"Editor".Equals(clickedDestination.Designation))
                        {
                            surface.Dispose();
                            surface = null;
                        }
                    }
                    else
                    {
                        Log.Info().WriteLine("Export cancelled or failed, showing menu again");

                        // Make sure a click besides the menu don't close it.
                        menu.Tag = null;

                        // This prevents the problem that the context menu shows in the task-bar
                        ShowMenuAtCursor(menu);
                    }
                }, bitmapScaleHandler
                                                   );
                if (item != null)
                {
                    menu.Items.Add(item);
                }
            }
            // Close
            menu.Items.Add(new ToolStripSeparator());
            var closeItem = new ToolStripMenuItem(GreenshotLanguage.Close)
            {
                Image = GreenshotResources.GetBitmap("Close.Image")
            };

            closeItem.Click += (sender, args) =>
            {
                // This menu entry is the close itself, we can dispose the surface
                menu.Close();
                menu.Dispose();
                // Only dispose if there is a destination which keeps the capture
                if (captureDetails.HasDestination("Editor"))
                {
                    return;
                }

                surface.Dispose();
                surface = null;
            };
            menu.Items.Add(closeItem);

            ShowMenuAtCursor(menu);
            return(exportInformation);
        }