<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??一站式輕松地調用各大LLM模型接口,支持GPT4、智譜、豆包、星火、月之暗面及文生圖、文生視頻 廣告
                # Java Swing 中的可調整大小的組件 > 原文: [http://zetcode.com/tutorials/javaswingtutorial/resizablecomponent/](http://zetcode.com/tutorials/javaswingtutorial/resizablecomponent/) 在 Java Swing 教程的這一部分中,我們將創建一個可調整大小的組件。 ## 可調整大小的組件 在創建圖表時,經常使用可調整大小的組件。 常見的可調整大小的組件是電子表格應用中的圖表。 可以將圖表移到應用的表格小部件上并調整大小。 [Tweet](https://twitter.com/share) 為了創建可以在面板上自由拖動的組件,我們使用啟用了絕對定位的面板。 在我們的示例中,我們將創建一個可以在父窗口上自由移動并調整大小的組件。 當可調整大小的組件具有焦點時,將在其可調整大小的組件的邊框上繪制八個小矩形。 矩形用作拖動點,我們可以在其中繪制組件并開始調整大小。 `ResizableComponentEx.java` ```java package com.zetcode; import java.awt.Color; import java.awt.EventQueue; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import javax.swing.JFrame; import javax.swing.JPanel; public class ResizableComponentEx extends JFrame { private Resizable res; public ResizableComponentEx() { initUI(); } private void initUI() { var pnl = new JPanel(null); add(pnl); var area = new JPanel(); area.setBackground(Color.white); res = new Resizable(area); res.setBounds(50, 50, 200, 150); pnl.add(res); addMouseListener(new MouseAdapter() { @Override public void mousePressed(MouseEvent me) { requestFocus(); res.repaint(); } }); setSize(350, 300); setTitle("Resizable component"); setLocationRelativeTo(null); setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); } public static void main(String[] args) { EventQueue.invokeLater(() -> { var ex = new ResizableComponentEx(); ex.setVisible(true); }); } } ``` `ResizableComponentEx`設置面板和組件。 ```java var pnl = new JPanel(null); ``` 我們對可調整大小的組件使用絕對定位。 通過將`null`提供給`JPanel`的構造器,我們創建了具有絕對定位的面板。 ```java addMouseListener(new MouseAdapter() { @Override public void mousePressed(MouseEvent me) { requestFocus(); res.repaint(); } }); ``` 如果我們在父面板上(即在可調整大小的組件外部)按下,我們將抓住焦點并重新繪制該組件。 邊框上的矩形將消失。 `ResizableBorder.java` ```java package com.zetcode; import java.awt.Color; import java.awt.Component; import java.awt.Cursor; import java.awt.Graphics; import java.awt.Insets; import java.awt.Rectangle; import java.awt.event.MouseEvent; import javax.swing.SwingConstants; import javax.swing.border.Border; public class ResizableBorder implements Border { private int dist = 8; int locations[] = { SwingConstants.NORTH, SwingConstants.SOUTH, SwingConstants.WEST, SwingConstants.EAST, SwingConstants.NORTH_WEST, SwingConstants.NORTH_EAST, SwingConstants.SOUTH_WEST, SwingConstants.SOUTH_EAST }; int cursors[] = { Cursor.N_RESIZE_CURSOR, Cursor.S_RESIZE_CURSOR, Cursor.W_RESIZE_CURSOR, Cursor.E_RESIZE_CURSOR, Cursor.NW_RESIZE_CURSOR, Cursor.NE_RESIZE_CURSOR, Cursor.SW_RESIZE_CURSOR, Cursor.SE_RESIZE_CURSOR }; public ResizableBorder(int dist) { this.dist = dist; } @Override public Insets getBorderInsets(Component component) { return new Insets(dist, dist, dist, dist); } @Override public boolean isBorderOpaque() { return false; } @Override public void paintBorder(Component component, Graphics g, int x, int y, int w, int h) { g.setColor(Color.black); g.drawRect(x + dist / 2, y + dist / 2, w - dist, h - dist); if (component.hasFocus()) { for (int i = 0; i < locations.length; i++) { var rect = getRectangle(x, y, w, h, locations[i]); g.setColor(Color.WHITE); g.fillRect(rect.x, rect.y, rect.width - 1, rect.height - 1); g.setColor(Color.BLACK); g.drawRect(rect.x, rect.y, rect.width - 1, rect.height - 1); } } } private Rectangle getRectangle(int x, int y, int w, int h, int location) { switch (location) { case SwingConstants.NORTH: return new Rectangle(x + w / 2 - dist / 2, y, dist, dist); case SwingConstants.SOUTH: return new Rectangle(x + w / 2 - dist / 2, y + h - dist, dist, dist); case SwingConstants.WEST: return new Rectangle(x, y + h / 2 - dist / 2, dist, dist); case SwingConstants.EAST: return new Rectangle(x + w - dist, y + h / 2 - dist / 2, dist, dist); case SwingConstants.NORTH_WEST: return new Rectangle(x, y, dist, dist); case SwingConstants.NORTH_EAST: return new Rectangle(x + w - dist, y, dist, dist); case SwingConstants.SOUTH_WEST: return new Rectangle(x, y + h - dist, dist, dist); case SwingConstants.SOUTH_EAST: return new Rectangle(x + w - dist, y + h - dist, dist, dist); } return null; } public int getCursor(MouseEvent me) { var c = me.getComponent(); int w = c.getWidth(); int h = c.getHeight(); for (int i = 0; i < locations.length; i++) { var rect = getRectangle(0, 0, w, h, locations[i]); if (rect.contains(me.getPoint())) { return cursors[i]; } } return Cursor.MOVE_CURSOR; } } ``` `ResizableBorder`負責繪制組件的邊框并確定要使用的光標的類型。 ```java int locations[] = { SwingConstants.NORTH, SwingConstants.SOUTH, SwingConstants.WEST, SwingConstants.EAST, SwingConstants.NORTH_WEST, SwingConstants.NORTH_EAST, SwingConstants.SOUTH_WEST, SwingConstants.SOUTH_EAST }; ``` 這些是繪制矩形的位置。 這些位置也是抓取點,可以在其中抓取組件并調整其大小。 ```java g.setColor(Color.black); g.drawRect(x + dist / 2, y + dist / 2, w - dist, h - dist); ``` 在`paintBorder()`方法中,我們繪制了可調整大小組件的邊框。 上面的代碼繪制了組件的外邊界。 ```java if (component.hasFocus()) { for (int i = 0; i < locations.length; i++) { var rect = getRectangle(x, y, w, h, locations[i]); g.setColor(Color.WHITE); g.fillRect(rect.x, rect.y, rect.width - 1, rect.height - 1); g.setColor(Color.BLACK); g.drawRect(rect.x, rect.y, rect.width - 1, rect.height - 1); } } ``` 僅當可調整大小的組件當前具有焦點時才繪制八個矩形。 ```java private Rectangle getRectangle(int x, int y, int w, int h, int location) { switch (location) { case SwingConstants.NORTH: return new Rectangle(x + w / 2 - dist / 2, y, dist, dist); case SwingConstants.SOUTH: return new Rectangle(x + w / 2 - dist / 2, y + h - dist, dist, dist); ... } ``` `getRectangle()`方法返回矩形的坐標。 ```java public int getCursor(MouseEvent me) { var c = me.getComponent(); int w = c.getWidth(); int h = c.getHeight(); for (int i = 0; i < locations.length; i++) { var rect = getRectangle(0, 0, w, h, locations[i]); if (rect.contains(me.getPoint())) { return cursors[i]; } } return Cursor.MOVE_CURSOR; } ``` `getCursor()`方法獲取相關抓點的光標類型。 `Resizable.java` ```java package com.zetcode; import javax.swing.JComponent; import javax.swing.event.MouseInputAdapter; import javax.swing.event.MouseInputListener; import java.awt.BorderLayout; import java.awt.Component; import java.awt.Cursor; import java.awt.Point; import java.awt.event.MouseEvent; public class Resizable extends JComponent { public Resizable(Component comp) { this(comp, new ResizableBorder(8)); } public Resizable(Component comp, ResizableBorder border) { setLayout(new BorderLayout()); add(comp); addMouseListener(resizeListener); addMouseMotionListener(resizeListener); setBorder(border); } private void resize() { if (getParent() != null) { getParent().revalidate(); } } MouseInputListener resizeListener = new MouseInputAdapter() { @Override public void mouseMoved(MouseEvent me) { if (hasFocus()) { var resizableBorder = (ResizableBorder) getBorder(); setCursor(Cursor.getPredefinedCursor(resizableBorder.getCursor(me))); } } @Override public void mouseExited(MouseEvent mouseEvent) { setCursor(Cursor.getDefaultCursor()); } private int cursor; private Point startPos = null; @Override public void mousePressed(MouseEvent me) { var resizableBorder = (ResizableBorder) getBorder(); cursor = resizableBorder.getCursor(me); startPos = me.getPoint(); requestFocus(); repaint(); } @Override public void mouseDragged(MouseEvent me) { if (startPos != null) { int x = getX(); int y = getY(); int w = getWidth(); int h = getHeight(); int dx = me.getX() - startPos.x; int dy = me.getY() - startPos.y; switch (cursor) { case Cursor.N_RESIZE_CURSOR: if (!(h - dy < 50)) { setBounds(x, y + dy, w, h - dy); resize(); } break; case Cursor.S_RESIZE_CURSOR: if (!(h + dy < 50)) { setBounds(x, y, w, h + dy); startPos = me.getPoint(); resize(); } break; case Cursor.W_RESIZE_CURSOR: if (!(w - dx < 50)) { setBounds(x + dx, y, w - dx, h); resize(); } break; case Cursor.E_RESIZE_CURSOR: if (!(w + dx < 50)) { setBounds(x, y, w + dx, h); startPos = me.getPoint(); resize(); } break; case Cursor.NW_RESIZE_CURSOR: if (!(w - dx < 50) && !(h - dy < 50)) { setBounds(x + dx, y + dy, w - dx, h - dy); resize(); } break; case Cursor.NE_RESIZE_CURSOR: if (!(w + dx < 50) && !(h - dy < 50)) { setBounds(x, y + dy, w + dx, h - dy); startPos = new Point(me.getX(), startPos.y); resize(); } break; case Cursor.SW_RESIZE_CURSOR: if (!(w - dx < 50) && !(h + dy < 50)) { setBounds(x + dx, y, w - dx, h + dy); startPos = new Point(startPos.x, me.getY()); resize(); } break; case Cursor.SE_RESIZE_CURSOR: if (!(w + dx < 50) && !(h + dy < 50)) { setBounds(x, y, w + dx, h + dy); startPos = me.getPoint(); resize(); } break; case Cursor.MOVE_CURSOR: var bounds = getBounds(); bounds.translate(dx, dy); setBounds(bounds); resize(); } setCursor(Cursor.getPredefinedCursor(cursor)); } } @Override public void mouseReleased(MouseEvent mouseEvent) { startPos = null; } }; } ``` `Resizable`類表示正在調整大小并在窗口上移動的組件。 ```java private void resize() { if (getParent() != null) { getParent().revalidate(); } } ``` 調整組件大小后,將調用`resize()`方法。 `revalidate()`方法導致重畫組件。 ```java MouseInputListener resizeListener = new MouseInputAdapter() { @Override public void mouseMoved(MouseEvent me) { if (hasFocus()) { var border = (ResizableBorder) getBorder(); setCursor(Cursor.getPredefinedCursor(border.getCursor(me))); } } ... } ``` 當我們將光標懸停在抓取點上時,我們將更改光標類型。 僅當組件具有焦點時,光標類型才會更改。 ```java @Override public void mousePressed(MouseEvent me) { var resizableBorder = (ResizableBorder) getBorder(); cursor = resizableBorder.getCursor(me); startPos = me.getPoint(); requestFocus(); repaint(); } ``` 如果單擊可調整大小的組件,則將更改光標,獲得拖動的起點,將焦點放在該組件上,然后重新繪制它。 ```java int x = getX(); int y = getY(); int w = getWidth(); int h = getHeight(); int dx = me.getX() - startPos.x; int dy = me.getY() - startPos.y; ``` 在`mouseDragged()`方法中,我們確定光標的 x 和 y 坐標以及組件的寬度和高度。 我們計算鼠標拖動事件期間的距離。 ```java case Cursor.N_RESIZE_CURSOR: if (!(h - dy < 50)) { setBounds(x, y + dy, w, h - dy); resize(); } break; ``` 對于所有大小調整,我們確保該組件不小于 50px。 否則,我們可以將其減小到最終將其隱藏的程度。 `setBounds()`方法重新定位組件并調整其大小。 ![Resizable component](https://img.kancloud.cn/c3/72/c3721109571977802745e62da5f583c3_350x300.jpg) 圖:可調整大小的組件 在 Java Swing 教程的這一部分中,我們創建了一個可調整大小的組件。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看