OSDN Git Service

Windows APIを実装部に隠蔽してみた。まだ不完全だが。
authorSFPGMR <sfpg@git.sourceforge.jp>
Fri, 29 Apr 2011 10:27:37 +0000 (19:27 +0900)
committerSFPGMR <sfpg@git.sourceforge.jp>
Fri, 29 Apr 2011 10:27:37 +0000 (19:27 +0900)
13 files changed:
wintimer/exception.h
wintimer/sf_com.h
wintimer/sf_windows.cpp
wintimer/sf_windows.h
wintimer/singleton.h
wintimer/stdafx.h
wintimer/taskbar.cpp [new file with mode: 0644]
wintimer/taskbar.h [new file with mode: 0644]
wintimer/toplevel_window.cpp
wintimer/toplevel_window.h
wintimer/winmain.cpp
wintimer/wintimer.vcxproj
wintimer/wintimer.vcxproj.filters

index 41965ea..43198d4 100644 (file)
@@ -31,4 +31,5 @@ namespace sf
        };
 
 
+
 }
\ No newline at end of file
index ff2a8a0..c1e8265 100644 (file)
@@ -3,19 +3,19 @@
   ==============================================================================
 
    This file is part of the Shooting3
-   Copyright 2005-7 by Satoshi Fujiwara.
+   Copyright 2005-11 by Satoshi Fujiwara.
 
-   S.F.Tracker can be redistributed and/or modified under the terms of the
+   mini timer can be redistributed and/or modified under the terms of the
    GNU General Public License, as published by the Free Software Foundation;
    either version 2 of the License, or (at your option) any later version.
 
-   S.F.Tracker is distributed in the hope that it will be useful,
+   mini timer 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.  See the
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
-   along with S.F.Tracker; if not, visit www.gnu.org/licenses or write to the
+   along with mini timer; if not, visit www.gnu.org/licenses or write to the
    Free Software Foundation, Inc., 59 Temple Place, Suite 330, 
    Boston, MA 02111-1307 USA
 
index fae9aed..c4915af 100644 (file)
@@ -17,7 +17,7 @@ EXTERN_C IMAGE_DOS_HEADER __ImageBase;
 
 namespace sf 
 {
-  LRESULT base_window::window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam)
+  LRESULT base_win32_window::window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam)
   {
 
     LRESULT 結果 = 0;
@@ -88,7 +88,7 @@ namespace sf
     return ::DefWindowProcW(hwnd,message,wParam,lParam);
   };
   
-  void base_window::register_class (
+  void base_win32_window::register_class (
     wchar_t * menu_name,
     boost::uint32_t        style ,
     boost::int32_t     cbClsExtra,
@@ -102,12 +102,12 @@ namespace sf
   }
 
   /** デフォルト設定 */
-  void base_window::register_class()
+  void base_win32_window::register_class()
   {
     wnd_class_.reset(new sf::window_class_ex(0,name_,HINST_THISCOMPONENT,thunk_proc_));
   }
 
-  void base_window::create_window()
+  void base_win32_window::create_window()
   {
     // Create the application window.
     //
@@ -133,10 +133,7 @@ namespace sf
       );
   }
 
-
-
-
-  void base_window::show(boost::uint32_t show_flag) 
+  void base_win32_window::show(boost::uint32_t show_flag) 
   {
     //HRESULT hr = S_OK;
     //BOOL enable;
@@ -154,31 +151,23 @@ namespace sf
     //}
     ::ShowWindow(hwnd_,show_flag);
   }
-  void base_window::update() {::UpdateWindow(hwnd_);}
 
-  base_window::~base_window()
+  void base_win32_window::update() {::UpdateWindow(hwnd_);}
+
+  base_win32_window::~base_win32_window()
   {
 
   }
 
-
-  base_window::base_window(const std::wstring& title,const std::wstring& name,bool fit_to_display,float width,float height)
-    : title_(title),name_(name),fit_to_display_(fit_to_display),
-    width_(width),height_(height),thunk_(this,base_window::WndProc),hwnd_(0)
+  base_win32_window::base_win32_window(const std::wstring& title,const std::wstring& name,bool fit_to_display,float width,float height)
+    : title_(title),name_(name),fit_to_display_(fit_to_display),width_(width),height_(height),thunk_(this,base_win32_window::WndProc),hwnd_(0)
   {
     thunk_proc_ = (WNDPROC)thunk_.getCode();
     //create_device_independent_resources();
   }
 
-
-
-  base_window::operator HWND()
-  {
-    return hwnd_;
-  };
-
-  //ID2D1FactoryPtr base_window::factory() { return impl_->factory();};
-  //ID2D1HwndRenderTargetPtr base_window::render_target() { return impl_->render_target();};
-  //IDWriteFactoryPtr base_window::write_factory() {return impl_->write_factory();};
+  //ID2D1FactoryPtr base_win32_window::factory() { return impl_->factory();};
+  //ID2D1HwndRenderTargetPtr base_win32_window::render_target() { return impl_->render_target();};
+  //IDWriteFactoryPtr base_win32_window::write_factory() {return impl_->write_factory();};
 }
 
index dc308b6..7761607 100644 (file)
@@ -3,6 +3,7 @@
 */
 // Windows Header Files:
 #include "exception.h"
+#include "base_window.h"
 #define XBYAK64
 #include "xbyak.h"
 // DLLのリンク
@@ -50,6 +51,12 @@ template <class COM_SMART_PTR > inline void safe_release(COM_SMART_PTR& ptr)
 
 namespace sf{
 
+  template <class Exc> struct throw_if_err
+  {
+    void operator()(HRESULT hr) {if(hr != S_OK){throw Exc(hr);}}
+  };
+
+
   ID2D1BitmapPtr load_bitmap_from_file(
     ID2D1HwndRenderTargetPtr render_target,
     IWICImagingFactoryPtr wic_factory,
@@ -236,19 +243,31 @@ namespace sf{
 
 
   /** window ベースクラス */
-  struct base_window 
+  struct base_win32_window : public base_window 
   {
     typedef boost::signals2::signal<LRESULT (HWND,boost::uint32_t,WPARAM, LPARAM) > on_message_type;
     on_message_type on_message;
-    typedef boost::signals2::signal<void ()> on_render_type;
-    on_render_type on_render;
-    operator HWND();
+    
+    operator HWND() {return hwnd_;};
+    
+    virtual void * raw_handle(){return hwnd_;};
+    virtual void show(boost::uint32_t show_flag);
+    virtual void text(std::wstring& text)
+    {
+      ::SetWindowTextW(*this,text.c_str());
+    };
+
+    virtual void update();
+
   protected:
-    base_window(
+    
+    base_win32_window(
       const std::wstring& title,
       const std::wstring& name,bool fit_to_display,
       float width,float height);
-    ~base_window();
+    
+    ~base_win32_window();
+
     void register_class (
       wchar_t* menu_name,
       boost::uint32_t style, 
@@ -262,21 +281,39 @@ namespace sf{
     /** デフォルト設定 */
     void register_class();
     void create_window();
-    void update();
-    void show(boost::uint32_t show_flag);
+
+    // SetWindowLong API
+    void set_long(int index,long data)
+    {
+      SetLastError(0);
+      if(::SetWindowLongW(hwnd_,index,data) == 0)
+      {
+        long err = 0;
+        if( (err = GetLastError()) != 0){
+          SetLastError(err);
+          throw sf::win32_error_exception();
+        }
+      };
+    }
+
+    bool invalidate_rect(bool erase = false,const RECT * rect_ptr = 0)
+    {
+      return ::InvalidateRect(*this,rect_ptr,erase) == TRUE;
+    }
+
   public:
     virtual LRESULT window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam);
   protected:
     static LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
     {
-      base_window* ptr = reinterpret_cast<base_window*>(hwnd);
+      base_win32_window* ptr = reinterpret_cast<base_win32_window*>(hwnd);
       hwnd = ptr->hwnd_;
       return ptr->window_proc(hwnd,message,wParam,lParam);
     };
 
     // thisとhwndをつなぐthunkクラス
     struct hwnd_this_thunk : public Xbyak::CodeGenerator {
-      hwnd_this_thunk(base_window* impl,WNDPROC proc)
+      hwnd_this_thunk(base_win32_window* impl,WNDPROC proc)
       {
         // rcxにhwndが格納されているので、それをimpl->hwndに保存
         mov(qword[&(impl->hwnd_)],rcx);
@@ -317,6 +354,11 @@ namespace sf{
     std::wstring task_name_;
     boost::uint32_t task_index_;
     HANDLE handle_;
+    std::wstring title_;
+    std::wstring name_;
+    float width_,height_;
+    bool fit_to_display_;
+
   };
 
   struct widget
index 298dff8..fcbea7b 100644 (file)
@@ -2,20 +2,20 @@
 /*
   ==============================================================================
 
-   This file is part of the S.F.Tracker
+   This file is part of the mini timer
    Copyright 2005-7 by Satoshi Fujiwara.
 
-   S.F.Tracker can be redistributed and/or modified under the terms of the
+   mini timer can be redistributed and/or modified under the terms of the
    GNU General Public License, as published by the Free Software Foundation;
    either version 2 of the License, or (at your option) any later version.
 
-   S.F.Tracker is distributed in the hope that it will be useful,
+   mini timer 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.  See the
    GNU General Public License for more details.
 
    You should have received a copy of the GNU General Public License
-   along with S.F.Tracker; if not, visit www.gnu.org/licenses or write to the
+   along with mini timer; if not, visit www.gnu.org/licenses or write to the
    Free Software Foundation, Inc., 59 Temple Place, Suite 330, 
    Boston, MA 02111-1307 USA
 
index 669e7cd..eca6573 100644 (file)
@@ -57,6 +57,7 @@
 //#include <boost/serialization/vector.hpp>
 //#include <boost/serialization/nvp.hpp>
 //#include <boost/serialization/void_cast.hpp>
+
 #include <boost/scoped_ptr.hpp> 
 #include <boost/scoped_array.hpp> 
 #include <boost/shared_ptr.hpp> 
diff --git a/wintimer/taskbar.cpp b/wintimer/taskbar.cpp
new file mode 100644 (file)
index 0000000..834c6b3
--- /dev/null
@@ -0,0 +1,63 @@
+#include "StdAfx.h"
+#include "sf_windows.h"
+#include "taskbar.h"
+
+
+namespace sf {
+
+const int taskbar::none = TBPF_NOPROGRESS;
+const int taskbar::indeterminate = TBPF_INDETERMINATE;
+const int taskbar::normal = TBPF_NORMAL;
+const int taskbar::error = TBPF_ERROR;
+const int taskbar::paused = TBPF_PAUSED;
+
+struct taskbar::impl
+{
+  typedef throw_if_err<sf::taskbar::exception> throw_if_err_;
+
+  impl(){}
+  ~impl()
+  {
+    discard();
+  }
+
+  void create() {
+    throw_if_err_()(taskbar_.CreateInstance(CLSID_TaskbarList));
+  }
+
+  void discard()
+  {
+    safe_release(taskbar_);
+  }
+    
+  void overlay_icon(sf::base_window& w,HICON icon,std::wstring& description)
+  {
+    throw_if_err_()(taskbar_->SetOverlayIcon(reinterpret_cast<HWND>(w.raw_handle()),icon,description.c_str()));
+  }
+
+  void progress_state(sf::base_window& w,TBPFLAG state)
+  {
+    throw_if_err_()(taskbar_->SetProgressState(reinterpret_cast<HWND>(w.raw_handle()),state));
+  }
+
+  void progress_value(sf::base_window& w,boost::uint64_t completed, boost::uint64_t total)
+  {
+    throw_if_err_()(taskbar_->SetProgressValue(reinterpret_cast<HWND>(w.raw_handle()),completed,total));
+  }
+   
+private:
+  _COM_SMARTPTR_TYPEDEF(ITaskbarList4,__uuidof(ITaskbarList4));
+  ITaskbarList4Ptr taskbar_;
+};
+
+   
+taskbar::taskbar() : impl_(new sf::taskbar::impl()) {}
+taskbar::~taskbar() { discard();};
+
+void taskbar::create(){impl_->create();};
+void taskbar::discard(){impl_->discard();};
+void taskbar::overlay_icon(sf::base_window& w,HICON icon,std::wstring& description){impl_->overlay_icon(w,icon,description);};
+void taskbar::progress_state(sf::base_window& w,int state){impl_->progress_state(w,(TBPFLAG)state);};
+void taskbar::progress_value(sf::base_window& w,boost::uint64_t completed, boost::uint64_t total){impl_->progress_value(w,completed,total);};
+
+}
\ No newline at end of file
diff --git a/wintimer/taskbar.h b/wintimer/taskbar.h
new file mode 100644 (file)
index 0000000..216d3ea
--- /dev/null
@@ -0,0 +1,60 @@
+#pragma once
+
+/*
+  ==============================================================================
+
+   This file is part of the mini timer
+   Copyright 2005-10 by Satoshi Fujiwara.
+
+   mini timer can be redistributed and/or modified under the terms of the
+   GNU General Public License, as published by the Free Software Foundation;
+   either version 2 of the License, or (at your option) any later version.
+
+   mini timer 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.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with mini timer; if not, visit www.gnu.org/licenses or write to the
+   Free Software Foundation, Inc., 59 Temple Place, Suite 330, 
+   Boston, MA 02111-1307 USA
+
+  ==============================================================================
+*/
+
+#include "exception.h"
+
+namespace sf
+{
+  
+  struct taskbar : boost::noncopyable
+  {
+    struct exception
+     : public sf::win32_error_exception 
+    {
+      exception(boost::uint32_t hr) : win32_error_exception(hr) {};
+      exception() : win32_error_exception() {} ;
+    };
+
+     taskbar();
+    ~taskbar();
+    void create();
+    void discard();
+    void overlay_icon(sf::base_window& w,HICON icon,std::wstring& description);
+    void progress_state(sf::base_window& w,int state);
+    void progress_value(sf::base_window& w,boost::uint64_t completed, boost::uint64_t total);
+
+    static const int none;
+    static const int indeterminate;
+    static const int normal;
+    static const int error;
+    static const int paused;
+
+  private:
+    struct impl;
+    std::shared_ptr<impl> impl_;
+  };
+
+}
+
index c1939a5..51adbe0 100644 (file)
@@ -5,6 +5,7 @@
 #include <boost/assign/ptr_list_inserter.hpp>
 #include <boost/foreach.hpp>
 #include "toplevel_window.h"
+#include "sf_windows.h"
 #include "exception.h"
 
 #define THROW_IFERR(hres) \
@@ -17,157 +18,42 @@ EXTERN_C IMAGE_DOS_HEADER __ImageBase;
 
 namespace sf 
 {
-  //ID2D1FactoryPtr base_window::factory() { return impl_->factory();};
-  //ID2D1HwndRenderTargetPtr base_window::render_target() { return impl_->render_target();};
-  //IDWriteFactoryPtr base_window::write_factory() {return impl_->write_factory();};
 
+HRESULT EnableBlurBehind(HWND hwnd)
+{
+  HRESULT hr = S_OK;
+
+  //Create and populate the BlurBehind structre
+  DWM_BLURBEHIND bb = {0};
+  //Enable Blur Behind and Blur Region;
+  bb.dwFlags = DWM_BB_ENABLE;
+  bb.fEnable = true;
+  bb.hRgnBlur = NULL;
+
+  //Enable Blur Behind
+  hr = DwmEnableBlurBehindWindow(hwnd, &bb);
+  if (SUCCEEDED(hr))
+  {
+    //do more things
+  }
+  return hr;
+}
  
-  toplevel_window::toplevel_window(const std::wstring& menu_name,const std::wstring& name,
-    bool fit_to_display,float width,float height) 
-    : base_window(menu_name,name,fit_to_display,width,height) , wm_task_bar_create_(0),timer_id_(0),result_time_(INTERVAL_SEC1),status_(active)
+struct toplevel_window::impl : public base_win32_window
+{
+
+  impl(const std::wstring& menu_name,const std::wstring& name,bool fit_to_display,float width = 160,float height = 100) 
+    : base_win32_window(menu_name,name,fit_to_display,width,height) , wm_task_bar_create_(0),timer_id_(0),result_time_(INTERVAL_SEC1),status_(active)
   {
-    on_render.connect(boost::bind(&toplevel_window::render,this));
+    on_render.connect(boost::bind(&impl::render,this));
   };
 
-  toplevel_window::~toplevel_window()
-  {
+  ~impl(){
     safe_release(factory_);
     safe_release(write_factory_);
   };
 
-  void toplevel_window::create_window()
-  {
-
-    // Windowを作成する
-    CreateWindowEx(
-      WS_EX_APPWINDOW,
-      name_.c_str(),
-      title_.c_str(),
-      0 ,
-      CW_USEDEFAULT,
-      CW_USEDEFAULT,
-      static_cast<boost::uint32_t>(ceil(width_ /** dpiX / 96.f*/)),
-      static_cast<boost::uint32_t>(ceil(height_ /** dpiY / 96.f*/)),
-      NULL,
-      NULL,
-      HINST_THISCOMPONENT,
-      this
-      );
-  }
-
-  void toplevel_window::create_device()
-  {
-
-    //         入力_.reset(new input(HINST_THISCOMPONENT,hwnd_));
-    HRESULT hr = S_OK;
-
-
-    //ウィンドウの現在の幅、高さを求める
-    RECT rc;
-    GetClientRect( hwnd_, &rc );
-    boost::uint32_t width = rc.right - rc.left;
-    boost::uint32_t height = rc.bottom - rc.top;
-
-    {
-      //wic_imaging_factory_.CreateInstance(CLSID_WICImagingFactory);
-      //                       bitmap_ = load_bitmap_from_file(render_target_,wic_imaging_factory_,L"myship.png");
-    }
-
-    if(!render_target_)
-    {
-      RECT rc;
-      GetClientRect(hwnd_, &rc);
-
-      D2D1_SIZE_U size = D2D1::SizeU(
-        rc.right - rc.left,
-        rc.bottom - rc.top
-        );
-      
-      const D2D1_PIXEL_FORMAT format =
-          D2D1::PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM,
-                            D2D1_ALPHA_MODE_PREMULTIPLIED);
-      
-      const D2D1_RENDER_TARGET_PROPERTIES target_prop = 
-          D2D1::RenderTargetProperties(D2D1_RENDER_TARGET_TYPE_DEFAULT,format);
-
-      THROW_IFERR(factory_->CreateHwndRenderTarget(
-        target_prop,
-        D2D1::HwndRenderTargetProperties(hwnd_, size,D2D1_PRESENT_OPTIONS_IMMEDIATELY),
-        &render_target_
-        ));
-      // Create a DC render target 
-      //D2D1_RENDER_TARGET_PROPERTIES props = D2D1::RenderTargetProperties(
-      //       D2D1_RENDER_TARGET_TYPE_DEFAULT,
-      //       D2D1::PixelFormat(
-      //               DXGI_FORMAT_B8G8R8A8_UNORM,
-      //               D2D1_ALPHA_MODE_IGNORE
-      //               ) , 0.0, 0.0,
-      //       D2D1_RENDER_TARGET_USAGE_GDI_COMPATIBLE
-      //       );
-
-      //THROW_IFERR(factory_->CreateDCRenderTarget(
-      //       &props,
-      //       &render_target_
-      //       ));
-    }
-  }
-
-  void toplevel_window::discard_device()
-  {
-    safe_release(render_target_);
-  }
-
-  void toplevel_window::create_device_independent_resources()
-  {
-    // Direct2DFactory の生成
-
-    if(!factory_){
-#if defined(DEBUG) || defined(_DEBUG)
-      D2D1_FACTORY_OPTIONS options;
-      options.debugLevel = D2D1_DEBUG_LEVEL_INFORMATION ;
-      THROW_IFERR(D2D1CreateFactory(
-        D2D1_FACTORY_TYPE_SINGLE_THREADED,
-        options,
-        &factory_
-        ));
-#else
-      THROW_IFERR(D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &factory_));
-#endif
-
-    }
-
-    if(!write_factory_){
-      THROW_IFERR(::DWriteCreateFactory(
-        DWRITE_FACTORY_TYPE_SHARED,
-        __uuidof(IDWriteFactory),
-        reinterpret_cast<IUnknown**>(&write_factory_)
-        ));
-    }
-
-
-    //wic_imaging_factory_.CreateInstance(CLSID_WICImagingFactory);
-
-    //thunk_proc_ = (WNDPROC)thunk_.getCode();
-    layout_rect_ = D2D1::RectF(0.0f,0.0f,width_,height_);
-    // Text Formatの作成
-    THROW_IFERR(write_factory_->CreateTextFormat(
-    L"メイリオ",                // Font family name.
-    NULL,                       // Font collection (NULL sets it to use the system font collection).
-    DWRITE_FONT_WEIGHT_REGULAR,
-    DWRITE_FONT_STYLE_NORMAL,
-    DWRITE_FONT_STRETCH_NORMAL,
-    24.0f,
-    L"ja-jp",
-    &write_text_format_
-    ));
-
-  }
-
-  LRESULT toplevel_window::window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam) 
-  {
-
-
+  LRESULT window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam){
     switch (message)
     {
     case WM_CREATE:
@@ -175,7 +61,7 @@ namespace sf
         // TODO:
         create_device();
         wm_task_bar_create_ = RegisterWindowMessage(L"TaskbarButtonCreated");
-        ::SetWindowTextW(hwnd_,L"ミニタイマー(活動中)");
+        text(std::wstring(L"ミニタイマー(活動中)"));
         //MARGINS mgn = {-1,0,0,0};//let,right,top,bottom
         //HRESULT hr = DwmExtendFrameIntoClientArea(hwnd_, &mgn);
         break;
@@ -236,33 +122,33 @@ namespace sf
         {
         case active:
           --result_time_;
-          taskbar_list_->SetProgressValue(hwnd_,result_time_,INTERVAL_SEC1);
+          taskbar_.progress_value(*this,result_time_,INTERVAL_SEC1);
 
           if(result_time_ == 0)
           {
             ::MessageBeep(MB_ICONEXCLAMATION);
             status_ = sleep;
             result_time_ = INTERVAL_SEC2;
-            taskbar_list_->SetProgressState(hwnd_,TBPF_PAUSED);
-            taskbar_list_->SetProgressValue(hwnd_,result_time_,INTERVAL_SEC2);
-            ::SetWindowTextW(hwnd_,L"ミニタイマー(休憩中)");
+            taskbar_.progress_state(*this,taskbar::paused);
+            taskbar_.progress_value(*this,result_time_,INTERVAL_SEC2);
+            text(std::wstring(L"ミニタイマー(休憩中)"));
           }
             ::InvalidateRect(hwnd_,NULL,FALSE);
           break;
         case sleep:
           {
             --result_time_;
-            taskbar_list_->SetProgressValue(hwnd_,result_time_,INTERVAL_SEC2);
+            taskbar_.progress_value(*this,result_time_,INTERVAL_SEC2);
             if(result_time_ == 0)
             {
               ::MessageBeep(MB_OK);
               status_ = active;
               result_time_ = INTERVAL_SEC1;
-              taskbar_list_->SetProgressState(hwnd_,TBPF_INDETERMINATE);
-              taskbar_list_->SetProgressValue(hwnd_,result_time_,INTERVAL_SEC1);
-              ::SetWindowTextW(hwnd_,L"ミニタイマー(活動中)");
+              taskbar_.progress_state(*this,taskbar::indeterminate);
+              taskbar_.progress_value(*this,result_time_,INTERVAL_SEC1);
+              text(std::wstring(L"ミニタイマー(活動中)"));
             }
-            ::InvalidateRect(hwnd_,NULL,FALSE);
+            invalidate_rect();
           }
           break;
         }
@@ -278,10 +164,10 @@ namespace sf
 
     if(message == wm_task_bar_create_)
     {
-      THROW_IFERR(taskbar_list_.CreateInstance(CLSID_TaskbarList,0,CLSCTX_INPROC));
-      taskbar_list_->SetOverlayIcon(hwnd_,NULL,L"ミニタイマー");
-      taskbar_list_->SetProgressState(hwnd_,TBPF_INDETERMINATE);
-      taskbar_list_->SetProgressValue(hwnd_,100,100);
+      taskbar_.create();
+      taskbar_.overlay_icon(*this,NULL,std::wstring(L"ミニタイマー"));
+      taskbar_.progress_state(*this,taskbar::indeterminate);
+      taskbar_.progress_value(*this,100,100);
       // タイマーの設定
       ::SetTimer(hwnd_,(UINT_PTR)&timer_id_,1000,NULL);
     }
@@ -290,7 +176,7 @@ namespace sf
     {
       ::KillTimer(hwnd_,(UINT_PTR)&timer_id_);
       //
-      safe_release(taskbar_list_);
+      taskbar_.discard();
       // 後始末
       discard_device();
       // レンダーターゲットのリリース
@@ -309,16 +195,124 @@ namespace sf
     return ::DefWindowProcW(hwnd,message,wParam,lParam);
   }
 
-  void toplevel_window::main_loop()
+  virtual void create(){
+    create_device_independent_resources();
+    register_class();
+    create_window();
+
+    // 半透明ウィンドウを有効にする。
+    BOOL dwmEnable;
+    DwmIsCompositionEnabled (&dwmEnable); 
+    if (dwmEnable) EnableBlurBehind(*this);
+
+  };
+
+  virtual void discard_device()
   {
-    render();
+    safe_release(render_target_);
   }
 
-  void toplevel_window::render()
-  {
+  virtual void create_device(){
+    //         入力_.reset(new input(HINST_THISCOMPONENT,hwnd_));
+    HRESULT hr = S_OK;
+
+    //ウィンドウの現在の幅、高さを求める
+    RECT rc;
+    GetClientRect( hwnd_, &rc );
+    boost::uint32_t width = rc.right - rc.left;
+    boost::uint32_t height = rc.bottom - rc.top;
+
+    {
+      //wic_imaging_factory_.CreateInstance(CLSID_WICImagingFactory);
+      //                       bitmap_ = load_bitmap_from_file(render_target_,wic_imaging_factory_,L"myship.png");
+    }
+
+    if(!render_target_)
+    {
+      RECT rc;
+      GetClientRect(hwnd_, &rc);
+
+      D2D1_SIZE_U size = D2D1::SizeU(
+        rc.right - rc.left,
+        rc.bottom - rc.top
+        );
+      
+      const D2D1_PIXEL_FORMAT format =
+          D2D1::PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM,
+                            D2D1_ALPHA_MODE_PREMULTIPLIED);
+      
+      const D2D1_RENDER_TARGET_PROPERTIES target_prop = 
+          D2D1::RenderTargetProperties(D2D1_RENDER_TARGET_TYPE_DEFAULT,format);
+
+      THROW_IFERR(factory_->CreateHwndRenderTarget(
+        target_prop,
+        D2D1::HwndRenderTargetProperties(hwnd_, size,D2D1_PRESENT_OPTIONS_IMMEDIATELY),
+        &render_target_
+        ));
+      // Create a DC render target 
+      //D2D1_RENDER_TARGET_PROPERTIES props = D2D1::RenderTargetProperties(
+      //       D2D1_RENDER_TARGET_TYPE_DEFAULT,
+      //       D2D1::PixelFormat(
+      //               DXGI_FORMAT_B8G8R8A8_UNORM,
+      //               D2D1_ALPHA_MODE_IGNORE
+      //               ) , 0.0, 0.0,
+      //       D2D1_RENDER_TARGET_USAGE_GDI_COMPATIBLE
+      //       );
+
+      //THROW_IFERR(factory_->CreateDCRenderTarget(
+      //       &props,
+      //       &render_target_
+      //       ));
+    }
+  }
+
+  virtual void create_device_independent_resources(){
+    // Direct2DFactory の生成
+
+    if(!factory_){
+#if defined(DEBUG) || defined(_DEBUG)
+      D2D1_FACTORY_OPTIONS options;
+      options.debugLevel = D2D1_DEBUG_LEVEL_INFORMATION ;
+      THROW_IFERR(D2D1CreateFactory(
+        D2D1_FACTORY_TYPE_SINGLE_THREADED,
+        options,
+        &factory_
+        ));
+#else
+      THROW_IFERR(D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &factory_));
+#endif
+
+    }
+
+    if(!write_factory_){
+      THROW_IFERR(::DWriteCreateFactory(
+        DWRITE_FACTORY_TYPE_SHARED,
+        __uuidof(IDWriteFactory),
+        reinterpret_cast<IUnknown**>(&write_factory_)
+        ));
+    }
+
+
+    //wic_imaging_factory_.CreateInstance(CLSID_WICImagingFactory);
+
+    //thunk_proc_ = (WNDPROC)thunk_.getCode();
+    layout_rect_ = D2D1::RectF(0.0f,0.0f,width_,height_);
+    // Text Formatの作成
+    THROW_IFERR(write_factory_->CreateTextFormat(
+    L"メイリオ",                // Font family name.
+    NULL,                       // Font collection (NULL sets it to use the system font collection).
+    DWRITE_FONT_WEIGHT_REGULAR,
+    DWRITE_FONT_STYLE_NORMAL,
+    DWRITE_FONT_STRETCH_NORMAL,
+    24.0f,
+    L"ja-jp",
+    &write_text_format_
+    ));
+
+  }
 
+  void render(){
     static float t = 0.0f;
-    
 
     if (render_target_)
     {
@@ -355,8 +349,51 @@ namespace sf
         throw;
       }
     }
+  }
+  void create_window()
+  {
+
+    // Windowを作成する
+    CreateWindowEx(
+      WS_EX_APPWINDOW | WS_EX_TOPMOST,
+      name_.c_str(),
+      title_.c_str(),
+      0 ,
+      CW_USEDEFAULT,
+      CW_USEDEFAULT,
+      static_cast<boost::uint32_t>(ceil(width_ /** dpiX / 96.f*/)),
+      static_cast<boost::uint32_t>(ceil(height_ /** dpiY / 96.f*/)),
+      NULL,
+      NULL,
+      HINST_THISCOMPONENT,
+      this
+      );
+  };
+
+private:
+
+  long wm_task_bar_create_;
+  sf::taskbar taskbar_;
+  UINT timer_id_;
+  static const int INTERVAL_SEC1 = 60 * 15;// 15分
+  static const int INTERVAL_SEC2 = 30;// 30秒
+
+  int result_time_;
+  enum timer_status {
+    active,
+    sleep
   };
 
+  ID2D1FactoryPtr factory_;
+  ID2D1HwndRenderTargetPtr render_target_;
+  IDWriteFactoryPtr write_factory_;
+  IWICImagingFactoryPtr wic_imaging_factory_;
+
+  timer_status status_;
+  IDWriteTextFormatPtr write_text_format_;
+  D2D1_RECT_F layout_rect_;
+};
+
   //
   // Creates a Direct2D bitmap from the specified
   // file name.
@@ -448,25 +485,17 @@ namespace sf
     return bitmap;
   }
 
-  HRESULT EnableBlurBehind(HWND hwnd)
-{
-   HRESULT hr = S_OK;
-
-   //Create and populate the BlurBehind structre
-   DWM_BLURBEHIND bb = {0};
-   //Enable Blur Behind and Blur Region;
-   bb.dwFlags = DWM_BB_ENABLE;
-   bb.fEnable = true;
-   bb.hRgnBlur = NULL;
-
-   //Enable Blur Behind
-   hr = DwmEnableBlurBehindWindow(hwnd, &bb);
-   if (SUCCEEDED(hr))
-   {
-      //do more things
-   }
-   return hr;
-}
+  toplevel_window::toplevel_window(const std::wstring& menu_name,const std::wstring& name,bool fit_to_display,float width ,float height)
+    : impl_(new impl(menu_name,name,fit_to_display,width,height))
+  {
+
+  };
+
+  void * toplevel_window::raw_handle(){return impl_->raw_handle();};
+  void toplevel_window::create(){impl_->create();};
+  void toplevel_window::show(boost::uint32_t show_flag){impl_->show(show_flag);};
+  void toplevel_window::text(std::wstring& text){impl_->text(text);};
+  void toplevel_window::update(){impl_->update();};
 
  toplevel_window_ptr create_toplevel_window
     (
@@ -479,14 +508,7 @@ namespace sf
     )
   {
     toplevel_window* p = new toplevel_window(menu_name,name,fit_to_display,width,height);
-    p->create_device_independent_resources();
-    p->register_class();
-    p->create_window();
-
-    BOOL dwmEnable;
-    DwmIsCompositionEnabled (&dwmEnable); 
-    if (dwmEnable) EnableBlurBehind(p->hwnd_);
-
+    p->create();
     p->show(show_flag);
     p->update();
     return toplevel_window_ptr(p);
index 0b6f006..ff752bf 100644 (file)
@@ -2,7 +2,8 @@
 /*
 */
 // Windows Header Files:
-#include "sf_windows.h"
+#include "base_window.h"
+#include "taskbar.h"
 namespace sf
 {
 
@@ -23,6 +24,7 @@ namespace sf
   /* このクラスは、create_toplevel_window 関数からのみ生成可能 */
   struct toplevel_window : public base_window
   {
+
     friend   toplevel_window_ptr create_toplevel_window
       (
       const std::wstring& menu_name,
@@ -30,46 +32,21 @@ namespace sf
       const boost::uint32_t show_flag,
       bool fit_to_display ,
       float width ,
-      float height
+      float height 
       );
 
-    void main_loop();
-
-    virtual void discard_device();
-    virtual void create_device();
-    virtual void create_device_independent_resources();
+    ~toplevel_window(){};
+    void * raw_handle();
+    void create();
+    void show(boost::uint32_t show_flag);
+    void text(std::wstring& text);
+    void update();
 
-  protected:
-    void render();
-    toplevel_window(const std::wstring& menu_name,const std::wstring& name,bool fit_to_display,float width = 160,float height = 100);
-    void create_window();
-  public:
-    ~toplevel_window();
-    LRESULT toplevel_window::window_proc(HWND hwnd,boost::uint32_t message, WPARAM wParam, LPARAM lParam);
   private:
-    long wm_task_bar_create_;
-    ITaskbarList3Ptr taskbar_list_;
-    UINT timer_id_;
-    static const int INTERVAL_SEC1 = 60 * 15;// 15分
-    static const int INTERVAL_SEC2 = 30;// 30秒
-
-    int result_time_;
-    enum timer_status {
-      active,
-      sleep
-    };
-
-    ID2D1FactoryPtr factory_;
-    ID2D1HwndRenderTargetPtr render_target_;
-    IDWriteFactoryPtr write_factory_;
-    IWICImagingFactoryPtr wic_imaging_factory_;
-
-    timer_status status_;
-    IDWriteTextFormatPtr write_text_format_;
-    D2D1_RECT_F layout_rect_;
-    
+    toplevel_window(const std::wstring& menu_name,const std::wstring& name,bool fit_to_display,float width = 180,float height = 100);
+    // 実装部
+    struct impl;
+    std::shared_ptr<impl> impl_;
   };
-
-
-
 }
\ No newline at end of file
index c136ce1..a4ab8fb 100644 (file)
@@ -1,11 +1,9 @@
 #include "stdafx.h"
-#include "sf_windows.h"
 #include "toplevel_window.h"
+#include "sf_windows.h"
 #include "message_loop.h"
 #include "sf_com.h"
 
-void  MIDIメッセージ到着時(const boost::uint32_t wMsg,const boost::uint32_t midi_message,const boost::uint32_t time_stamp);
-
 /** WinMain */
 int APIENTRY _tWinMain(HINSTANCE hInstance,
                      HINSTANCE hPrevInstance,
index 32969ad..fe296cc 100644 (file)
@@ -45,6 +45,7 @@
       <Optimization>Disabled</Optimization>
       <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
       <StructMemberAlignment>16Bytes</StructMemberAlignment>
+      <AdditionalOptions>/Zm110 %(AdditionalOptions)</AdditionalOptions>
     </ClCompile>
     <Link>
       <GenerateDebugInformation>true</GenerateDebugInformation>
@@ -64,6 +65,7 @@
     </Link>
   </ItemDefinitionGroup>
   <ItemGroup>
+    <ClInclude Include="base_window.h" />
     <ClInclude Include="code_converter.h" />
     <ClInclude Include="dout.h" />
     <ClInclude Include="exception.h" />
     <ClInclude Include="sf_windows.h" />
     <ClInclude Include="singleton.h" />
     <ClInclude Include="stdafx.h" />
+    <ClInclude Include="taskbar.h" />
     <ClInclude Include="toplevel_window.h" />
   </ItemGroup>
   <ItemGroup>
+    <ClCompile Include="base_window.cpp" />
     <ClCompile Include="code_converter.cpp" />
     <ClCompile Include="exception.cpp" />
     <ClCompile Include="logger.cpp" />
@@ -85,6 +89,7 @@
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|x64'">Create</PrecompiledHeader>
     </ClCompile>
+    <ClCompile Include="taskbar.cpp" />
     <ClCompile Include="toplevel_window.cpp" />
     <ClCompile Include="winmain.cpp" />
   </ItemGroup>
index 6e1f002..339cc10 100644 (file)
@@ -2,24 +2,59 @@
 <Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
   <ItemGroup>
     <ClInclude Include="code_converter.h" />
-    <ClInclude Include="dout.h" />
     <ClInclude Include="exception.h" />
     <ClInclude Include="logger.h" />
-    <ClInclude Include="message_loop.h" />
-    <ClInclude Include="sf_com.h" />
-    <ClInclude Include="sf_memory.h" />
     <ClInclude Include="singleton.h" />
-    <ClInclude Include="stdafx.h" />
-    <ClInclude Include="sf_windows.h" />
     <ClInclude Include="toplevel_window.h" />
+    <ClInclude Include="taskbar.h" />
+    <ClInclude Include="base_window.h" />
+    <ClInclude Include="sf_com.h">
+      <Filter>win32</Filter>
+    </ClInclude>
+    <ClInclude Include="sf_memory.h">
+      <Filter>win32</Filter>
+    </ClInclude>
+    <ClInclude Include="sf_windows.h">
+      <Filter>win32</Filter>
+    </ClInclude>
+    <ClInclude Include="dout.h">
+      <Filter>win32</Filter>
+    </ClInclude>
+    <ClInclude Include="stdafx.h">
+      <Filter>win32</Filter>
+    </ClInclude>
+    <ClInclude Include="message_loop.h">
+      <Filter>win32</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="code_converter.cpp" />
-    <ClCompile Include="exception.cpp" />
-    <ClCompile Include="logger.cpp" />
-    <ClCompile Include="stdafx.cpp" />
-    <ClCompile Include="winmain.cpp" />
-    <ClCompile Include="sf_windows.cpp" />
-    <ClCompile Include="toplevel_window.cpp" />
+    <ClCompile Include="base_window.cpp" />
+    <ClCompile Include="sf_windows.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="toplevel_window.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="winmain.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="logger.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="exception.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="stdafx.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+    <ClCompile Include="taskbar.cpp">
+      <Filter>win32</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <Filter Include="win32">
+      <UniqueIdentifier>{ac651b31-e7cb-4909-a4cd-059605cc42dd}</UniqueIdentifier>
+    </Filter>
   </ItemGroup>
 </Project>
\ No newline at end of file