53132


ご質問させていただきます｡

DateTimePickerでユーザーに年月までしか選択させたくないです｡  
以下の画像のように月をクリックすると､その月のカレンダーが表示されてしまいますが､  
そうではなく､datetimepickerのvalueを2016/02/01で入れて､入力を終了させたいのです｡

[![画像の説明をここに入力](https://i.stack.imgur.com/oe0CP.jpg)](https://i.stack.imgur.com/oe0CP.jpg)

ちなみにDateTimePickerのテキストはFormatでyyyy/mmとする事で年月までしか表示させないようにする事はできました｡  
DateTimePickerで上記のような制御は可能でしょうか｡

もしくは､他の良い方法がございましたら､ご教授ください｡  
よろしくお願いします｡


CC BY-SA 4.0
2016-02-05T04:43:25.617
21731
2019-03-02T15:45:49.740
2019-03-02T13:42:52.633
76
12388
question
c#
DateTimePickerでユーザーに月までしか選択させない


表示に関しては`Format`プロパティを`Custom`にし、`CustomFormat`プロパティに`yyyy年
MM月`などの書式を設定すればよいと思います。

この状態でも`Value`には年月以外の値も含まれている場合がありますが、これに関してはイベントか派生クラスで値を丸めるしかないです。基本的には`new
DateTime(year, month, 1)`のような処理を変更時や値の取得時に行えばよいです。

[code]

    private void dateTimePicker1_ValueChanged(object sender, EventArgs e)
    {
        var v = dateTimePicker1.Value;
        dateTimePicker1.Value = new DateTime(v.Year, v.Month, 1);
    }
    
[/code]

なお上の方法ではすべてのコントロールにイベントを設定する必要がありますが、もっと本質的に対処したい場合は`DateTimePicker`の派生型を実装してください。


CC BY-SA 3.0
2016-02-05T05:30:11.160
21735
2016-02-05T05:41:46.537
2016-02-05T05:41:46.537
5750
5750
21731
answer


<https://stackoverflow.com/questions/34846455/how-can-i-set-the-
datetimepicker-dropdown-to-show-months-only>  
↑こちらと同様な質問かと思ったのですが、違いましたでしょうか。

<https://stackoverflow.com/questions/15014280/how-can-i-programmatically-
close-the-dropdown-calendar-of-a-datetimepicker-or-up>  
↑値が変更されたタイミングでドロップダウンを閉じるには、ShowUpDownプロパティで対応すればよさそうです。

ただしドロップダウンの初期表示時や、値が変更されない場合の対応も含めて、  
日のカレンダーを表示しないようにする方法はわかりませんでした。  
（Windows Formsの場合）


CC BY-SA 3.0
2016-02-05T06:20:39.100
21737
2016-02-05T06:20:39.100
2017-05-23T12:38:55.250
-1
13314
21731
answer


Pao@Office の 村井です。  
私も入用だったので、こんな感じで作ってみました。荒いですが、わかりやすいかと  
は思います。  
ご参考まで。

[code]

        bool flgカレンダー = false;
        int yyyy = 0;
        DateTimePicker dt_;
        private void dt_DropDown(object sender, EventArgs e)
        {
            dt_ = (DateTimePicker)sender;
            tmカレンダー.Enabled = true;
            flgカレンダー = true;
            yyyy = ((DateTime)dt_.Value).Year;
        }
    
        private void dt_CloseUp(object sender, EventArgs e)
        {
            tmカレンダー.Enabled = false;
            flgカレンダー = false;
    
        }
        private void tmカレンダー_Tick(object sender, EventArgs e)
        {
            tmカレンダー.Enabled = false;
    
            dt_.Select();
            SendKeys.SendWait("^{UP}"); // Ctrl↑キー送信
    
    
        }
        private void dt_ValueChanged(object sender, EventArgs e)
        {
            dt_ = (DateTimePicker)sender;
            if (flgカレンダー)
            {
                if (yyyy != ((DateTime)dt_.Value).Year)
                {
                    yyyy = ((DateTime)dt_.Value).Year;
                }
                else
                {
                    dt_.Select();
                    SendKeys.SendWait("{ENTER}"); // Enterキー送信
                }
            }
        }
    
[/code]


CC BY-SA 3.0
2016-12-15T07:32:17.230
31165
2016-12-15T08:35:50.563
2016-12-15T08:35:50.563
19927
19927
21731
answer


DropDownイベントに以下を実装します。

[code]

    // pinvoke:
    private const int DTM_GETMONTHCAL = 0x1000 + 8;
    private const int MCM_SETCURRENTVIEW = 0x1000 + 32;
    
    [System.Runtime.InteropServices.DllImport("user32.dll")]
    private static extern IntPtr SendMessage(IntPtr hWnd, int msg, IntPtr wp, IntPtr lp);
    
    private void dateTimePicker1_DropDown(object sender, EventArgs e)
    {
        DateTimePicker myDt = (DateTimePicker)sender;
    
        IntPtr cal = SendMessage(dateTimePicker1.Handle, DTM_GETMONTHCAL, IntPtr.Zero, IntPtr.Zero);
        SendMessage(cal, MCM_SETCURRENTVIEW, IntPtr.Zero, (IntPtr)1);
    
    }
    
[/code]


CC BY-SA 4.0
2019-03-02T08:41:49.697
53132
2019-03-02T15:45:49.740
2019-03-02T15:45:49.740
19110
15667
21731
answer