1 // Written by Christopher E. Miller 2 // See the included license.txt for copyright and license details. 3 4 module dfl.picturebox; 5 import core.sys.windows.windows; 6 7 import dfl.base; 8 import dfl.control; 9 import dfl.drawing; 10 import dfl.event; 11 import dfl.exception; 12 13 enum PictureBoxSizeMode : ubyte { 14 15 NORMAL, // Image at upper left of control. 16 17 AUTO_SIZE, // Control sizes to fit image size. 18 19 CENTER_IMAGE, // Image at center of control. 20 21 STRETCH_IMAGE, // Image stretched to fit control. 22 } 23 24 class PictureBox : Control { 25 this() { 26 //resizeRedraw = true; // Redrawn manually in onResize() when necessary. 27 } 28 29 final @property void image(Image img) { 30 if (this.img is img) { 31 return; 32 } 33 34 if (_mode == PictureBoxSizeMode.AUTO_SIZE) { 35 if (img) { 36 clientSize = img.size; 37 } else { 38 clientSize = Size(0, 0); 39 } 40 } 41 42 this.img = img; 43 44 if (created) { 45 invalidate(); 46 } 47 48 onImageChanged(EventArgs.empty); 49 } 50 51 final @property Image image() { 52 return img; 53 } 54 55 final @property void sizeMode(PictureBoxSizeMode sm) { 56 if (_mode == sm) { 57 return; 58 } 59 60 final switch (sm) { 61 case PictureBoxSizeMode.AUTO_SIZE: 62 if (img) { 63 clientSize = img.size; 64 } else { 65 clientSize = Size(0, 0); 66 } 67 break; 68 69 case PictureBoxSizeMode.NORMAL: 70 break; 71 72 case PictureBoxSizeMode.CENTER_IMAGE: 73 break; 74 75 case PictureBoxSizeMode.STRETCH_IMAGE: 76 break; 77 } 78 79 _mode = sm; 80 81 if (created) { 82 invalidate(); 83 } 84 85 onSizeModeChanged(EventArgs.empty); 86 } 87 88 final @property PictureBoxSizeMode sizeMode() { 89 return _mode; 90 } 91 92 @property void borderStyle(BorderStyle bs) { 93 final switch (bs) { 94 case BorderStyle.FIXED_3D: 95 _style(_style() & ~WS_BORDER); 96 _exStyle(_exStyle() | WS_EX_CLIENTEDGE); 97 break; 98 99 case BorderStyle.FIXED_SINGLE: 100 _exStyle(_exStyle() & ~WS_EX_CLIENTEDGE); 101 _style(_style() | WS_BORDER); 102 break; 103 104 case BorderStyle.NONE: 105 _style(_style() & ~WS_BORDER); 106 _exStyle(_exStyle() & ~WS_EX_CLIENTEDGE); 107 break; 108 } 109 110 if (created) { 111 redrawEntire(); 112 } 113 } 114 115 @property BorderStyle borderStyle() { 116 if (_exStyle() & WS_EX_CLIENTEDGE) { 117 return BorderStyle.FIXED_3D; 118 } else if (_style() & WS_BORDER) { 119 return BorderStyle.FIXED_SINGLE; 120 } 121 return BorderStyle.NONE; 122 } 123 124 //EventHandler sizeModeChanged; 125 Event!(PictureBox, EventArgs) sizeModeChanged; 126 //EventHandler imageChanged; 127 Event!(PictureBox, EventArgs) imageChanged; 128 129 protected: 130 131 void onSizeModeChanged(EventArgs ea) { 132 sizeModeChanged(this, ea); 133 } 134 135 void onImageChanged(EventArgs ea) { 136 imageChanged(this, ea); 137 } 138 139 override void onPaint(PaintEventArgs ea) { 140 if (img) { 141 final switch (_mode) { 142 case PictureBoxSizeMode.NORMAL: 143 case PictureBoxSizeMode.AUTO_SIZE: // Drawn the same as normal. 144 img.draw(ea.graphics, 145 Point(0, 0)); 146 break; 147 148 case PictureBoxSizeMode.CENTER_IMAGE: { 149 Size isz; 150 isz = img.size; 151 img.draw(ea.graphics, Point((clientSize.width - isz.width) / 2, 152 (clientSize.height - isz.height) / 2)); 153 } 154 break; 155 156 case PictureBoxSizeMode.STRETCH_IMAGE: 157 img.drawStretched(ea.graphics, 158 Rect(0, 0, clientSize.width, clientSize.height)); 159 break; 160 } 161 } 162 163 super.onPaint(ea); 164 } 165 166 override void onResize(EventArgs ea) { 167 if (PictureBoxSizeMode.CENTER_IMAGE == _mode || PictureBoxSizeMode.STRETCH_IMAGE == _mode) { 168 invalidate(); 169 } 170 171 super.onResize(ea); 172 } 173 174 private: 175 PictureBoxSizeMode _mode = PictureBoxSizeMode.NORMAL; 176 Image img = null; 177 }