Advertisement
Guest User

Untitled

a guest
Jun 10th, 2014
56
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. import com.badlogic.gdx.Input;
  2. import com.badlogic.gdx.graphics.g2d.Batch;
  3. import com.badlogic.gdx.scenes.scene2d.Actor;
  4. import com.badlogic.gdx.scenes.scene2d.InputEvent;
  5. import com.badlogic.gdx.scenes.scene2d.InputListener;
  6. import com.badlogic.gdx.scenes.scene2d.Stage;
  7. import com.badlogic.gdx.scenes.scene2d.Touchable;
  8. import com.badlogic.gdx.scenes.scene2d.ui.Skin;
  9. import com.badlogic.gdx.scenes.scene2d.ui.Table;
  10. import com.badlogic.gdx.scenes.scene2d.utils.Align;
  11. import com.badlogic.gdx.scenes.scene2d.utils.Drawable;
  12.  
  13. /**
  14.  * This is very much like a regular Table, although it has some extra features.
  15.  * It is movable on a Stage, and can be resized by dragging.
  16.  * It can also act modal if needed, and be locked to be inside of the Stage if needed.
  17.  *
  18.  * This is basicly Window from scene2d.ui, with a few modifications.
  19.  *
  20.  * @author Mads Peter Horndrup
  21.  */
  22. public class MovableTable extends Table {
  23.    
  24.     /** Different flags to define different behaviors */
  25.     private boolean isModal, isResizable, isMovable;
  26.    
  27.     /** Maximum pixels from the border where the MovableWindow can be resized */
  28.     private int resizeBorder = 8;
  29.    
  30.     /** Are we currently resizing or moving the MovableWindow?? */
  31.     private boolean dragging;
  32.    
  33.     /** Should we make sure the MovableWindow stays inside the Viewport?? */
  34.     private boolean keepWithinStage;
  35.    
  36.     /** What Actors allow the MovableWindow to be dragged */
  37.     protected Actor[] dragActors;
  38.    
  39.     private MovableTableStyle style;
  40.    
  41.     /** Used to indicate that side of the MovableWindow that is being resized, and if it's being moved */
  42.     static private final int MOVE = 1 << 5;
  43.    
  44.     public MovableTable(Skin skin) {
  45.         this(skin.get(MovableTableStyle.class));
  46.         setSkin(skin);
  47.     }
  48.  
  49.     public MovableTable(Skin skin, String styleName) {
  50.         this(skin.get(styleName, MovableTableStyle.class));
  51.         setSkin(skin);
  52.     }
  53.  
  54.     public MovableTable(MovableTableStyle closeableWindowStyle) {
  55.         setTouchable(Touchable.enabled);
  56.         setClip(true);
  57.         setStyle(closeableWindowStyle);
  58.         setWidth(150);
  59.         setHeight(150);
  60.         setMovable(true);
  61.         setResizable(false);
  62.         setKeepWithinStage(true);
  63.        
  64.         dragActors = new Actor[1];
  65.         dragActors[0] = this;
  66.  
  67.         addCaptureListener(new InputListener() {
  68.             public boolean touchDown(InputEvent event, float x, float y,
  69.                     int pointer, int button) {
  70.                 toFront();
  71.                 return false;
  72.             }
  73.         });
  74.         addListener(new InputListener() {
  75.             int edge;
  76.             float startX, startY, lastX, lastY;
  77.  
  78.             public boolean touchDown(InputEvent event, float x, float y,
  79.                     int pointer, int button) {
  80.                 Actor hitActor = hit(x,y,true);
  81.                 boolean success = false;
  82.                 for (Actor a : getDraggableRegions()) {
  83.                     if (hitActor.equals(a)) {
  84.                         success = true;
  85.                     }
  86.                 }
  87.                 if (!success) {
  88.                     return false;
  89.                 }
  90.                 if (button == Input.Buttons.LEFT) {
  91.                     int border = resizeBorder;
  92.                     float width = getWidth(), height = getHeight();
  93.                     edge = 0;
  94.                     if (isResizable) {
  95.                         if (x < border)
  96.                             edge |= Align.left;
  97.                         if (x > width - border)
  98.                             edge |= Align.right;
  99.                         if (y < border)
  100.                             edge |= Align.bottom;
  101.                         if (y > height - border)
  102.                             edge |= Align.top;
  103.                         if (edge != 0)
  104.                             border += 25;
  105.                         if (x < border)
  106.                             edge |= Align.left;
  107.                         if (x > width - border)
  108.                             edge |= Align.right;
  109.                         if (y < border)
  110.                             edge |= Align.bottom;
  111.                         if (y > height - border)
  112.                             edge |= Align.top;
  113.                     }
  114.                     if (isMovable
  115.                             && edge == 0    // We are not resizing!
  116.                             && y <= height  // Inside the Window
  117.                             && y >= 0      
  118.                             && x >= 0
  119.                             && x <= width)
  120.                         edge = MOVE;
  121.                     dragging = edge != 0;
  122.                     startX = x;
  123.                     startY = y;
  124.                     lastX = x;
  125.                     lastY = y;
  126.                 }
  127.                 return edge != 0 || isModal;
  128.             }
  129.  
  130.             public void touchUp(InputEvent event, float x, float y,
  131.                     int pointer, int button) {
  132.                 dragging = false;
  133.             }
  134.  
  135.             public void touchDragged(InputEvent event, float x, float y,
  136.                     int pointer) {
  137.                 if (!dragging)
  138.                     return;
  139.                 float width = getWidth(), height = getHeight();
  140.                 float windowX = getX(), windowY = getY();
  141.  
  142.                 float minWidth = getMinWidth(), maxWidth = getMaxWidth();
  143.                 float minHeight = getMinHeight(), maxHeight = getMaxHeight();
  144.                 Stage stage = getStage();
  145.                 boolean clampPosition = keepWithinStage
  146.                         && getParent() == stage.getRoot();
  147.  
  148.                 if ((edge & MOVE) != 0) { // We are moving!
  149.                     float amountX = x - startX, amountY = y - startY;
  150.                     windowX += amountX;
  151.                     windowY += amountY;
  152.                 }
  153.                 if ((edge & Align.left) != 0) { // We are resizing!
  154.                     float amountX = x - startX;
  155.                     if (width - amountX < minWidth)
  156.                         amountX = -(minWidth - width);
  157.                     if (clampPosition && windowX + amountX < 0)
  158.                         amountX = -windowX;
  159.                     width -= amountX;
  160.                     windowX += amountX;
  161.                 }
  162.                 if ((edge & Align.bottom) != 0) {
  163.                     float amountY = y - startY;
  164.                     if (height - amountY < minHeight)
  165.                         amountY = -(minHeight - height);
  166.                     if (clampPosition && windowY + amountY < 0)
  167.                         amountY = -windowY;
  168.                     height -= amountY;
  169.                     windowY += amountY;
  170.                 }
  171.                 if ((edge & Align.right) != 0) {
  172.                     float amountX = x - lastX;
  173.                     if (width + amountX < minWidth)
  174.                         amountX = minWidth - width;
  175.                     if (clampPosition
  176.                             && windowX + width + amountX > stage.getWidth())
  177.                         amountX = stage.getWidth() - windowX - width;
  178.                     width += amountX;
  179.                 }
  180.                 if ((edge & Align.top) != 0) {
  181.                     float amountY = y - lastY;
  182.                     if (height + amountY < minHeight)
  183.                         amountY = minHeight - height;
  184.                     if (clampPosition
  185.                             && windowY + height + amountY > stage.getHeight())
  186.                         amountY = stage.getHeight() - windowY - height;
  187.                     height += amountY;
  188.                 }
  189.                 lastX = x;
  190.                 lastY = y;
  191.                 setBounds(Math.round(windowX), Math.round(windowY),
  192.                         Math.round(width), Math.round(height));
  193.             }
  194.  
  195.             public boolean mouseMoved(InputEvent event, float x, float y) {
  196.                 return isModal;
  197.             }
  198.  
  199.             public boolean scrolled(InputEvent event, float x, float y,
  200.                     int amount) {
  201.                 return isModal;
  202.             }
  203.  
  204.             public boolean keyDown(InputEvent event, int keycode) {
  205.                 return isModal;
  206.             }
  207.  
  208.             public boolean keyUp(InputEvent event, int keycode) {
  209.                 return isModal;
  210.             }
  211.  
  212.             public boolean keyTyped(InputEvent event, char character) {
  213.                 return isModal;
  214.             }
  215.         });
  216.     }
  217.    
  218.     /**
  219.      * Checks if the Window is within the Stage. If not, it is pushed inside.
  220.      */
  221.     private void keepWithinStage () {
  222.         if (!keepWithinStage) return;
  223.         Stage stage = getStage();
  224.         if (getParent() == stage.getRoot()) {
  225.             float parentWidth = stage.getWidth();
  226.             float parentHeight = stage.getHeight();
  227.             if (getX() < 0) setX(0);
  228.             if (getRight() > parentWidth) setX(parentWidth - getWidth());
  229.             if (getY() < 0) setY(0);
  230.             if (getTop() > parentHeight) setY(parentHeight - getHeight());
  231.         }
  232.     }
  233.    
  234.     /**
  235.      * @return  The Actor that was hit first.
  236.      */
  237.     public Actor hit (float x, float y, boolean touchable) {
  238.         Actor hit = super.hit(x, y, touchable);
  239.         if (hit == null && isModal && (!touchable || getTouchable() == Touchable.enabled)) return this;
  240.         return hit;
  241.     }
  242.    
  243.     /**
  244.      * This method is used to determine what Actors can be clicked to drag the dialog.
  245.      * This is to prevent dragging inside the content of the MovableWindow.
  246.      * @return  An Array of Actors that can be used to drag the MovableWindow.
  247.      */
  248.     protected Actor[] getDraggableRegions() {
  249.         return dragActors;
  250.     }
  251.    
  252.     /**
  253.      * Renders the beautiful Table.
  254.      */
  255.     public void draw(Batch batch, float parentAlpha) {
  256.         keepWithinStage();
  257.         super.draw(batch, parentAlpha);
  258.     }
  259.    
  260.     public void setStyle(MovableTableStyle style) {
  261.         if (style == null) throw new IllegalArgumentException("style cannot be null.");
  262.         this.style = style;
  263.         setBackground(style.background);
  264.         invalidateHierarchy(); // This one is questionable!
  265.     }
  266.    
  267.     public MovableTableStyle getStyle () {
  268.         return style;
  269.     }
  270.    
  271.     public boolean isModal() {
  272.         return isModal;
  273.     }
  274.  
  275.     public void setModal(boolean isModal) {
  276.         this.isModal = isModal;
  277.     }
  278.  
  279.     public boolean isResizable() {
  280.         return isResizable;
  281.     }
  282.  
  283.     public void setResizable(boolean isResizable) {
  284.         this.isResizable = isResizable;
  285.     }
  286.  
  287.     public boolean isMovable() {
  288.         return isMovable;
  289.     }
  290.  
  291.     public void setMovable(boolean isMovable) {
  292.         this.isMovable = isMovable;
  293.     }
  294.  
  295.     public boolean isKeepWithinStage() {
  296.         return keepWithinStage;
  297.     }
  298.  
  299.     public void setKeepWithinStage(boolean keepWithinStage) {
  300.         this.keepWithinStage = keepWithinStage;
  301.     }
  302.  
  303.     static public class MovableTableStyle {
  304.        
  305.         public Drawable background;
  306.     }
  307. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement