mirror of
https://git.femboyfinancial.jp/james/lipsync.git
synced 2024-11-29 13:21:59 -08:00
265 lines
9.8 KiB
C#
265 lines
9.8 KiB
C#
/*
|
|
* Common.cs
|
|
* Copyright (c) 2007-2009 kbinani
|
|
*
|
|
* This file is part of LipSync.
|
|
*
|
|
* LipSync is free software; you can redistribute it and/or
|
|
* modify it under the terms of the BSD License.
|
|
*
|
|
* LipSync 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.Collections.Generic;
|
|
using System.Text;
|
|
using System.Drawing;
|
|
using System.Drawing.Imaging;
|
|
using System.IO;
|
|
using System.Runtime.InteropServices;
|
|
using System.Windows.Forms;
|
|
|
|
namespace LipSync {
|
|
|
|
/// <summary>
|
|
/// LipSync共用の関数
|
|
/// </summary>
|
|
public class Common {
|
|
private static string m_log_file = "";
|
|
private static StreamWriter m_sw = null;
|
|
private static SaveFileDialog s_dialog = null;
|
|
public static Color CURVE_X = Color.Black;
|
|
public static Color CURVE_Y = Color.White;
|
|
public static Color CURVE_SCALE = Color.Orange;
|
|
public static Color CURVE_ALPHA = Color.Red;
|
|
public static Color CURVE_ROTATE = Color.Navy;
|
|
|
|
/// <summary>
|
|
/// ファイルダイアログのFilterに指定しようとしている文字列がエラーを起こさないかどうかを確かめます
|
|
/// </summary>
|
|
/// <param name="filter"></param>
|
|
/// <returns></returns>
|
|
public static bool CheckFilterValidity( string filter ) {
|
|
if ( s_dialog == null ) {
|
|
s_dialog = new SaveFileDialog();
|
|
}
|
|
try {
|
|
s_dialog.Filter = filter;
|
|
return true;
|
|
} catch {
|
|
return false;
|
|
}
|
|
}
|
|
|
|
public static void DebugWriteLine( string s ) {
|
|
#if DEBUG
|
|
#if MONO
|
|
Console.WriteLine( s );
|
|
System.Diagnostics.Trace.WriteLine( s );
|
|
System.Diagnostics.Debug.WriteLine( s );
|
|
#else
|
|
//System.Diagnostics.Debug.WriteLine( s );
|
|
Console.WriteLine( s );
|
|
#endif
|
|
#endif
|
|
}
|
|
|
|
public static Image GetThumbnailImage( Image image, int width, int height ) {
|
|
Bitmap res = new Bitmap( width, height, PixelFormat.Format32bppArgb );
|
|
if ( image == null ) {
|
|
return res;
|
|
}
|
|
int w = image.Width;
|
|
int h = image.Height;
|
|
float ASPECTO = (float)width / (float)height;
|
|
float aspecto = (float)w / (float)h;
|
|
float order = 1f; //拡大率
|
|
int top = 0; //描画位置y座標
|
|
int left = 0; //描画位置x座標
|
|
if ( ASPECTO > aspecto ) {
|
|
// サムネイルのほうが横長
|
|
order = (float)height / (float)h;
|
|
left = (int)(width - order * w) / 2;
|
|
} else {
|
|
// サムネイルのほうが縦長
|
|
order = (float)width / (float)w;
|
|
top = (int)(height - order * h) / 2;
|
|
}
|
|
using ( Graphics g = Graphics.FromImage( res ) ) {
|
|
g.Clear( Color.Transparent );
|
|
g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
|
|
g.DrawImage( image, left, top, w * order, h * order );
|
|
}
|
|
return res;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 2つの整数の最大公約数を返します。
|
|
/// </summary>
|
|
/// <param name="m"></param>
|
|
/// <param name="n"></param>
|
|
/// <returns></returns>
|
|
public static long GetGCD( long m, long n ) {
|
|
if ( n > m ) {
|
|
long a = n;
|
|
n = m;
|
|
m = a;
|
|
}
|
|
while ( true ) {
|
|
if ( n == 0 ) {
|
|
return m;
|
|
}
|
|
long quotient = m / n;
|
|
long odd = m - n * quotient;
|
|
if ( odd == 0 ) {
|
|
return n;
|
|
}
|
|
m = n;
|
|
n = odd;
|
|
}
|
|
}
|
|
|
|
|
|
public static Point PointFromPointF( PointF point_f ) {
|
|
return new Point( (int)point_f.X, (int)point_f.Y );
|
|
}
|
|
|
|
|
|
public static Size SizeFromSizeF( SizeF size_f ) {
|
|
return new Size( (int)size_f.Width, (int)size_f.Height );
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
/// 画像から不透明領域を検出する。
|
|
/// </summary>
|
|
/// <param name="bmp"></param>
|
|
/// <returns></returns>
|
|
public static Rectangle GetNonTransparentRegion( Bitmap bmp ) {
|
|
if ( bmp.PixelFormat != PixelFormat.Format32bppArgb ) {
|
|
return new Rectangle();
|
|
}
|
|
BitmapData bmpdat = bmp.LockBits(
|
|
new Rectangle( 0, 0, bmp.Width, bmp.Height ),
|
|
ImageLockMode.ReadOnly,
|
|
PixelFormat.Format32bppArgb
|
|
);
|
|
|
|
int stride = bmpdat.Stride;
|
|
|
|
int ymax = 0;
|
|
int ymin = (bmp.Height - 1) * stride;
|
|
int xmax = 0;
|
|
int xmin = (bmp.Width - 1) * 4;
|
|
const byte ZERO = 0;
|
|
unsafe {
|
|
byte* dat = (byte*)(void*)bmpdat.Scan0;
|
|
int xend = bmp.Width * 4;
|
|
int yend;
|
|
for ( int x = 0; x < xend; x += 4 ) {
|
|
// yminを決める
|
|
yend = ymin;//ymin* stride;
|
|
for ( int y = 0; y <= yend; y += stride ) {
|
|
if ( dat[x + y + 3] != ZERO ) {
|
|
//ymin = Math.Min( ymin, y / stride );
|
|
ymin = Math.Min( ymin, y );
|
|
break;
|
|
}
|
|
}
|
|
|
|
// ymaxを決める
|
|
yend = ymax;// ymax * stride;
|
|
for ( int y = (bmp.Height - 1) * stride; y >= yend; y -= stride ) {
|
|
if ( dat[x + y + 3] != ZERO ) {
|
|
//ymax = Math.Max( ymax, y / stride );
|
|
ymax = Math.Max( ymax, y );
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
yend = ymax;// ymax * stride;
|
|
for ( int y = ymin; y <= yend; y += stride ) {
|
|
// xminを決める
|
|
for ( int x = 0; x < xmin; x += 4 ) {
|
|
if ( dat[x + y + 3] != ZERO ) {
|
|
//xmin = Math.Min( xmin, x / 4 );
|
|
xmin = Math.Min( xmin, x );
|
|
break;
|
|
}
|
|
}
|
|
|
|
// xmaxを決める
|
|
for ( int x = (bmp.Width - 1) * 4; x >= xmax; x -= 4 ) {
|
|
if ( dat[x + y + 3] != ZERO ) {
|
|
//xmax = Math.Max( xmax, x / 4 );
|
|
xmax = Math.Max( xmax, x );
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
if ( xmax <= xmin || ymax <= ymin ) {
|
|
xmin = 0;
|
|
xmax = bmp.Width - 1;
|
|
ymin = 0;
|
|
ymax = bmp.Height - 1;
|
|
} else {
|
|
xmin = xmin / 4;
|
|
xmax = xmax / 4;
|
|
ymin = ymin / stride;
|
|
ymax = ymax / stride;
|
|
}
|
|
}
|
|
bmp.UnlockBits( bmpdat );
|
|
return new Rectangle( xmin, ymin, xmax - xmin + 1, ymax - ymin + 1 );
|
|
}
|
|
|
|
public static void LogPush( Exception ex ) {
|
|
LogPush( ex.Source + Environment.NewLine + ex.Message + Environment.NewLine + ex.StackTrace );
|
|
}
|
|
public static void LogPush( string procedure, string message_type, string message ) {
|
|
LogPush( procedure + ";" + message_type + ";" + message );
|
|
}
|
|
static void LogPush( string message ) {
|
|
if ( m_sw == null ) {
|
|
m_log_file = Path.Combine( Application.StartupPath, "error.log" );
|
|
m_sw = new StreamWriter( m_log_file, true, Encoding.Unicode );
|
|
m_sw.WriteLine( "************************************************************************" );
|
|
m_sw.WriteLine( "Logger started : " + DateTime.Now.ToString() );
|
|
m_sw.WriteLine( "------------------------------------------------------------------------" );
|
|
}
|
|
m_sw.WriteLine( DateTime.Now.ToString() + ";" + message );
|
|
m_sw.Flush();
|
|
}
|
|
|
|
public static void LogClose() {
|
|
if ( m_sw != null ) {
|
|
m_sw.Close();
|
|
m_sw = null;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 指定したパスのファイルからイメージを読み込みます
|
|
/// </summary>
|
|
/// <param name="fpath">イメージファイルへのパス</param>
|
|
/// <returns></returns>
|
|
public static Image ImageFromFile( string fpath ) {
|
|
Bitmap result = null;
|
|
if ( File.Exists( fpath ) ) {
|
|
using ( FileStream fs = new FileStream( fpath, FileMode.Open, FileAccess.Read ) ) {
|
|
Image temp = Image.FromStream( fs );
|
|
result = new Bitmap( temp.Width, temp.Height, PixelFormat.Format32bppArgb );
|
|
using ( Graphics g = Graphics.FromImage( result ) ) {
|
|
g.DrawImage( temp, 0, 0, temp.Width, temp.Height );
|
|
}
|
|
temp.Dispose();
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
}
|
|
|
|
}
|