2013年11月12日火曜日

[c#]DataGridViewのマウスホイールでのスクロールを1行単位にする

こちらのサイトにありました。

 DataGridViewはマウスホイールのスクロールで3行送りです。(OS設定に依存します)
このスクロール量を1行送りに変えます。

DataGridViewを継承したクラスを作って、OnMouseWheelでチョイチョイとすればいい感じになります。

MouseEventArgsコンストラクターの第5引数が若干意味不明です。
なにやら、マウスホイールの1ラッチで120単位の移動量となるとか、説明を見てもよくわかりません。

実行すると、マウスホイールを手前に1ラッチすると、e.Deltaには-120が入っています。
MouseWheelScrollLinesには3が入っています。

つまり、第5引数には-40を設定すれば、1行送りになるかというと、確かにそうなります。
マウスの設定でスクロールする行数を1に変更しても、e.Deltaには-120が入ってきます。
この場合、-120でも1行送りになります。

どういう仕組なの?

よくわかりませんが、結果オーライで行きます。

  1. public class DataGridViewEx : DataGridView  
  2. {  
  3.     // ホイールマウス制御  
  4.     protected override void OnMouseWheel(MouseEventArgs e)  
  5.     {  
  6.         // マウス ホイールを回転したときにスクロールする行数を取得  
  7.         Int32 scroll = SystemInformation.MouseWheelScrollLines;  
  8.   
  9.         // MouseEventArgsクラスの移動量を1行に変更  
  10.         MouseEventArgs ex = new MouseEventArgs(e.Button, e.Clicks, e.X, e.Y, e.Delta / scroll);  
  11.   
  12.         base.OnMouseWheel(ex);  
  13.     }  
  14. }  

2013年11月1日金曜日

[c#]フォームが1つしか表示されないようにする

メインフォームとサブフォームがあって、サブフォームはモードレスで表示する場合に、サブフォームが1つだけ表示されるようにする方法です。


  1. private SubForm _subForm = null;  
  2. private void showSubForm()  
  3. {  
  4.     //フォームが表示されているかの判定  
  5.     if (this._subForm == null || this._subForm.IsDisposed)  
  6.         this._subForm = new PlanListForm();  
  7.   
  8.     if (!this._subForm.Visible)  
  9.     {  
  10.         this._subForm.Show();  
  11.     }  
  12.     else  
  13.     {  
  14.         this._subForm.Activate();  
  15.     }  
  16.   
  17. }  

2013年9月4日水曜日

[SQL Server] SQL Serverでテーブル定義取得(全テーブル)

SQL Serverで、テーブル定義らしいものを取得するクエリです。
これとの違いは、データベース内のすべてのテーブルについて出力します。

  1. select  
  2.  obj.name as 'テーブル名'  
  3. ,col.name as '名称'  
  4. ,(select top 1 name from systypes where systypes.xtype = col.xtype) as '型'  
  5. ,col.length as '桁数'  
  6. ,case isnull(col.scale,0)  
  7.  when 0 then ' '  
  8.  else cast( col.scale as char(10) )  
  9.  end '小数部'  
  10. ,case  col.isnullable  
  11.  when 0 then '○'  
  12.  else ' '  
  13.  end 'nn'  
  14. ,isnull((select case colid when 0 then '' else '○' end  from sysindexkeys as keys where col.id = keys.id  and col.colid = keys.colid and keys.indid = 1),' 'as 'pk'  
  15. ,isnull((select top 1 ex.value from sys.extended_properties as ex where col.id = ex.major_id and ex.minor_id = col.colid and ex.name = 'ms_description' ),' 'as 'コメント'  
  16. from syscolumns as col  
  17. inner join sysobjects as obj on col.id = obj.id  
  18. where obj.name in  (select name from sysobjects where xtype = 'u')  

2013年4月26日金曜日

PowerShot Nが届きました


Canon PowerShot Nが届きました。
動作がキビキビしてて気持ちいいですね。
ゴールデンウィーク中に色々と使って見たいと思います。

2013年4月23日火曜日

[c#]VSテストプロジェクトで単体テストのカバレッジが100%にならなかった点の対策

Visual Studio Team System 2008にてテストプロジェクトを利用して、単体テストを行っています。
また、このエディションではコードカバレッジを取れるので100%にすることも要件にしています。

その中で見た目は処理が通っているのですが、カバレッジが100%にならないケースが出てきました。
以下がその例です。


  1. public void Method01(System.Windows.Forms.Control.ControlCollection list)  
  2. {  
  3.     List<control> wk = new List<control>();  
  4.     foreach (Control tmp in list)  
  5.     {  
  6.         if (tmp is Label) continue;  
  7.         wk.Add(tmp);  
  8.     }  
  9. }  


Collectionをforeachしているだけなのですが、これが問題のようです。
詳しい理由はわかりませんが、裏方さんのコードに通らないパスがあるっポイです。
とにかく、Collectionをforeachするとダメなので、Listをforeachするように変える処理を入れます。


  1. //CollectionをListに変換する  
  2. public List<t> ConvertList<t>(ICollection collection)  
  3. {  
  4.     List<t> ret = new List<t>();  
  5.     IEnumerator tmp = collection.GetEnumerator();  
  6.       
  7.     while(tmp.MoveNext()) {  
  8.         ret.Add((T)tmp.Current);              
  9.     }  
  10.     return ret;  
  11. }  

それで、foreachの所でこのメソッドを使います。


  1. public void Method01(System.Windows.Forms.Control.ControlCollection list)  
  2. {  
  3.     List<control> wk = new List<control>();  
  4.     foreach (Control tmp in ConvertList<Control>(list))  
  5.     {  
  6.         if (tmp is Label) continue;  
  7.         wk.Add(tmp);  
  8.     }  
  9. }  


これでカバレッジが100%になるようになりました。

2013年3月31日日曜日

レンズ修理のつもりでしたが、オーバーホールに。

昨年頃からEF 100-400 4.5-5.6を使っているときに、Err01が頻発するようになってしまいました。
絞り解放だと問題ないのですが、少しでも絞るとErr01に。

これが出ると、本体の電源を入れなおさないと使えないのでイラッとするんです。

ネットで調べてみると、絞りユニットが壊れると発生しやすいとか。

買ったのが2003年の夏。
使い始めて10年、さすがに疲れてきたようです。
見た目的にも、印字はかすれて、ネジからは錆が出ています。


横浜にあるキャノンのサービスセンターに持って行き、詳しい話を聞いてみました。

Err01に関しては、症状からして絞りユニットが壊れている可能性が高いとのこと。
それよりも、レンズのカビがひどい状況だそうです。

10年間、毎日のように海に持って行って、防湿庫にも入れてませんでした。
当然の状況ですよね。

レンズはそのまま入院となりました。



で、2週間が経って無事に退院してきました。

マウント交換、ISユニット交換、絞りユニット交換、各種スイッチユニット交換、レンズの半分以上交換。。。
何から何まで交換されてしまいました。


ISスイッチ形状が少し変わっていました。
それ以外の違いはないようです。

修理費用は車の車検費用くらい掛かってしまいました。


修理票にも大量の記述と、欄に収まらない部品点数です。

ついでにカチッと止まらなくなっていたレンズフードを購入しました。
純正より安かったので、JJCの互換レンズフードです。


CanonEF100-400mm F4.5-5.6L IS用レンズフードET-83C互換品(ホワイト)

これで見た目も中身も新品同様です。
これからは、もうちょっと大切に使っていこうと思います。

2013年2月20日水曜日

[php]翌月の末日の取得

phpにて翌月の末日を取得する方法です。

  1. date("Y-m-t" ,strtotime("+1 month"));  

2013年2月6日水曜日

[Web]キャッシュされた画像の対策

画像ファイルを同じ名前で更新しても、クライアントにキャッシュされた画像があると新しいファイルが表示されず、キャッシュされたファイルが表示されます。

HTMLのメタタグでキャッシュ制御を行っても、それはHTML自体のキャッシュであって、個別の画像ファイルについては、制御出来ないようです。

ファイル名を変えるのが一番の対策なのですが、制限によりそれが出来ませんでした。

そこでとった対策は、画像のファイル名にURLパラメーターをつける事です。


  1. <img alt="画像" src="image.jpg?abc">  
上の「?abc」の部分です。
これを入れるとブラウザ側は「image.jpg?abc」で一連のファイル名と記憶するので、ファイルを入れ替えた時は「image.jpg?efg」とすれば、新しいファイルとして読み込んでくれます。

今回はphpでの対応が可能でしたので、uniqid()関数を使って対応しました。
  1. <img alt="画像" src="image.jpg?<?= uniqid() =>">  
気になる点としては、ブラウザがキャッシュすることによってサーバーの負荷が軽減されているのに、毎回読ませることになってしまう所です。

この点の対策としては、パラメーターに設定する値を最終更新日時のハッシュ値とかタイムスタンプなどにしておけば、更新されないうちは同じキャッシュにヒットします。

諸事情により、今回はuniqid()での対応としました。