mirror of
https://git.femboyfinancial.jp/james/lipsync.git
synced 2024-11-22 02:32:04 -08:00
507 lines
22 KiB
C#
507 lines
22 KiB
C#
/*
|
|
* BSplitContainer.cs
|
|
* Copyright (c) 2008-2009 kbinani
|
|
*
|
|
* This file is part of Boare.Lib.AppUtil.
|
|
*
|
|
* Boare.Lib.AppUtil is free software; you can redistribute it and/or
|
|
* modify it under the terms of the BSD License.
|
|
*
|
|
* Boare.Lib.AppUtil is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
*/
|
|
using System;
|
|
using System.ComponentModel;
|
|
using System.Drawing;
|
|
using System.Windows.Forms;
|
|
|
|
namespace Boare.Lib.AppUtil {
|
|
|
|
[Serializable]
|
|
public partial class BSplitContainer : ContainerControl {
|
|
private Orientation m_orientation = Orientation.Horizontal;
|
|
private int m_splitter_distance = 50;
|
|
private int m_panel1_min = 25;
|
|
private int m_panel2_min = 25;
|
|
private int m_splitter_width = 4;
|
|
private bool m_splitter_moving = false;
|
|
private int m_splitter_distance_draft = 50;
|
|
private BSplitterPanel m_panel1;
|
|
private BSplitterPanel m_panel2;
|
|
private System.ComponentModel.IContainer components = null;
|
|
private bool m_splitter_fixed = false;
|
|
private Pen m_panel1_border = null;
|
|
private Pen m_panel2_border = null;
|
|
private System.Windows.Forms.FixedPanel m_fixed_panel;
|
|
private PictureBox m_lbl_splitter;
|
|
private int m_panel2_distance = 1;
|
|
private double m_distance_rate = 0.5;
|
|
|
|
public event SplitterEventHandler SplitterMoved;
|
|
[Browsable(false)]
|
|
public event ControlEventHandler ControlAdded;
|
|
|
|
public BSplitContainer() {
|
|
InitializeComponent();
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_lbl_splitter.Cursor = Cursors.VSplit;
|
|
} else {
|
|
m_lbl_splitter.Cursor = Cursors.HSplit;
|
|
}
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_panel2_distance = this.Width - m_splitter_distance;
|
|
} else {
|
|
m_panel2_distance = this.Height - m_splitter_distance;
|
|
}
|
|
m_distance_rate = m_splitter_distance / (double)(m_splitter_distance + m_panel2_distance);
|
|
}
|
|
|
|
public System.Windows.Forms.FixedPanel FixedPanel {
|
|
get {
|
|
return m_fixed_panel;
|
|
}
|
|
set {
|
|
System.Windows.Forms.FixedPanel old = m_fixed_panel;
|
|
m_fixed_panel = value;
|
|
if ( m_fixed_panel != FixedPanel.None && m_fixed_panel != old ) {
|
|
if ( m_fixed_panel == FixedPanel.Panel1 ) {
|
|
m_panel2.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Left | AnchorStyles.Right;
|
|
if ( m_orientation == Orientation.Vertical ) {
|
|
m_panel1.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
|
|
} else {
|
|
m_panel1.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Left;
|
|
}
|
|
} else {
|
|
m_panel1.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Left | AnchorStyles.Right;
|
|
if ( m_orientation == Orientation.Vertical ) {
|
|
m_panel2.Anchor = AnchorStyles.Bottom | AnchorStyles.Left | AnchorStyles.Right;
|
|
} else {
|
|
m_panel2.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Right;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
public bool IsSplitterFixed {
|
|
get {
|
|
return m_splitter_fixed;
|
|
}
|
|
set {
|
|
m_splitter_fixed = value;
|
|
if ( m_splitter_fixed ) {
|
|
m_lbl_splitter.Cursor = Cursors.Default;
|
|
} else {
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_lbl_splitter.Cursor = Cursors.VSplit;
|
|
} else {
|
|
m_lbl_splitter.Cursor = Cursors.HSplit;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 使用中のリソースをすべてクリーンアップします。
|
|
/// </summary>
|
|
/// <param name="disposing">マネージ リソースが破棄される場合 true、破棄されない場合は false です。</param>
|
|
protected override void Dispose( bool disposing ) {
|
|
if ( disposing && (components != null) ) {
|
|
components.Dispose();
|
|
}
|
|
base.Dispose( disposing );
|
|
}
|
|
|
|
/// <summary>
|
|
/// デザイナ サポートに必要なメソッドです。このメソッドの内容を
|
|
/// コード エディタで変更しないでください。
|
|
/// </summary>
|
|
private void InitializeComponent() {
|
|
this.m_lbl_splitter = new System.Windows.Forms.PictureBox();
|
|
this.m_panel2 = new Boare.Lib.AppUtil.BSplitterPanel();
|
|
this.m_panel1 = new Boare.Lib.AppUtil.BSplitterPanel();
|
|
((System.ComponentModel.ISupportInitialize)(this.m_lbl_splitter)).BeginInit();
|
|
this.SuspendLayout();
|
|
//
|
|
// m_lbl_splitter
|
|
//
|
|
this.m_lbl_splitter.BackColor = System.Drawing.Color.Transparent;
|
|
this.m_lbl_splitter.Location = new System.Drawing.Point( 0, 0 );
|
|
this.m_lbl_splitter.Name = "m_lbl_splitter";
|
|
this.m_lbl_splitter.Size = new System.Drawing.Size( 100, 50 );
|
|
this.m_lbl_splitter.TabIndex = 0;
|
|
this.m_lbl_splitter.TabStop = false;
|
|
this.m_lbl_splitter.MouseMove += new System.Windows.Forms.MouseEventHandler( this.m_lbl_splitter_MouseMove );
|
|
this.m_lbl_splitter.MouseDown += new System.Windows.Forms.MouseEventHandler( this.m_lbl_splitter_MouseDown );
|
|
this.m_lbl_splitter.MouseUp += new System.Windows.Forms.MouseEventHandler( this.m_lbl_splitter_MouseUp );
|
|
//
|
|
// m_panel2
|
|
//
|
|
this.m_panel2.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
|
|
| System.Windows.Forms.AnchorStyles.Left)
|
|
| System.Windows.Forms.AnchorStyles.Right)));
|
|
this.m_panel2.BorderColor = System.Drawing.Color.Black;
|
|
this.m_panel2.Location = new System.Drawing.Point( 0, 103 );
|
|
this.m_panel2.Margin = new System.Windows.Forms.Padding( 0 );
|
|
this.m_panel2.Name = "m_panel2";
|
|
this.m_panel2.Size = new System.Drawing.Size( 441, 245 );
|
|
this.m_panel2.TabIndex = 1;
|
|
this.m_panel2.BorderStyleChanged += new System.EventHandler( this.m_panel2_BorderStyleChanged );
|
|
this.m_panel2.SizeChanged += new System.EventHandler( this.m_panel2_SizeChanged );
|
|
//
|
|
// m_panel1
|
|
//
|
|
this.m_panel1.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
|
|
| System.Windows.Forms.AnchorStyles.Left)
|
|
| System.Windows.Forms.AnchorStyles.Right)));
|
|
this.m_panel1.BorderColor = System.Drawing.Color.Black;
|
|
this.m_panel1.Location = new System.Drawing.Point( 0, 0 );
|
|
this.m_panel1.Margin = new System.Windows.Forms.Padding( 0, 0, 0, 4 );
|
|
this.m_panel1.Name = "m_panel1";
|
|
this.m_panel1.Size = new System.Drawing.Size( 441, 99 );
|
|
this.m_panel1.TabIndex = 0;
|
|
this.m_panel1.BorderStyleChanged += new System.EventHandler( this.m_panel1_BorderStyleChanged );
|
|
this.m_panel1.SizeChanged += new System.EventHandler( this.m_panel1_SizeChanged );
|
|
//
|
|
// SplitContainerEx
|
|
//
|
|
this.Controls.Add( this.m_panel2 );
|
|
this.Controls.Add( this.m_panel1 );
|
|
this.Controls.Add( this.m_lbl_splitter );
|
|
this.Size = new System.Drawing.Size( 441, 348 );
|
|
this.Paint += new System.Windows.Forms.PaintEventHandler( this.SplitContainerEx_Paint );
|
|
((System.ComponentModel.ISupportInitialize)(this.m_lbl_splitter)).EndInit();
|
|
this.ResumeLayout( false );
|
|
}
|
|
|
|
private void SplitContainerEx_Paint( object sender, PaintEventArgs e ) {
|
|
bool panel1_visible = true;
|
|
if ( Orientation == Orientation.Horizontal ) {
|
|
if ( m_panel1.Width == 0 ) {
|
|
panel1_visible = false;
|
|
}
|
|
} else {
|
|
if ( m_panel1.Height == 0 ) {
|
|
panel1_visible = false;
|
|
}
|
|
}
|
|
if ( m_panel1.BorderStyle == BorderStyle.FixedSingle && panel1_visible ) {
|
|
if ( m_panel1_border == null ) {
|
|
m_panel1_border = new Pen( m_panel1.BorderColor );
|
|
} else {
|
|
if ( !m_panel1.BorderColor.Equals( m_panel1_border.Color ) ) {
|
|
m_panel1_border = new Pen( m_panel1.BorderColor );
|
|
}
|
|
}
|
|
e.Graphics.DrawRectangle( m_panel1_border,
|
|
new Rectangle( m_panel1.Left - 1, m_panel1.Top - 1, m_panel1.Width + 1, m_panel1.Height + 1) );
|
|
}
|
|
|
|
bool panel2_visible = true;
|
|
if ( Orientation == Orientation.Horizontal ) {
|
|
if ( m_panel2.Width == 0 ) {
|
|
panel2_visible = false;
|
|
}
|
|
} else {
|
|
if ( m_panel2.Height == 0 ) {
|
|
panel2_visible = false;
|
|
}
|
|
}
|
|
if ( m_panel2.BorderStyle == BorderStyle.FixedSingle && panel2_visible ) {
|
|
if ( m_panel2_border == null ) {
|
|
m_panel2_border = new Pen( m_panel2.BorderColor );
|
|
} else {
|
|
if ( !m_panel2.BorderColor.Equals( m_panel2_border.Color ) ) {
|
|
m_panel2_border = new Pen( m_panel2.BorderColor );
|
|
}
|
|
}
|
|
e.Graphics.DrawRectangle( m_panel2_border,
|
|
new Rectangle( m_panel2.Left - 1, m_panel2.Top - 1, m_panel2.Width + 1, m_panel2.Height + 1 ) );
|
|
}
|
|
}
|
|
|
|
private void m_panel2_BorderStyleChanged( object sender, EventArgs e ) {
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
}
|
|
|
|
private void m_panel1_BorderStyleChanged( object sender, EventArgs e ) {
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
}
|
|
|
|
private void m_panel2_SizeChanged( object sender, EventArgs e ) {
|
|
m_panel2.Invalidate( true );
|
|
}
|
|
|
|
private void m_panel1_SizeChanged( object sender, EventArgs e ) {
|
|
m_panel1.Invalidate( true );
|
|
}
|
|
|
|
public int Panel1MinSize {
|
|
get {
|
|
return m_panel1_min;
|
|
}
|
|
set {
|
|
int min_splitter_distance = value;
|
|
if ( m_splitter_distance < min_splitter_distance && min_splitter_distance > 0 ) {
|
|
m_splitter_distance = min_splitter_distance;
|
|
}
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, value, m_panel2_min, false );
|
|
}
|
|
}
|
|
|
|
public int Panel2MinSize {
|
|
get {
|
|
return m_panel2_min;
|
|
}
|
|
set {
|
|
int max_splitter_distance = (m_orientation == Orientation.Horizontal) ?
|
|
this.Width - m_splitter_width - value :
|
|
this.Height - m_splitter_width - value;
|
|
if ( m_splitter_distance > max_splitter_distance && max_splitter_distance > 0 ) {
|
|
m_splitter_distance = max_splitter_distance;
|
|
}
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, m_panel1_min, value, false );
|
|
}
|
|
}
|
|
|
|
public int SplitterWidth {
|
|
get {
|
|
return m_splitter_width;
|
|
}
|
|
set {
|
|
if ( value < 1 ) {
|
|
value = 1;
|
|
}
|
|
UpdateLayout( m_splitter_distance, value, m_panel1_min, m_panel2_min, false );
|
|
}
|
|
}
|
|
|
|
private bool UpdateLayout( int splitter_distance, int splitter_width, int panel1_min, int panel2_min, bool check_only ) {
|
|
Point mouse = this.PointToClient( Control.MousePosition );
|
|
int pad1 = (m_panel1.BorderStyle == BorderStyle.FixedSingle) ? 1 : 0;
|
|
int pad2 = (m_panel2.BorderStyle == BorderStyle.FixedSingle) ? 1 : 0;
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
int p1 = splitter_distance;
|
|
if ( p1 < 0 ) {
|
|
p1 = 0;
|
|
} else if ( this.Width < p1 + splitter_width ) {
|
|
p1 = this.Width - splitter_width;
|
|
}
|
|
int p2 = this.Width - p1 - splitter_width;
|
|
if ( check_only ) {
|
|
if ( p1 < panel1_min || p2 < panel2_min ) {
|
|
return false;
|
|
}
|
|
} else {
|
|
if ( p1 < panel1_min ) {
|
|
p1 = panel1_min;
|
|
}
|
|
p2 = this.Width - p1 - splitter_width;
|
|
if ( p2 < panel2_min ) {
|
|
p2 = panel2_min;
|
|
//return false;
|
|
}
|
|
}
|
|
if ( !check_only ) {
|
|
m_panel1.Left = pad1;
|
|
m_panel1.Top = pad1;
|
|
m_panel1.Width = (p1 - 2 * pad1 >= 0) ? (p1 - 2 * pad1) : 0;
|
|
m_panel1.Height = (this.Height - 2 * pad1 >= 0) ? (this.Height - 2 * pad1) : 0;
|
|
|
|
m_panel2.Left = p1 + splitter_width + pad2;
|
|
m_panel2.Top = pad2;
|
|
m_panel2.Width = (p2 - 2 * pad2 >= 0) ? (p2 - 2 * pad2) : 0;
|
|
m_panel2.Height = (this.Height - 2 * pad2 >= 0) ? (this.Height - 2 * pad2) : 0;
|
|
|
|
m_splitter_distance = p1;
|
|
m_panel2_distance = this.Width - m_splitter_distance;
|
|
m_distance_rate = m_splitter_distance / (double)(m_splitter_distance + m_panel2_distance);
|
|
if ( SplitterMoved != null ) {
|
|
SplitterMoved( this, new SplitterEventArgs( mouse.X, mouse.Y, p1, 0 ) );
|
|
}
|
|
m_splitter_width = splitter_width;
|
|
m_panel1_min = panel1_min;
|
|
m_panel2_min = panel2_min;
|
|
|
|
m_lbl_splitter.Left = p1;
|
|
m_lbl_splitter.Top = 0;
|
|
m_lbl_splitter.Width = splitter_width;
|
|
m_lbl_splitter.Height = this.Height;
|
|
}
|
|
return true;
|
|
} else {
|
|
int p1 = splitter_distance;
|
|
if ( p1 < 0 ) {
|
|
p1 = 0;
|
|
} else if ( this.Height < p1 + splitter_width ) {
|
|
p1 = this.Height - splitter_width;
|
|
}
|
|
int p2 = this.Height - p1 - splitter_width;
|
|
if ( check_only ) {
|
|
if ( p1 < panel1_min || p2 < panel2_min ) {
|
|
return false;
|
|
}
|
|
} else {
|
|
if ( p1 < panel1_min ) {
|
|
p1 = panel1_min;
|
|
}
|
|
p2 = this.Height - p1 - splitter_width;
|
|
if ( p2 < panel2_min ) {
|
|
p2 = panel2_min;
|
|
//return false;
|
|
}
|
|
}
|
|
if ( !check_only ) {
|
|
m_panel1.Left = pad1;
|
|
m_panel1.Top = pad1;
|
|
m_panel1.Width = (this.Width - 2 * pad1 >= 0) ? (this.Width - 2 * pad1) : 0;
|
|
m_panel1.Height = (p1 - 2 * pad1 >= 0) ? (p1 - 2 * pad1) : 0;
|
|
|
|
m_panel2.Left = pad2;
|
|
m_panel2.Top = p1 + splitter_width + pad2;
|
|
m_panel2.Width = (this.Width - 2 * pad2 >= 0) ? (this.Width - 2 * pad2) : 0;
|
|
m_panel2.Height = (p2 - 2 * pad2 >= 0) ? (p2 - 2 * pad2) : 0;
|
|
|
|
m_splitter_distance = p1;
|
|
m_panel2_distance = this.Height - m_splitter_distance;
|
|
m_distance_rate = m_splitter_distance / (double)(m_splitter_distance + m_panel2_distance);
|
|
if ( SplitterMoved != null ) {
|
|
SplitterMoved( this, new SplitterEventArgs( mouse.X, mouse.Y, 0, p1 ) );
|
|
}
|
|
m_splitter_width = splitter_width;
|
|
m_panel1_min = panel1_min;
|
|
m_panel2_min = panel2_min;
|
|
|
|
m_lbl_splitter.Left = 0;
|
|
m_lbl_splitter.Top = p1;
|
|
m_lbl_splitter.Width = this.Width;
|
|
m_lbl_splitter.Height = splitter_width;
|
|
}
|
|
return true;
|
|
}
|
|
}
|
|
|
|
public int SplitterDistance {
|
|
get {
|
|
return m_splitter_distance;
|
|
}
|
|
set {
|
|
UpdateLayout( value, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_panel2_distance = this.Width - m_splitter_distance;
|
|
} else {
|
|
m_panel2_distance = this.Height - m_splitter_distance;
|
|
}
|
|
}
|
|
}
|
|
|
|
public Orientation Orientation {
|
|
get {
|
|
return m_orientation;
|
|
}
|
|
set {
|
|
if ( m_orientation != value ) {
|
|
m_orientation = value;
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_lbl_splitter.Cursor = Cursors.VSplit;
|
|
} else {
|
|
m_lbl_splitter.Cursor = Cursors.HSplit;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public BSplitterPanel Panel1 {
|
|
get {
|
|
return m_panel1;
|
|
}
|
|
}
|
|
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public BSplitterPanel Panel2 {
|
|
get {
|
|
return m_panel2;
|
|
}
|
|
}
|
|
|
|
protected override void OnSizeChanged( EventArgs e ) {
|
|
#if DEBUG
|
|
Console.WriteLine( "BSplitContainer+OnSizeChanged" );
|
|
//Console.WriteLine( " FixedPanel=" + FixedPanel );
|
|
//Console.WriteLine( " m_splitter_distance=" + m_splitter_distance );
|
|
Console.WriteLine( " Width=" + Width );
|
|
Console.WriteLine( " Height=" + Height );
|
|
//Console.WriteLine( " m_panel2_distance=" + m_panel2_distance );
|
|
#endif
|
|
base.OnSizeChanged( e );
|
|
if ( Width <= 0 || Height <= 0 ) {
|
|
return;
|
|
}
|
|
if ( m_fixed_panel == FixedPanel.Panel2 ) {
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_splitter_distance = this.Width - m_panel2_distance;
|
|
} else {
|
|
m_splitter_distance = this.Height - m_panel2_distance;
|
|
}
|
|
} else if ( m_fixed_panel == FixedPanel.None ) {
|
|
#if DEBUG
|
|
//Console.WriteLine( " m_distance_rate=" + m_distance_rate );
|
|
#endif
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_splitter_distance = (int)(this.Width * m_distance_rate);
|
|
} else {
|
|
m_splitter_distance = (int)(this.Height * m_distance_rate);
|
|
}
|
|
}
|
|
UpdateLayout( m_splitter_distance, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
}
|
|
|
|
private void m_lbl_splitter_MouseDown( object sender, MouseEventArgs e ) {
|
|
if ( !m_splitter_fixed ) {
|
|
m_splitter_moving = true;
|
|
m_splitter_distance_draft = m_splitter_distance;
|
|
this.Cursor = (m_orientation == Orientation.Horizontal) ? Cursors.VSplit : Cursors.HSplit;
|
|
m_lbl_splitter.BackColor = SystemColors.ControlDark;
|
|
m_lbl_splitter.BringToFront();
|
|
}
|
|
}
|
|
|
|
private void m_lbl_splitter_MouseUp( object sender, MouseEventArgs e ) {
|
|
if ( m_splitter_moving ) {
|
|
m_splitter_moving = false;
|
|
UpdateLayout( m_splitter_distance_draft, m_splitter_width, m_panel1_min, m_panel2_min, false );
|
|
this.Cursor = Cursors.Default;
|
|
m_lbl_splitter.BackColor = SystemColors.Control;
|
|
}
|
|
}
|
|
|
|
private void m_lbl_splitter_MouseMove( object sender, MouseEventArgs e ) {
|
|
base.OnMouseMove( e );
|
|
if ( m_splitter_fixed ) {
|
|
return;
|
|
}
|
|
Point mouse_local = this.PointToClient( Control.MousePosition );
|
|
if ( m_splitter_moving ) {
|
|
int new_distance = m_splitter_distance;
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
new_distance = mouse_local.X;
|
|
} else {
|
|
new_distance = mouse_local.Y;
|
|
}
|
|
if ( UpdateLayout( new_distance, m_splitter_width, m_panel1_min, m_panel2_min, true ) ) {
|
|
m_splitter_distance_draft = new_distance;
|
|
if ( m_orientation == Orientation.Horizontal ) {
|
|
m_lbl_splitter.Left = m_splitter_distance_draft;
|
|
} else {
|
|
m_lbl_splitter.Top = m_splitter_distance_draft;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|