1 /* 2 * Copyright 2016 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #ifndef Window_DEFINED 9 #define Window_DEFINED 10 11 #include "DisplayParams.h" 12 #include "SkRect.h" 13 #include "SkTDArray.h" 14 #include "SkTypes.h" 15 16 class GrContext; 17 class SkCanvas; 18 class SkSurface; 19 class SkSurfaceProps; 20 21 namespace sk_app { 22 23 class WindowContext; 24 25 class Window { 26 public: 27 static Window* CreateNativeWindow(void* platformData); 28 29 virtual ~Window() { this->detach(); } 30 31 virtual void setTitle(const char*) = 0; 32 virtual void show() = 0; 33 34 // JSON-formatted UI state for Android. Do nothing by default 35 virtual void setUIState(const char*) {} 36 37 // Shedules an invalidation event for window if one is not currently pending. 38 // Make sure that either onPaint or markInvalReceived is called when the client window consumes 39 // the the inval event. They unset fIsContentInvalided which allow future onInval. 40 void inval(); 41 42 virtual bool scaleContentToFit() const { return false; } 43 44 enum BackendType { 45 kNativeGL_BackendType, 46 #if SK_ANGLE && defined(SK_BUILD_FOR_WIN) 47 kANGLE_BackendType, 48 #endif 49 #ifdef SK_VULKAN 50 kVulkan_BackendType, 51 #endif 52 #if SK_METAL && defined(SK_BUILD_FOR_MAC) 53 kMetal_BackendType, 54 #endif 55 kRaster_BackendType, 56 57 kLast_BackendType = kRaster_BackendType 58 }; 59 enum { 60 kBackendTypeCount = kLast_BackendType + 1 61 }; 62 63 virtual bool attach(BackendType) = 0; 64 void detach(); 65 66 // input handling 67 enum class Key { 68 kNONE, //corresponds to android's UNKNOWN 69 70 kLeftSoftKey, 71 kRightSoftKey, 72 73 kHome, //!< the home key - added to match android 74 kBack, //!< (CLR) 75 kSend, //!< the green (talk) key 76 kEnd, //!< the red key 77 78 k0, 79 k1, 80 k2, 81 k3, 82 k4, 83 k5, 84 k6, 85 k7, 86 k8, 87 k9, 88 kStar, //!< the * key 89 kHash, //!< the # key 90 91 kUp, 92 kDown, 93 kLeft, 94 kRight, 95 96 // Keys needed by ImGui 97 kTab, 98 kPageUp, 99 kPageDown, 100 kDelete, 101 kEscape, 102 kShift, 103 kCtrl, 104 kOption, // AKA Alt 105 kA, 106 kC, 107 kV, 108 kX, 109 kY, 110 kZ, 111 112 kOK, //!< the center key 113 114 kVolUp, //!< volume up - match android 115 kVolDown, //!< volume down - same 116 kPower, //!< power button - same 117 kCamera, //!< camera - same 118 119 kLast = kCamera 120 }; 121 static const int kKeyCount = static_cast<int>(Key::kLast) + 1; 122 123 enum ModifierKeys { 124 kShift_ModifierKey = 1 << 0, 125 kControl_ModifierKey = 1 << 1, 126 kOption_ModifierKey = 1 << 2, // same as ALT 127 kCommand_ModifierKey = 1 << 3, 128 kFirstPress_ModifierKey = 1 << 4, 129 }; 130 131 enum InputState { 132 kDown_InputState, 133 kUp_InputState, 134 kMove_InputState // only valid for mouse 135 }; 136 137 class Layer { 138 public: 139 Layer() : fActive(true) {} 140 virtual ~Layer() = default; 141 142 bool getActive() { return fActive; } 143 void setActive(bool active) { fActive = active; } 144 145 // return value of 'true' means 'I have handled this event' 146 virtual void onBackendCreated() {} 147 virtual void onAttach(Window* window) {} 148 virtual bool onChar(SkUnichar c, uint32_t modifiers) { return false; } 149 virtual bool onKey(Key key, InputState state, uint32_t modifiers) { return false; } 150 virtual bool onMouse(int x, int y, InputState state, uint32_t modifiers) { return false; } 151 virtual bool onMouseWheel(float delta, uint32_t modifiers) { return false; } 152 virtual bool onTouch(intptr_t owner, InputState state, float x, float y) { return false; } 153 virtual void onUIStateChanged(const SkString& stateName, const SkString& stateValue) {} 154 virtual void onPrePaint() {} 155 virtual void onPaint(SkSurface*) {} 156 virtual void onResize(int width, int height) {} 157 158 private: 159 friend class Window; 160 bool fActive; 161 }; 162 163 void pushLayer(Layer* layer) { 164 layer->onAttach(this); 165 fLayers.push_back(layer); 166 } 167 168 void onBackendCreated(); 169 bool onChar(SkUnichar c, uint32_t modifiers); 170 bool onKey(Key key, InputState state, uint32_t modifiers); 171 bool onMouse(int x, int y, InputState state, uint32_t modifiers); 172 bool onMouseWheel(float delta, uint32_t modifiers); 173 bool onTouch(intptr_t owner, InputState state, float x, float y); // multi-owner = multi-touch 174 void onUIStateChanged(const SkString& stateName, const SkString& stateValue); 175 void onPaint(); 176 void onResize(int width, int height); 177 178 int width() const; 179 int height() const; 180 181 virtual const DisplayParams& getRequestedDisplayParams() { return fRequestedDisplayParams; } 182 virtual void setRequestedDisplayParams(const DisplayParams&, bool allowReattach = true); 183 184 // Actual parameters in effect, obtained from the native window. 185 int sampleCount() const; 186 int stencilBits() const; 187 188 // Returns null if there is not a GPU backend or if the backend is not yet created. 189 GrContext* getGrContext() const; 190 191 protected: 192 Window(); 193 194 SkTDArray<Layer*> fLayers; 195 DisplayParams fRequestedDisplayParams; 196 197 WindowContext* fWindowContext = nullptr; 198 199 virtual void onInval() = 0; 200 201 // Uncheck fIsContentInvalided to allow future inval/onInval. 202 void markInvalProcessed(); 203 204 bool fIsContentInvalidated = false; // use this to avoid duplicate invalidate events 205 206 void visitLayers(std::function<void(Layer*)> visitor); 207 bool signalLayers(std::function<bool(Layer*)> visitor); 208 }; 209 210 } // namespace sk_app 211 #endif 212