Swing/SmoothScroll の変更点
- 追加された行はこの色です。
- 削除された行はこの色です。
- Swing/SmoothScroll へ行く。
- Swing/SmoothScroll の差分を削除
--- category: swing folder: SmoothScroll title: JTextAreaでSmoothScrollによる行移動 tags: [JScrollPane, JViewport, Animation, JTextArea] author: aterai pubdate: 2007-08-13T13:01:23+09:00 description: SmoothScrollアニメーション有りでJTextAreaの任意の行まで移動します。 image: https://lh3.googleusercontent.com/_9Z4BYR88imo/TQTTSaxFSzI/AAAAAAAAAkI/KtedLqwCXBY/s800/SmoothScroll.png --- * 概要 [#summary] `SmoothScroll`アニメーション有りで`JTextArea`の任意の行まで移動します。 #download(https://lh3.googleusercontent.com/_9Z4BYR88imo/TQTTSaxFSzI/AAAAAAAAAkI/KtedLqwCXBY/s800/SmoothScroll.png) * サンプルコード [#sourcecode] #code(link){{ Document doc = textArea.getDocument(); Element root = doc.getDefaultRootElement(); int ln = getDestLineNumber(textField, root); if (ln < 0) { Toolkit.getDefaultToolkit().beep(); return; } int ln = model.getNumber().intValue(); try { final Element elem = root.getElement(ln - 1); final Rectangle dest = textArea.modelToView(elem.getStartOffset()); final Rectangle current = scroll.getViewport().getViewRect(); new Timer(20, new ActionListener() { @Override public void actionPerformed(ActionEvent ae) { Timer animator = (Timer) ae.getSource(); if (dest.y < current.y && animator.isRunning()) { int d = Math.max(1, (current.y - dest.y) / 2); current.y = current.y - d; textArea.scrollRectToVisible(current); } else if (dest.y > current.y && animator.isRunning()) { int d = Math.max(1, (dest.y - current.y) / 2); current.y = current.y + d; textArea.scrollRectToVisible(current); } else { textArea.setCaretPosition(elem.getStartOffset()); animator.stop(); } Element elem = root.getElement(ln - 1); Rectangle dest = textArea.modelToView(elem.getStartOffset()); Rectangle current = scroll.getViewport().getViewRect(); new Timer(20, e -> { Timer animator = (Timer) e.getSource(); if (dest.y < current.y && animator.isRunning()) { int d = Math.max(1, (current.y - dest.y) / 2); current.y = current.y - d; textArea.scrollRectToVisible(current); } else if (dest.y > current.y && animator.isRunning()) { int d = Math.max(1, (dest.y - current.y) / 2); current.y = current.y + d; textArea.scrollRectToVisible(current); } else { textArea.setCaretPosition(elem.getStartOffset()); animator.stop(); } }).start(); } catch (BadLocationException ble) { Toolkit.getDefaultToolkit().beep(); } catch (BadLocationException ex) { UIManager.getLookAndFeel().provideErrorFeedback(textArea); } }} * 解説 [#explanation] 上記のサンプルでは、`java.swing.Timer`でイベントが発生すると`scrollRectToVisible(...)`メソッドを使用して目的位置と現在位置の差の半分だけ`ViewRect`のスクロールを繰り返すことで行移動アニメーションを行っています。 * 参考リンク [#reference] - [[JTextAreaの任意の行に移動>Swing/GotoLine]] * コメント [#comment] #comment #comment