当前位置: 首页 > 面试题库 >

如何在JScrollPane中实现位置敏感缩放?

竺鸿骞
2023-03-14
问题内容

我正在尝试在中实现位置敏感缩放JScrollPane。该JScrollPane包含自定义组件paint将绘制自己的任何空间,它被分配里面-
所以变焦是那么容易,因为使用MouseWheelListener的要求重新调整内部组件。

但是我也想放大(或缩小)一个点,以在生成的放大(或缩小)视图中将该点尽可能地保持中心(这就是我所说的“位置敏感”缩放),类似在Google地图中如何缩放。我确信这之前已经做过很多次了-
有人知道在Java Swing下执行此操作的“正确”方法吗?玩Graphic2D而不是使用的转换会更好JScrollPanes吗?

示例代码如下:

package test;

import java.awt.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;

public class FPanel extends javax.swing.JPanel {

private Dimension preferredSize = new Dimension(400, 400);    
private Rectangle2D[] rects = new Rectangle2D[50];

public static void main(String[] args) {        
    JFrame jf = new JFrame("test");
    jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    jf.setSize(400, 400);
    jf.add(new JScrollPane(new FPanel()));
    jf.setVisible(true);
}

public FPanel() {
    // generate rectangles with pseudo-random coords
    for (int i=0; i<rects.length; i++) {
        rects[i] = new Rectangle2D.Double(
                Math.random()*.8, Math.random()*.8, 
                Math.random()*.2, Math.random()*.2);
    }
    // mouse listener to detect scrollwheel events
    addMouseWheelListener(new MouseWheelListener() {
        public void mouseWheelMoved(MouseWheelEvent e) {
            updatePreferredSize(e.getWheelRotation(), e.getPoint());
        }
    });
}

private void updatePreferredSize(int n, Point p) {
    double d = (double) n * 1.08;
    d = (n > 0) ? 1 / d : -d;
    int w = (int) (getWidth() * d);
    int h = (int) (getHeight() * d);
    preferredSize.setSize(w, h);
    getParent().doLayout();
    // Question: how do I keep 'p' centered in the resulting view?
}

public Dimension getPreferredSize() {
    return preferredSize;
}

private Rectangle2D r = new Rectangle2D.Float();
public void paint(Graphics g) {
    super.paint(g);
    g.setColor(Color.red);
    int w = getWidth();
    int h = getHeight();
    for (Rectangle2D rect : rects) {
        r.setRect(rect.getX() * w, rect.getY() * h, 
                rect.getWidth() * w, rect.getHeight() * h);
        ((Graphics2D)g).draw(r);
    }       
  }
}

问题答案:

经过测试,似乎可以…

private void updatePreferredSize(int n, Point p) {
    double d = (double) n * 1.08;
    d = (n > 0) ? 1 / d : -d;

    int w = (int) (getWidth() * d);
    int h = (int) (getHeight() * d);
    preferredSize.setSize(w, h);

    int offX = (int)(p.x * d) - p.x;
    int offY = (int)(p.y * d) - p.y;
    setLocation(getLocation().x-offX,getLocation().y-offY);

    getParent().doLayout();
}

更新资料

这是一个解释:该点p是鼠标相对于的位置FPanel。由于您正在缩放面板的尺寸,因此p(相对于面板的尺寸)的位置将以相同的比例缩放。通过从缩放位置减去当前位置,您可以获得调整面板大小时点“移动”了多少。然后,只需在相反方向上将滚动窗格中的面板位置移动相同的量,然后p放回鼠标光标下方即可。



 类似资料:
  • 问题内容: 在C / C ++ / Java / C#中是否有相对简单易懂(易于实现)的局部敏感哈希示例? 我想了解更多有关此概念的信息,因此想在几个文本文件上尝试实现只是为了了解其工作原理,因此我不需要任何高性能或任何内容……仅是哈希示例对于相似的输入返回相似的哈希值的函数。我可以通过后面的例子从中学到更多。:) 问题答案: 对于字符串,您可以使用近似匹配算法。 产生随机字串 对于所有字符串,使

  • 问题内容: 我有一个带有utf8一般ci排序规则的MySQL表。在表中,我可以看到两个条目: 阿巴德 阿巴德 我正在使用如下查询: 查询结果给出两个词: 阿巴德 阿巴德 有没有办法表明我只希望MySQL找到带重音的单词?我希望查询仅返回 阿巴德 我也尝试过以下查询: 它没有给我任何结果。感谢您的帮助。 问题答案: 如果您对该字段的搜索始终对重音敏感,则将该字段的排序规则声明为utf8_bin(这将

  • 本文向大家介绍python 实现敏感词过滤的方法,包括了python 实现敏感词过滤的方法的使用技巧和注意事项,需要的朋友参考一下 如下所示: 测试结果: 1) 敏感词 100个 2) 敏感词 1000 个 从上面的实验我们可以看出,在DFA 算法只有在敏感词较多的情况下,才有意义。在百来个敏感词的情况下,甚至不如普通算法 下面从理论上推导时间复杂度,为了方便分析,首先假定消息文本是等长的,长度为

  • 本文向大家介绍浅谈Python 敏感词过滤的实现,包括了浅谈Python 敏感词过滤的实现的使用技巧和注意事项,需要的朋友参考一下 一个简单的实现 其中strip() 函数 删除附近的一些空格,解码采用utf-8的形式,然后将其转为小写。 parse()函数就是打开文件,然后从中取各个关键词,然后将其存在关键词集合中。 filter()函数是一个过滤器函数,其中将消息转化为小写,然后将关键词替换成

  • 主要内容:1.引入包,2.配置加密、解密的密码,3.测试用例中生成加密后的秘钥,4.将加密后的字符串替换原明文,5.部署时配置 salt(盐)值MySQL 登录密码,Redis 登录密码以及第三方的密钥等等一览无余。这里介绍一个加解密组件,提高一些属性配置的安全性。 1.引入包 2.配置加密、解密的密码 3.测试用例中生成加密后的秘钥 4.将加密后的字符串替换原明文 5.部署时配置 salt(盐)值 为了防止 salt(盐)泄露被反解出密码,可以在项目部署的时候使用命令传入 salt 值:

  • 主要内容:1.引入包,2.配置加密、解密的密码,3.测试用例中生成加密后的秘钥,4.将加密后的字符串替换原明文,5.部署时配置 salt(盐)值MySQL 登录密码,Redis 登录密码以及第三方的密钥等等一览无余。这里介绍一个加解密组件,提高一些属性配置的安全性。 1.引入包 2.配置加密、解密的密码 3.测试用例中生成加密后的秘钥 4.将加密后的字符串替换原明文 5.部署时配置 salt(盐)值 为了防止 salt(盐)泄露被反解出密码,可以在项目部署的时候使用命令传入 salt 值: