I wanna make an application with "vertical entries" and I want that the backgroung keep static while you go up or down seeing the entries, I use that code:
VerticalFieldManager BGVFM = new VerticalFieldManager(VerticalFieldManager.USE_ALL_WIDTH | VerticalFieldManager.USE_ALL_HEIGHT) {
public void paint(Graphics graphics) {
graphics.drawBitmap(0, 0, Display.getWidth(), Display.getHeight(), fondo, 0, 0);
super.paint(graphics);
}
};
...
add(BGVFM)
But if I scroll, the image. It's possible to do what I want to do?
Related
In PySide you can override the paintEvent() method of a QWidget to control how the widget is painted on the screen. Is there an equivalent for Node in JavaFX?
In context: I'm in need of a way to display a custom image format on the screen. Constantly converting my format and JavaFX's Image so I can display it in an ImageView is too slow for me, in addition to being messier.
I've taken a look at ImageView.java and Canvas.java, but no luck. ImageView is using css, and Canvas appears to be doing something with the deprecated impl_ methods, for which I've found no documentation on.
Thanks!
Generally, the paint mechanisms in JavaFX changed towards a more event-based approach. To follow the JavaFX way, you should probably look at Timeline or AnimationTimer and only update the display when the actual image data changes.
However, you could use the old Swing way in JavaFX, if you like:
public class MyPane extends Pane {
private final Canvas canvas;
public MyPane() {
canvas = new Canvas(getWidth(), getHeight());
getChildren().add(canvas);
widthProperty().addListener(e -> canvas.setWidth(getWidth()));
heightProperty().addListener(e -> canvas.setHeight(getHeight()));
}
#Override
protected void layoutChildren() {
super.layoutChildren();
GraphicsContext gc = canvas.getGraphicsContext2D();
gc.clearRect(0, 0, getWidth(), getHeight());
gc.setFill(Color.RED);
gc.fillRect(10, 10, getWidth() - 20, getHeight() - 20);
// Paint your custom image here:
gc.drawImage(someImage, 0, 0);
}
}
The above code would be the equivalence of this Swing code:
public class MyPanel extends JPanel {
private static final long serialVersionUID = -969772195113348076L;
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
g.clearRect(0, 0, getWidth(), getHeight());
g.setColor(java.awt.Color.RED);
g.fillRect(10, 10, getWidth() - 20, getHeight() - 20);
// Paint your custom image here:
g.drawImage(someImage, 0, 0, null);
}
}
How to create more than one window of a single sketch in Processing?
Actually I want to detect and track a particular color (through webcam) in one window and display the detected co-ordinates as a point in another window.Till now I'm able to display the points in the same window where detecting it.But I want to split it into two different windows.
You need to create a new frame and a new PApplet... here's a sample sketch:
import javax.swing.*;
SecondApplet s;
void setup() {
size(640, 480);
PFrame f = new PFrame(width, height);
frame.setTitle("first window");
f.setTitle("second window");
fill(0);
}
void draw() {
background(255);
ellipse(mouseX, mouseY, 10, 10);
s.setGhostCursor(mouseX, mouseY);
}
public class PFrame extends JFrame {
public PFrame(int width, int height) {
setBounds(100, 100, width, height);
s = new SecondApplet();
add(s);
s.init();
show();
}
}
public class SecondApplet extends PApplet {
int ghostX, ghostY;
public void setup() {
background(0);
noStroke();
}
public void draw() {
background(50);
fill(255);
ellipse(mouseX, mouseY, 10, 10);
fill(0);
ellipse(ghostX, ghostY, 10, 10);
}
public void setGhostCursor(int ghostX, int ghostY) {
this.ghostX = ghostX;
this.ghostY = ghostY;
}
}
One option might be to create a sketch twice the size of your original window and just offset the detected coordinates by half the sketch's size.
Here's a very rough code snippet (assumming blob will be a detected color blob):
int camWidth = 320;
int camHeight = 240;
Capture cam;
void setup(){
size(camWidth * 2,camHeight);
//init cam/opencv/etc.
}
void draw(){
//update cam and get data
image(cam,0,0);
//draw
rect(camWidth+blob.x,blob.y,blob.width,blob.height);
}
To be honest, it might be easier to overlay the tracked information. For example, if you're doing color tracking, just display the outlines of the bounding box of the tracked area.
If you really really want to display another window, you can use a JPanel.
Have a look at this answer for a running code example.
I would recommend using G4P, a GUI library for Processing that has some functionality built in for handling multiple windows. I have used this before with a webcam and it worked well. It comes with a GWindow object that will spawn a window easily. There is a short tutorial on the website that explains the basics.
I've included some old code that I have that will show you the basic idea. What is happening in the code is that I make two GWindows and send them each a PImage to display: one gets a webcam image and the other an effected image. The way you do this is to augment the GWinData object to also include the data you would like to pass to the windows. Instead of making one specific object for each window I just made one object with the two PImages in it. Each GWindow gets its own draw loop (at the bottom of the example) where it loads the PImage from the overridden GWinData object and displays it. In the main draw loop I read the webcam and then process it to create the two images and then store them into the GWinData object.
Hopefully that gives you enough to get started.
import guicomponents.*;
import processing.video.*;
private GWindow window;
private GWindow window2;
Capture video;
PImage sorted;
PImage imgdif; // image with pixel thresholding
MyWinData data;
void setup(){
size(640, 480,P2D); // Change size to 320 x 240 if too slow at 640 x 480
// Uses the default video input, see the reference if this causes an error
video = new Capture(this, 640, 480, 24);
numPixels = video.width * video.height;
data = new MyWinData();
window = new GWindow(this, "TEST", 0,0, 640,480, true, P2D);
window.isAlwaysOnTop();
window.addData(data);
window.addDrawHandler(this, "Window1draw");
window2 = new GWindow(this, "TEST", 640,0 , 640,480, true, P2D);
window2.isAlwaysOnTop();
window2.addData(data);
window2.addDrawHandler(this, "Window2draw");
loadColors("64rev.csv");
colorlength = mycolors.length;
distances = new float[colorlength];
noCursor();
}
void draw()
{
if (video.available())
{
background(0);
video.read();
image(video,0,0);
loadPixels();
imgdif = get(); // clones the last image drawn to the screen v1.1
sorted = get();
/// Removed a lot of code here that did the processing
// hand data to our data class to pass to other windows
data.sortedimage = sorted;
data.difimage = imgdif;
}
}
class MyWinData extends GWinData {
public PImage sortedimage;
public PImage difimage;
MyWinData(){
sortedimage = createImage(640,480,RGB);
difimage = createImage(640,480,RGB);
}
}
public void Window1draw(GWinApplet a, GWinData d){
MyWinData data = (MyWinData) d;
a.image(data.sortedimage, 0,0);
}
public void Window2draw(GWinApplet a, GWinData d){
MyWinData data = (MyWinData) d;
a.image(data.difimage,0,0);
}
I'm a fairly experienced programmer, but new to GUI programming. I'm trying to port a plotting library I wrote for DFL to gtkD, and I can't get drawings to show up. The following code produces a blank window for me. Can someone please tell me what's wrong with it, and/or post minimal example code for getting a few lines onto a DrawingArea and displaying the results in a MainWindow?
import gtk.DrawingArea, gtk.Main, gtk.MainWindow, gdk.GC, gdk.Drawable,
gdk.Color;
void main(string[] args) {
Main.init(args);
auto win = new MainWindow("Hello, world");
win.setDefaultSize(800, 600);
auto drawingArea = new DrawingArea(800, 600);
win.add(drawingArea);
drawingArea.realize();
auto drawable = drawingArea.getWindow();
auto gc = new GC(drawable);
gc.setForeground(new Color(255, 0, 0));
gc.setBackground(new Color(255, 255, 255));
drawable.drawLine(gc, 0, 0, 100, 100);
drawingArea.showAll();
drawingArea.queueDraw();
win.showAll();
Main.run();
}
I have no experience whatsoever in D, but lots in GTK, so with the help of the gtkD tutorial I managed to hack up a minimal example:
import gtk.DrawingArea, gtk.Main, gtk.MainWindow, gdk.GC, gdk.Drawable,
gdk.Color, gtk.Widget;
class DrawingTest : MainWindow
{
this()
{
super("Hello, world");
setDefaultSize(800, 600);
auto drawingArea = new DrawingArea(800, 600);
add(drawingArea);
drawingArea.addOnExpose(&drawStuff);
showAll();
}
bool drawStuff(GdkEventExpose *event, Widget self)
{
auto drawable = self.getWindow();
auto gc = new GC(drawable);
gc.setForeground(new Color(cast(ubyte)255, cast(ubyte)0, cast(ubyte)0));
gc.setBackground(new Color(cast(ubyte)255, cast(ubyte)255, cast(ubyte)255));
drawable.drawLine(gc, 0, 0, 100, 100);
return true;
}
}
void main(string[] args) {
Main.init(args);
new DrawingTest();
Main.run();
}
In GTK, a DrawingArea is actually just a blank widget for you to paint on, and painting on widgets must always be done in the expose-event handler. (Although I understand this will change in GTK 3!)
I understand you can't connect functions as signal callbacks, only delegates, so that's the reason for the DrawingTest class.
I want to "fix" the Background while only the ListFields scrolls.
Current Problem:
Scrolling Down (the surounding box should move with the List)
Corresponding code for the VerticalFieldManager
VerticalFieldManager _bottom_box = new VerticalFieldManager(Field.FIELD_HCENTER | Field.FIELD_VCENTER | VerticalFieldManager.VERTICAL_SCROLL | Field.USE_ALL_HEIGHT)
{
protected void sublayout(int maxWidth, int maxHeight)
{
super.sublayout(maxWidth, maxHeight);
setExtent(maxWidth - 6, maxHeight - 3);
}
protected void paint(Graphics graphics)
{
graphics.clear();
graphics.setColor(Color.WHITE);
graphics.fillRect(0, 0, (this.getWidth()), (this.getHeight()));
graphics.setColor(color_computacenter_light_blue);
graphics.drawRect(0, 0, (this.getWidth()), (this.getHeight()));
super.paint(graphics);
}
};
Any Ideas, how to fix this? Thanks
It's a little difficult to know without more info about the structure of that screen, but the root cause is something to do with the difference between the visible height on screen (given by getHeight()) and the virtual height. You're drawing to the virtual viewport with that paint method, so I think this tweak should fix things:
protected void paint(Graphics graphics)
{
graphics.clear();
graphics.setColor(Color.WHITE);
graphics.fillRect(0, graphics.getClippingRect().y, (this.getWidth()), (this.getHeight()));
graphics.setColor(color_computacenter_light_blue);
graphics.drawRect(0, graphics.getClippingRect().y, (this.getWidth()), (this.getHeight()));
super.paint(graphics);
}
I have created a customized BasicEditField with Border using Bitmap.Now while typing the text,it crosses the border of the BasicEditField.
This is my code
class customEditField1 extends EditField
{
Bitmap mBorder = null;
customEditField1(Bitmap borderBitmap)
{
mBorder = borderBitmap;
}
protected void paint(Graphics graphics)
{
graphics.drawBitmap(0, 0, mBorder.getWidth(),mBorder.getHeight(), mBorder, 0, 0);
super.paint(graphics);
}
}
I want to create a BasicEditField which should hide the previously entered text and displays the newly entered text and the typed text should be with in the border.It should not depends on the number of chars limit.And i want to Apply padding between the text and the border.
You can put BasicEditField into HorizontalFieldManager.
Don't forget to move border bitmap painting from BasicEditField to HorizontalFieldManager.
class ScrollEdit extends HorizontalFieldManager {
Bitmap mBorder = null;
public BasicEditField mEdit = null;
public ScrollEdit(Bitmap border) {
super(HORIZONTAL_SCROLL | NO_HORIZONTAL_SCROLLBAR);
mBorder = border;
mEdit = new EditField(BasicEditField.NO_NEWLINE);
add(mEdit);
}
protected void paint(Graphics graphics) {
graphics.drawBitmap(0, 0, mBorder.getWidth(), mBorder.getHeight(),
mBorder, 0, 0);
super.paint(graphics);
}
}
But you will have to play around with layout and setExtent to size manager and edit correctly. My advice is to try it without border bitmap first.
See Scroll BasicEditField instead of wrap
Talking about the wrap, set padding to BasicEditField within manager or add white space in border bitmap...