1 // Written in the D programming language. 2 /++ 3 + Authors: KanzakiKino 4 + Copyright: KanzakiKino 2018 5 + License: LGPL-3.0 6 ++/ 7 module w4d.widget.popup.base; 8 import w4d.widget.base, 9 w4d.widget.panel, 10 w4d.widget.root, 11 w4d.exception; 12 import gl3n.linalg; 13 14 /// A base widget of popup. 15 class PopupWidget : RootWidget 16 { 17 /// WindowContext of the popup target. 18 protected WindowContext _objectContext; 19 20 protected vec2 _pos, _size; 21 22 /// 23 override void handlePopup ( bool opened, WindowContext w ) 24 { 25 w.requestRedraw(); 26 27 if ( opened ) { 28 _objectContext = w; 29 } else { 30 _objectContext = null; 31 } 32 } 33 34 /// 35 this () 36 { 37 super(); 38 _objectContext = null; 39 40 _pos = vec2(0,0); 41 _size = vec2(0,0); 42 } 43 44 /// Moves the popup to the pos and resize to the size. 45 void move ( vec2 pos, vec2 size ) 46 { 47 _pos = pos; 48 _size = size; 49 requestLayout(); 50 } 51 /// Closes the popup. 52 void close () 53 { 54 enforce( _objectContext, 55 "The popup is not opened yet." ); 56 _objectContext.setPopup( null ); 57 } 58 59 /// 60 override vec2 layout ( vec2 rootlt, vec2 rootsz ) 61 { 62 .Widget.layout( _pos, _size ); 63 64 const rootrb = rootlt + rootsz; 65 66 const lt = style.translate; 67 const rb = lt + style.box.collisionSize; 68 69 auto late = vec2(0,0); 70 if ( lt.x < rootlt.x ) { 71 late.x = rootlt.x - lt.x; 72 } else if ( rb.x > rootrb.x ) { 73 late.x = rootrb.x - rb.x; 74 } 75 if ( lt.y < rootlt.y ) { 76 late.y = rootlt.y - lt.y; 77 } else if ( rb.y > rootrb.y ) { 78 late.y = rootrb.y - rb.y; 79 } 80 81 shift( late ); 82 return vec2(0,0); 83 } 84 }