From 02e945999b65d43627c2f1a17286d09b1fe47c9c Mon Sep 17 00:00:00 2001 From: Ulf Date: Thu, 13 Jun 2013 01:06:54 +0200 Subject: [PATCH] refactor added a timing solution to prevent windows from resizing when changing the frame option --- FileTail.cs | 10 + Preview.Designer.cs | 33 +- Preview.cs | 29 +- ....Designer.cs => PreviewHandler.Designer.cs | 38 +-- MainForm.cs => PreviewHandler.cs | 289 ++++++++++-------- MainForm.resx => PreviewHandler.resx | 0 Program.cs | 2 +- preview toy.csproj | 11 +- preview toy.v11.suo | Bin 80896 -> 80896 bytes 9 files changed, 223 insertions(+), 189 deletions(-) create mode 100644 FileTail.cs rename MainForm.Designer.cs => PreviewHandler.Designer.cs (86%) rename MainForm.cs => PreviewHandler.cs (50%) rename MainForm.resx => PreviewHandler.resx (100%) diff --git a/FileTail.cs b/FileTail.cs new file mode 100644 index 0000000..fa7fce4 --- /dev/null +++ b/FileTail.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace PreviewToy +{ + class FileTail + { + } +} diff --git a/Preview.Designer.cs b/Preview.Designer.cs index 4f65bfb..f542a91 100644 --- a/Preview.Designer.cs +++ b/Preview.Designer.cs @@ -14,28 +14,31 @@ namespace PreviewToy /// private void InitializeComponent() { - this.pictureBox1 = new System.Windows.Forms.PictureBox(); - ((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).BeginInit(); + this.render_area = new System.Windows.Forms.PictureBox(); + ((System.ComponentModel.ISupportInitialize)(this.render_area)).BeginInit(); this.SuspendLayout(); // - // pictureBox1 + // render_area // - this.pictureBox1.Dock = System.Windows.Forms.DockStyle.Fill; - this.pictureBox1.Location = new System.Drawing.Point(0, 0); - this.pictureBox1.Margin = new System.Windows.Forms.Padding(0); - this.pictureBox1.Name = "pictureBox1"; - this.pictureBox1.Size = new System.Drawing.Size(304, 190); - this.pictureBox1.TabIndex = 0; - this.pictureBox1.TabStop = false; - this.pictureBox1.Click += new System.EventHandler(this.pictureBox1_Click); + this.render_area.BackColor = System.Drawing.Color.Black; + this.render_area.BackgroundImageLayout = System.Windows.Forms.ImageLayout.None; + this.render_area.Cursor = System.Windows.Forms.Cursors.Hand; + this.render_area.Dock = System.Windows.Forms.DockStyle.Fill; + this.render_area.Location = new System.Drawing.Point(0, 0); + this.render_area.Margin = new System.Windows.Forms.Padding(0); + this.render_area.Name = "render_area"; + this.render_area.Size = new System.Drawing.Size(48, 30); + this.render_area.TabIndex = 0; + this.render_area.TabStop = false; + this.render_area.Click += new System.EventHandler(this.render_area_Click); // // Preview // this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; - this.ClientSize = new System.Drawing.Size(304, 190); + this.ClientSize = new System.Drawing.Size(48, 30); this.ControlBox = false; - this.Controls.Add(this.pictureBox1); + this.Controls.Add(this.render_area); this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.SizableToolWindow; this.MaximizeBox = false; this.MinimizeBox = false; @@ -46,14 +49,14 @@ namespace PreviewToy this.Text = "Preview"; this.TopMost = true; this.Load += new System.EventHandler(this.Preview_Load); - ((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.render_area)).EndInit(); this.ResumeLayout(false); } #endregion - private System.Windows.Forms.PictureBox pictureBox1; + private System.Windows.Forms.PictureBox render_area; } diff --git a/Preview.cs b/Preview.cs index 85c262d..599afda 100644 --- a/Preview.cs +++ b/Preview.cs @@ -14,19 +14,22 @@ namespace PreviewToy public IntPtr sourceWindow; private DwmApi.DWM_THUMBNAIL_PROPERTIES m_ThumbnailProperties; private bool has_been_set_up = false; - private PreviewToyMain spawner; + private PreviewToyHandler spawner; - public Preview(IntPtr sourceWindow, String title, PreviewToyMain spawner, Size size) + public Preview(IntPtr sourceWindow, String title, PreviewToyHandler spawner, Size size) { + has_been_set_up = false; this.sourceWindow = sourceWindow; - this.spawner = spawner; - this.Size = size; + this.spawner = spawner; InitializeComponent(); SetUp(); this.Text = title; + + has_been_set_up = true; + } protected override void OnResize(EventArgs e) @@ -69,8 +72,7 @@ namespace PreviewToy m_ThumbnailProperties.rcDestination = new DwmApi.RECT(0, 0, ClientRectangle.Right, ClientRectangle.Bottom); DwmApi.DwmUpdateThumbnailProperties(m_hThumbnail, m_ThumbnailProperties); - - has_been_set_up = true; + } private void Preview_Load(object sender, EventArgs e) @@ -78,11 +80,6 @@ namespace PreviewToy } - private void pictureBox1_Click(object sender, EventArgs e) - { - bring_client_to_foreground(); - } - public void bring_client_to_foreground() { DwmApi.SetForegroundWindow(sourceWindow); @@ -97,5 +94,15 @@ namespace PreviewToy } } + private void render_area_Click(object sender, EventArgs e) + { + bring_client_to_foreground(); + } + + public void set_render_area_size(Size size) + { + this.Size = size; + } + } } \ No newline at end of file diff --git a/MainForm.Designer.cs b/PreviewHandler.Designer.cs similarity index 86% rename from MainForm.Designer.cs rename to PreviewHandler.Designer.cs index 3f7838b..245664d 100644 --- a/MainForm.Designer.cs +++ b/PreviewHandler.Designer.cs @@ -8,7 +8,7 @@ using System.Diagnostics; namespace PreviewToy { - partial class PreviewToyMain + partial class PreviewToyHandler { /// /// Required designer variable. @@ -37,13 +37,11 @@ namespace PreviewToy private void InitializeComponent() { this.components = new System.ComponentModel.Container(); - System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(PreviewToyMain)); + System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(PreviewToyHandler)); this.option_hide_active = new System.Windows.Forms.CheckBox(); this.option_hide_all_if_not_right_type = new System.Windows.Forms.CheckBox(); this.option_unique_layout = new System.Windows.Forms.CheckBox(); this.option_sync_size = new System.Windows.Forms.CheckBox(); - this.list_running_clients = new System.Windows.Forms.ListBox(); - this.label1 = new System.Windows.Forms.Label(); this.option_always_on_top = new System.Windows.Forms.CheckBox(); this.option_show_thumbnail_frames = new System.Windows.Forms.CheckBox(); this.forum_url = new System.Windows.Forms.LinkLabel(); @@ -106,24 +104,6 @@ namespace PreviewToy this.option_sync_size.UseVisualStyleBackColor = true; this.option_sync_size.CheckedChanged += new System.EventHandler(this.option_sync_size_CheckedChanged); // - // list_running_clients - // - this.list_running_clients.FormattingEnabled = true; - this.list_running_clients.Location = new System.Drawing.Point(12, 164); - this.list_running_clients.Name = "list_running_clients"; - this.list_running_clients.Size = new System.Drawing.Size(303, 108); - this.list_running_clients.TabIndex = 6; - this.list_running_clients.SelectedIndexChanged += new System.EventHandler(this.list_running_clients_SelectedIndexChanged); - // - // label1 - // - this.label1.AutoSize = true; - this.label1.Location = new System.Drawing.Point(9, 147); - this.label1.Name = "label1"; - this.label1.Size = new System.Drawing.Size(84, 13); - this.label1.TabIndex = 7; - this.label1.Text = "Running Clients:"; - // // option_always_on_top // this.option_always_on_top.AutoSize = true; @@ -155,7 +135,7 @@ namespace PreviewToy // forum_url // this.forum_url.AutoSize = true; - this.forum_url.Location = new System.Drawing.Point(9, 278); + this.forum_url.Location = new System.Drawing.Point(9, 210); this.forum_url.Name = "forum_url"; this.forum_url.Size = new System.Drawing.Size(94, 13); this.forum_url.TabIndex = 10; @@ -165,7 +145,7 @@ namespace PreviewToy // // previewToyMainBindingSource // - this.previewToyMainBindingSource.DataSource = typeof(PreviewToy.PreviewToyMain); + this.previewToyMainBindingSource.CurrentChanged += new System.EventHandler(this.previewToyMainBindingSource_CurrentChanged); // // option_sync_size_x // @@ -183,18 +163,16 @@ namespace PreviewToy this.option_sync_size_y.TabIndex = 12; this.option_sync_size_y.TextChanged += new System.EventHandler(this.option_sync_size_y_TextChanged); // - // PreviewToyMain + // PreviewToyHandler // this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; - this.ClientSize = new System.Drawing.Size(327, 300); + this.ClientSize = new System.Drawing.Size(246, 232); this.Controls.Add(this.option_sync_size_y); this.Controls.Add(this.option_sync_size_x); this.Controls.Add(this.forum_url); this.Controls.Add(this.option_show_thumbnail_frames); this.Controls.Add(this.option_always_on_top); - this.Controls.Add(this.label1); - this.Controls.Add(this.list_running_clients); this.Controls.Add(this.option_sync_size); this.Controls.Add(this.option_unique_layout); this.Controls.Add(this.option_hide_all_if_not_right_type); @@ -203,7 +181,7 @@ namespace PreviewToy this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon"))); this.Margin = new System.Windows.Forms.Padding(0); this.MaximizeBox = false; - this.Name = "PreviewToyMain"; + this.Name = "PreviewToyHandler"; this.Text = "EVE Online previewer"; this.TopMost = true; this.WindowState = System.Windows.Forms.FormWindowState.Minimized; @@ -220,8 +198,6 @@ namespace PreviewToy private CheckBox option_hide_all_if_not_right_type; private CheckBox option_unique_layout; private CheckBox option_sync_size; - private ListBox list_running_clients; - private Label label1; private BindingSource previewToyMainBindingSource; private CheckBox option_always_on_top; private CheckBox option_show_thumbnail_frames; diff --git a/MainForm.cs b/PreviewHandler.cs similarity index 50% rename from MainForm.cs rename to PreviewHandler.cs index 5e5e836..b60f530 100644 --- a/MainForm.cs +++ b/PreviewHandler.cs @@ -12,20 +12,21 @@ using System.Windows.Threading; namespace PreviewToy { - public partial class PreviewToyMain : Form + public partial class PreviewToyHandler : Form { private Dictionary thumbnails; private DispatcherTimer dispatcherTimer; - private IntPtr last_known_active_window; + private IntPtr last_known_active_window_; private Dictionary> layouts; - private Size sync_size; - private bool is_initialized; - public PreviewToyMain() + private bool frames_were_hidden = false; + private Stopwatch ignoring_size_sync; + + public PreviewToyHandler() { is_initialized = false; @@ -42,14 +43,18 @@ namespace PreviewToy dispatcherTimer.Interval = new TimeSpan(0, 0, 1); dispatcherTimer.Start(); + ignoring_size_sync = new Stopwatch(); + is_initialized = true; } + private void GlassForm_Load(object sender, EventArgs e) { refresh_thumbnails(); } + private void init_options() { option_always_on_top.Checked = Properties.Settings.Default.always_on_top; @@ -57,167 +62,181 @@ namespace PreviewToy option_hide_all_if_not_right_type.Checked = Properties.Settings.Default.hide_all; option_unique_layout.Checked = Properties.Settings.Default.unique_layout; option_sync_size.Checked = Properties.Settings.Default.sync_resize; - sync_size.Width = (int)Properties.Settings.Default.sync_resize_x; - sync_size.Height = (int)Properties.Settings.Default.sync_resize_y; + option_show_thumbnail_frames.Checked = Properties.Settings.Default.show_thumb_frames; } - private void refresh_thumbnails() + + private void spawn_and_kill_previews() { if (!is_initialized) { return; } - var sys_activeWindow = DwmApi.GetForegroundWindow(); - Process[] processes = Process.GetProcessesByName("ExeFile"); List processHandles = new List(); // pop new previews - if (processes.Length > 0) + + foreach (Process process in processes) { - foreach (Process process in processes) + processHandles.Add(process.MainWindowHandle); + + Size sync_size = new Size(); + sync_size.Width = (int)Properties.Settings.Default.sync_resize_x; + sync_size.Height = (int)Properties.Settings.Default.sync_resize_y; + + if (!thumbnails.ContainsKey(process.MainWindowHandle) && process.MainWindowTitle != "") { - processHandles.Add(process.MainWindowHandle); + thumbnails[process.MainWindowHandle] = new Preview(process.MainWindowHandle, "...", this, sync_size); + thumbnails[process.MainWindowHandle].set_render_area_size(sync_size); + + // apply more thumbnail specific options + thumbnails[process.MainWindowHandle].TopMost = Properties.Settings.Default.always_on_top; + set_thumbnail_frame_style(thumbnails[process.MainWindowHandle], Properties.Settings.Default.show_thumb_frames); - if (!thumbnails.ContainsKey(process.MainWindowHandle) && process.MainWindowTitle != "") - { - Size initial_size = new Size(64, 64); - if (option_sync_size.Checked){initial_size = sync_size;} - thumbnails[process.MainWindowHandle] = new Preview(process.MainWindowHandle, "-> " + process.MainWindowTitle + " <-", this, initial_size); - this.list_running_clients.Items.Add(process.MainWindowTitle + " ("+process.MainWindowHandle+")"); - } - else if (thumbnails.ContainsKey(process.MainWindowHandle)) //or update the preview titles - { - thumbnails[process.MainWindowHandle].Text = "-> " + process.MainWindowTitle + " <-"; - } - - - if (sys_activeWindow == process.MainWindowHandle) - { - last_known_active_window = sys_activeWindow; - } } + + else if (thumbnails.ContainsKey(process.MainWindowHandle)) //or update the preview titles + { + thumbnails[process.MainWindowHandle].Text = "-> " + process.MainWindowTitle + " <-"; + } + } - + // clean up old previews - if (thumbnails.Count > 0) - { - List to_be_pruned = new List(); - foreach (IntPtr processHandle in thumbnails.Keys) - { - if (!(processHandles.Contains(processHandle))) - { - to_be_pruned.Add(processHandle); - } - } - foreach (IntPtr processHandle in to_be_pruned) + List to_be_pruned = new List(); + foreach (IntPtr processHandle in thumbnails.Keys) + { + if (!(processHandles.Contains(processHandle))) { - thumbnails[processHandle].Close(); - thumbnails.Remove(processHandle); - layouts.Remove(processHandle); - this.list_running_clients.Items.Remove(processHandle); + to_be_pruned.Add(processHandle); } } - if (thumbnails.Count > 0) + foreach (IntPtr processHandle in to_be_pruned) { - // is the active window an eve window? - bool active_window_is_right_type = false; - foreach (KeyValuePair entry in thumbnails) - { - if (entry.Key == sys_activeWindow || entry.Value.Handle == sys_activeWindow || this.Handle == sys_activeWindow) - { - active_window_is_right_type = true; - } - } + thumbnails[processHandle].Close(); + thumbnails.Remove(processHandle); + layouts.Remove(processHandle); + } + } - // update the list selection - if (active_window_is_right_type) + private void handle_unique_layout(Preview preview, IntPtr last_known_active_window) + { + Dictionary layout; + if (layouts.TryGetValue(last_known_active_window, out layout)) + { + Point new_loc; + if (layout.TryGetValue(preview.Handle, out new_loc)) { - int active_index = list_running_clients.Items.IndexOf(last_known_active_window); - if(active_index != -1) - { - list_running_clients.SetSelected(active_index, true); - } + preview.Location = new_loc; } else { - list_running_clients.ClearSelected(); + // create inner dict + layout[preview.Handle] = preview.Location; } + } + else if ((int)last_known_active_window != 0) + { + // create outer dict + layouts[last_known_active_window] = new Dictionary(); + layouts[last_known_active_window][preview.Handle] = preview.Location; + } + } - // hide, show, resize and move - foreach (KeyValuePair entry in thumbnails) + + private void manage_thumbnail_size_and_position(IntPtr last_known_active_window, IntPtr sys_activeWindow, bool active_window_is_right_type) + { + // hide, show, resize and move + foreach (KeyValuePair entry in thumbnails) + { + if (!active_window_is_right_type && option_hide_all_if_not_right_type.Checked) { - if (!active_window_is_right_type && option_hide_all_if_not_right_type.Checked) - { - entry.Value.Hide(); - } - else if (entry.Key == last_known_active_window && option_hide_active.Checked) - { - entry.Value.Hide(); - } - else - { - entry.Value.Show(); + entry.Value.Hide(); + } + else if (entry.Key == last_known_active_window && option_hide_active.Checked) + { + entry.Value.Hide(); + } + else + { + entry.Value.Show(); - if (option_sync_size.Checked && entry.Value.Handle != sys_activeWindow) - { - entry.Value.Size = this.sync_size; - } - - if (option_unique_layout.Checked) - { - Dictionary layout; - if(layouts.TryGetValue(last_known_active_window, out layout)) - { - Point new_loc; - if (layout.TryGetValue(entry.Value.Handle, out new_loc)) - { - entry.Value.Location = new_loc; - } - else - { - // create inner dict - layout[entry.Value.Handle] = entry.Value.Location; - } - } - else if ((int)last_known_active_window != 0) - { - // create outer dict - layouts[last_known_active_window] = new Dictionary(); - layouts[last_known_active_window][entry.Value.Handle] = entry.Value.Location; - } - } + if (option_unique_layout.Checked) + { + handle_unique_layout(entry.Value, last_known_active_window); } } } } + private bool is_active_window_right_type(IntPtr sys_activeWindow) + { + // is the active window an eve window? + bool active_window_is_right_type = false; + foreach (KeyValuePair entry in thumbnails) + { + if (entry.Key == sys_activeWindow || entry.Value.Handle == sys_activeWindow || this.Handle == sys_activeWindow) + { + active_window_is_right_type = true; + } + } + return active_window_is_right_type; + } - public void set_sync_size(Size sync_size_) + + private void refresh_thumbnails() + { + spawn_and_kill_previews(); + + IntPtr sys_activeWindow = DwmApi.GetForegroundWindow(); + Preview poo; + if( thumbnails.TryGetValue(sys_activeWindow, out poo) ) + { + last_known_active_window_ = sys_activeWindow; + } + + bool active_window_is_right_type = is_active_window_right_type(sys_activeWindow); + manage_thumbnail_size_and_position(last_known_active_window_, sys_activeWindow, active_window_is_right_type); + } + + + public void set_sync_size(Size sync_size) { if (!is_initialized) { return; } - if (option_sync_size.Checked) + if (option_sync_size.Checked && option_show_thumbnail_frames.Checked && ignoring_size_sync.ElapsedMilliseconds > 500) { - this.sync_size = sync_size_; - option_sync_size_x.Text = this.sync_size.Width.ToString(); - option_sync_size_y.Text = this.sync_size.Height.ToString(); + ignoring_size_sync.Stop(); + + option_sync_size_x.Text = sync_size.Width.ToString(); + option_sync_size_y.Text = sync_size.Height.ToString(); + + foreach (KeyValuePair entry in thumbnails) + { + if (entry.Value.Handle != DwmApi.GetForegroundWindow()) + { + entry.Value.set_render_area_size(sync_size); + } + } + } + } public void set_preview_position(IntPtr preview_handle, Point position) { Dictionary layout; - if (layouts.TryGetValue(last_known_active_window, out layout)) + if (layouts.TryGetValue(last_known_active_window_, out layout)) { layout[preview_handle] = position; } - else if((int)last_known_active_window != 0) + else if ((int)last_known_active_window_ != 0) { - layouts[last_known_active_window] = new Dictionary(); - layouts[last_known_active_window][preview_handle] = position; + layouts[last_known_active_window_] = new Dictionary(); + layouts[last_known_active_window_][preview_handle] = position; } } @@ -283,8 +302,7 @@ namespace PreviewToy Properties.Settings.Default.sync_resize_x = x; Properties.Settings.Default.Save(); - this.sync_size.Height = (int)Properties.Settings.Default.sync_resize_y; - this.sync_size.Width = (int)Properties.Settings.Default.sync_resize_x; + set_sync_size(new Size((int)x, (int)y)); } return true; } @@ -292,13 +310,13 @@ namespace PreviewToy private void option_sync_size_x_TextChanged(object sender, EventArgs e) { - if (try_save_size_xy()) { refresh_thumbnails(); } + if (try_save_size_xy()) { } } private void option_sync_size_y_TextChanged(object sender, EventArgs e) { - if (try_save_size_xy()) { refresh_thumbnails(); } + if (try_save_size_xy()) { } } @@ -313,30 +331,49 @@ namespace PreviewToy } + private void set_thumbnail_frame_style(Preview preview, bool show_frames) + { + if (show_frames) + { + preview.FormBorderStyle = FormBorderStyle.SizableToolWindow; + ignoring_size_sync.Stop(); + ignoring_size_sync.Reset(); + ignoring_size_sync.Start(); + } + else + { + preview.FormBorderStyle = FormBorderStyle.None; + } + } + + private void option_show_thumbnail_frames_CheckedChanged(object sender, EventArgs e) { Properties.Settings.Default.show_thumb_frames = option_show_thumbnail_frames.Checked; Properties.Settings.Default.Save(); foreach (var thumbnail in thumbnails) { - if (Properties.Settings.Default.show_thumb_frames) - { - thumbnail.Value.FormBorderStyle = FormBorderStyle.SizableToolWindow; - } - else - { - thumbnail.Value.FormBorderStyle = FormBorderStyle.None; - } + set_thumbnail_frame_style(thumbnail.Value, Properties.Settings.Default.show_thumb_frames); } } + private void list_running_clients_SelectedIndexChanged(object sender, EventArgs e){} + private void linkLabel1_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e) { string url = "https://forums.eveonline.com/default.aspx?g=posts&t=246157"; ProcessStartInfo sInfo = new ProcessStartInfo(new Uri(url).AbsoluteUri); Process.Start(sInfo); } + + + private void previewToyMainBindingSource_CurrentChanged(object sender, EventArgs e) + { + + } + + } } \ No newline at end of file diff --git a/MainForm.resx b/PreviewHandler.resx similarity index 100% rename from MainForm.resx rename to PreviewHandler.resx diff --git a/Program.cs b/Program.cs index 6ca02db..6604c0b 100644 --- a/Program.cs +++ b/Program.cs @@ -12,7 +12,7 @@ namespace PreviewToy { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(true); - Application.Run(new PreviewToyMain()); + Application.Run(new PreviewToyHandler()); } } } \ No newline at end of file diff --git a/preview toy.csproj b/preview toy.csproj index 8857436..ac657ae 100644 --- a/preview toy.csproj +++ b/preview toy.csproj @@ -81,17 +81,18 @@ - + + Form - - MainForm.cs + + PreviewHandler.cs - + Designer - MainForm.cs + PreviewHandler.cs ResXFileCodeGenerator diff --git a/preview toy.v11.suo b/preview toy.v11.suo index ac84e3d1f452e7ce4eddd4ccb9b5de6d49053c64..e5f563442d21ee64fa312e09265301d38cb4a9e2 100644 GIT binary patch delta 3968 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