I am trying to implement a Tooltip in a loop, for displaying some words after hovering over a rectangle. The problem is that, the words just show up once in a while (sometimes even without a delay, sometimes not even after waiting for a minute). When I put the tooltip statement outside of the loop the words always show up (with a short delay), but I need the statement inside. Any idea what causes the problem?
for (int i = 0; i < finalList.size(); i++) {
for (int j = 0; j < names.getName().size(); j++) {
Label number = new Label(" " + finalList.get(i).get(j).getNamesFrequencySection());
Rectangle rec = new Rectangle();
rec.setY(j * 20 + 20);
rec.setX(i * 80 + 100);
rec.setWidth(80);
rec.setHeight(20);
if (finalList.get(i).get(j).getNamesFrequencySection() == 0) {
rec.setFill(Color.rgb(255, 255, 255));
}
else {
rec.setFill(Color.rgb(250 - (3 * finalList.get(i).get(j).getNamesFrequencySection()), 0, 0));
}
number.setLayoutY(j * 20 + 20);
number.setLayoutX(i * 80 + 130);
root.getChildren().add(rec);
root.getChildren().add(number);
Tooltip.install(rec, new Tooltip(finalList.get(i).get(j).getMostCommon().replaceAll("[^a-zA-Z ]","")));
}
}
NamesFrequency is an Integer and getMostCommon() is the String of the words.
Related
I'm working on a pathfinding algorithm in processing. If I don't draw a line that crosses the path between the green and the red dot, it works, but if I do, I've got a problem, that if I call a function, the program does absolutely nothing but freezes, and I have no idea why. The pixelss stores what you draw, and there are all kinds of stuff, that don't matter at this problem.
When you paste it to processing, press ctrl+t to auto-format it so you can understand it better, but I'd bet it's a newbie issue.
int[][] pixelss = new int[500][500];
void setup() {
background(255);
size(500, 500);}
int[][] badcoos = new int[500][500];
void golinego() {
stroke(200, 200, 255);
line(30, 30, 470, 470);
int j = 30;
int i = 30;
while (dist(i, j, 470, 470) > 10) {
stroke(0, 0, 180);
circle(i, j, 1);
if (pixelss[i+1][j+1]==0) {
i++;j++;}
if (pixelss[i][j]==1) {
if (pixelss[i][j+1]==1) {
if (pixelss[i+1][j]==0) {
i++;}
} else if (pixelss[i+1][j]==1) {
if (pixelss[i][j+1]==0) {
j++;}
} else {
i-=1;
j-=1;}}}}
void draw() {
stroke(0, 255, 0);
fill(0, 255, 0);
circle(30, 30, 10);
stroke(255, 0, 0);
fill(255, 0, 0);
circle(470, 470, 10);
if (mousePressed == true) {
try {
stroke(0);
fill(0);
circle(mouseX, mouseY, 2);
pixelss[mouseX][mouseY] = 1;
pixelss[mouseX+1][mouseY] = 1;
pixelss[mouseX-1][mouseY] = 1;
pixelss[mouseX][mouseY+1] = 1;
pixelss[mouseX][mouseY-1] = 1;
pixelss[mouseX+1][mouseY+1] = 1;
pixelss[mouseX-1][mouseY+1] = 1;
pixelss[mouseX+1][mouseY-1] = 1;
pixelss[mouseX-1][mouseY-1] = 1;
}catch(ArrayIndexOutOfBoundsException e) {}}}
void keyPressed() {
if (key=='r') {
pixelss = new int[500][500];
badcoos = new int[500][500];
background(255);}
if (key==' ') {
golinego();}
if (key=='d') {
background(0);
for (int i = 0; i < 500; i++) {
for (int j = 0; j < 500; j++) {
if (pixelss[i][j]==1) {
stroke(255);
circle(i, j, 1);}}}}}
The program is getting caught in your while loop.
You can see this if you print out the values of i and j inside the loop. They never meet the condition to escape the loop, so that chunk of code runs repeatedly with no change.
while (dist(i, j, 470, 470) > 10) {
println(i, j);
// etc...
}
This hangs the app because the while loop needs to complete before the the draw function gets called again to update the screen.
It's not clear to me what you're actually doing in the while loop, but that's where you should look. Either alter your logic inside the loop, or change the condition to ensure that the code doesn't get stuck in an infinite loop.
You should at least print something when the ArrayIndexOutOfBoundsException is caught.
It looks like you are working with some kind of gui library, make sure you are doing any processing in separate thread from the gui or the gui will become unresponsive and appear to 'freeze' like you describe.
https://docs.oracle.com/javase/tutorial/uiswing/concurrency/index.html
I want to make random rectangles on Processing. So far, I used for loops for making window size rectangle but I can't figure out how to make only 10 rectangle randomly. Here is my sample code for you:
void setup()
{
size(400, 400);
}
void draw()
{
background(0); // Black Background
stroke(255); // White lines
for (int j = 0; j <= height; j += 40)
{
for (int i = 0; i < width; i += 40)
{
fill(0);
rect(i, j, 40, 40);
}
}
}
It shows 100 black rectangles but I want to see only 10 black rectangles. For example: The first line will get random 1 rectangle, second line will get 2 , third line will get 1 and it goes till the 10.
There are multiple ways to solve this fun homework/exercise.
First thing is drawing the right number of boxes per column:
void setup()
{
size(400, 400);
background(0); // Black Background
fill(0);
stroke(255); // White lines
int boxSize = 40;
int maxBoxes = 1;
for (int j = 0; j <= height; j += boxSize)
{
// box count per row
int boxCount = 0;
for (int i = 0; i < width; i += boxSize)
{
// only draw the max number of boxes
if(boxCount < maxBoxes){
rect(i, j, 40, 40);
// increment per row box count
boxCount++;
}
}
// increment max boxes per box
maxBoxes++;
}
}
Secondly the positions for the drawn boxes per column need to be randomized, but ideally not overlap. One option is to split the full solution space to sections: each section having it's own range of positions so it won't overlap the next.
void setup()
{
size(400, 400);
background(0); // Black Background
fill(0);
stroke(255); // White lines
int boxSize = 40;
int maxBoxes = 1;
int totalBoxes = width / boxSize;
for (int j = 0; j <= height; j += boxSize)
{
// box count per row
int boxCount = 0;
// a list of box indices of where to draw a box (as opposed
int[] randomXIndices = new int[maxBoxes];
// how many index ranges to span per row
int indexRangePerBox = totalBoxes / maxBoxes;
// for each random index
for(int k = 0 ; k < maxBoxes; k++)
{
// pre-calculate which random index to select
// using separate ranges per box to avoid overlaps
randomXIndices[k] = (int)random(indexRangePerBox * k, indexRangePerBox * (k + 1));
}
for (int i = 0; i < width; i += boxSize)
{
// only draw the max number of boxes
if(boxCount < maxBoxes)
{
int randomX = randomXIndices[boxCount] * boxSize;
rect(randomX, j, 40, 40);
// increment per row box count
boxCount++;
}
}
// increment max boxes per box
maxBoxes++;
}
}
void draw(){
}
void mousePressed(){
setup();
}
Click to reset. Notice that the bottom rows almost always look the same:
there is less wiggle room to pick a random position
random() is a rough pseudo-random number generator, but there are better ones out there like randomGaussian(), noise(), etc.
overall there are other strategies to explore picking random positions and avoiding overlaps
Live demo bellow:
function setup()
{
createCanvas(400, 400);
reset();
// reset once per second
setInterval(reset, 1000);
}
function reset(){
background(0); // Black Background
fill(0);
stroke(255); // White lines
var boxSize = 40;
var maxBoxes = 1;
var totalBoxes = width / boxSize;
for (var j = 0; j <= height; j += boxSize)
{
// box count per row
var boxCount = 0;
// a list of box indices of where to draw a box (as opposed
var randomXIndices = new Array(maxBoxes);
// how many index ranges to span per row
var indexRangePerBox = totalBoxes / maxBoxes;
// for each random index
for(var k = 0 ; k < maxBoxes; k++)
{
// pre-calculate which random index to select
// using separate ranges per box to avoid overlaps
randomXIndices[k] = floor(random(indexRangePerBox * k, indexRangePerBox * (k + 1)));
}
for (var i = 0; i < width; i += boxSize)
{
// only draw the max number of boxes
if(boxCount < maxBoxes)
{
var randomX = randomXIndices[boxCount] * boxSize;
rect(randomX, j, 40, 40);
// increment per row box count
boxCount++;
}
}
// increment max boxes per box
maxBoxes++;
}
}
function draw(){
}
function mousePressed(){
reset();
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.0.0/p5.min.js"></script>
So i've made a simple program that have as its objective to draw a rect on the screen when a button is clicked on the mouse, if its the left button it make a rect on the left half of the screen, and if it the right it make a rect in the right half of the screen.
The problem is that i used a for loop to make the rect get drew for some time continuously, but it just does not happen.
Here is my code:
int bab = 0;
void setup() {
size(500, 500);
frameRate(24);
background(255);
int b = 0;
}
void draw() {
background(255);
println(bab);
bab++;
if(mousePressed == true && mouseButton == LEFT) {
fill(100, 0, 0);
for(int i = 0; i <= 20000; i++) {
fill(100, 0, 0);
rect(0, 200, width/2, 50);
println("The value is: " + i);
}
background(255);
}else if(mousePressed == true && mouseButton == RIGHT) {
fill(255, 255, 0);
for(int i = 0; i <= 200; i++) {
rect(width/2, 0, width/2, height);
}
}
}
Try this code:
long leftOn = 0;
long rightOn = 0;
void draw() {
// clear window buffer (white color)
background(255);
if (mousePressed == true && mouseButton == LEFT) {
// remember timestamp when left button was pressed in variable leftOn
leftOn = millis();
rightOn = 0;
} else if (mousePressed == true && mouseButton == RIGHT) {
// remember timestamp when right button was pressed
rightOn = millis();
leftOn = 0;
}
// now is current timestamp
long now = millis();
/*
* if now - last left click distance is lower than 1000 ms - draw left rect
* else if now - right left click distance is lower than 1000 ms - draw right rect
*/
if (now - leftOn <= 1000*1) {
fill(0,255,0);
rect(0,0,width/2,height);
} else if (now - rightOn <= 1000*1) {
fill(255,255,0);
rect(width/2, 0, width/2, height);
}
// else - nothing is drawn in this frame, so window will be empty in this frame
}
Looping is done by Processing - I mean when you set frame rate to 20 it means that Processing will call method draw() every 50 ms (20 times in 1 second).
So, you have to implement how 1 single frame should be drawn. You dont need looping to make things last longer.
In above code left rect will appear and last for 1 second from last left button was pressed. And right rect for 1 second from right button.
The millis() method returns the number of milliseconds that elapsed from startup. You can then remember in leftOn when left button was pressed. And you draw left rect if time difference between now and last leftOn is less then 1000 ms - for example.
Your for loop uses i as it's control / to represent each iteration through the loop. You also have the drawing happening in this loop, so that each iteration should draw something.
However, nowhere in your loop do you use the i variable -- you only print it to the console.
for(int i = 0; i <= 20000; i++) {
fill(100, 0, 0); // does not use i
rect(0, 200, width/2, 50); // does not use i
println("O valor é: " + i);
}
So what you have really is a loop that draws the exact same thing, 20000 times. So to you it looks like nothing is happening, but it is, it's just the same thing is happening repeatedly.
Maybe you wanted something more like:
for(int i = 0; i <= 20000; i++) {
fill(100, 0 + i, 0 + i);
rect(0 + i, 200, width/2, 50 + i);
println("O valor é: " + i);
}
^ I really have no idea if that makese sense... But you need to use the loop control variable i somewhere in your drawing code, or else yes, you will draw the same thing repeatedly.
I would like to implement a "grid view" of pixmaps. This is how I would like the UI to behave: You click a button and it shows a QGraphicsView with a QGraphicsScene (done) and then I would like to show all of my QPixmaps in a grid view. I don't actually want to see a grid I just want to organize the pixmaps like 10 columns (pixmaps) pr. row, and then a 10px whitespace in-between each pixmap. (not done). How would this be implemented?
EDIT: Here's what I've done so far (which produces the outcome described in the second comment)
public SpriteScene() {
super(0, 0, 800, 500);
QPixmap[] sprites = GUI.getWInterface().sprites;
List<QPixmap> l = Arrays.asList(sprites);
Iterator<QPixmap> i = l.iterator();
int rows = 10 / sprites.length;
boolean isDone = false;
for(int y = 0; y < rows; y++) {
for(int x = 0; x < 10; x++) {
if(i.hasNext()) {
QGraphicsPixmapItem pixmap = addPixmap(i.next());
pixmap.setPos(x * 64 + 10 , y * 64 + 10);
} else {
isDone = true;
break;
}
}
if(isDone) {
break;
}
}
}
SpriteScene extends QGraphicsScene and is being added to a QGraphicsView like this:
spriteView = new QGraphicsView(new SpriteScene(), this);
spriteView.setGeometry(0, 35, 850, 550);
spriteView.setAlignment(new Qt.AlignmentFlag[]{Qt.AlignmentFlag.AlignLeft, Qt.AlignmentFlag.AlignTop});
spriteView.hide();
Oh and by the way each pixmap is 64x64px :)
pixmap.setPos(x * 64 + 10 , y * 64 + 10);
Write that down on paper for the first few values:
x = 0, y = 0 => pos = ( 10, 10)
x = 1, y = 0 => pos = ( 74, 10)
x = 2, y = 0 => pos = (138, 10)
There's only 64 pixel different between each successive x offset. You need 74 pixels - the size of the pixmap plus the size of the border.
Set a few variables for your image with, height, horizontal and vertical spacing, and your code should look like:
pixmap.setPos(x * (width+hspacing) + offsetx, y * (height+vspacing) + offsety);
The offsetx/y would probably look nicer if they were half the respective spacing valued to get the grid "centered".
I am creating objects on a line in a window created by this piece of code:
void createTurtles() {
int nrTurtles = Keyboard.nextInt("Set amount of turtles: ");
w = new GraphicsWindow(500, 300);
drawLinez();
for (int k = 1; k <= nrTurtles; k++) {
Turtle t = new Turtle(w, 50, 50 + k*10);
t.right(90);
t.setSpeed(100);
t.penDown();
turtles.add(t);
}
}
This codeline:
Turtle t = new Turtle(w, 50, 50 + k*10);
Creates one turtle at the time. Right now i have set that the turtles will have the Y coordinat of 50, and the X coordinat of 50+k*10. This is because the line starts at the X coordinat of 50 and stops at the X coordinat of 250.
Now what i want is, based on the nr of turtles created (user inputs this), i want the turtles to be spread on this line evenly. How to do it? It has do to with the line that i wrote and maybe the k value or the 10.
The line is illustrated in the picture (see link below), its the red line, that the number of turtles are created at.
Devide the height - 100 of the window by the number of turtles and you will have your distanceBetweenTurles:
int nrTurtles = Keyboard.nextInt("Set amount of turtles: ");
int height = 300;
w = new GraphicsWindow(500, height);
drawLinez();
double distanceBetweenTurles = (height - 100.0) / nrTurtles;
for (int k = 1; k <= nrTurtles; k++) {
Turtle t = new Turtle(w, 50, 50 + (int) (k * distanceBetweenTurtles));
t.right(90);
t.setSpeed(100);
t.penDown();
turtles.add(t);
}