Loading...
Logo
Processing Forum
EDIT: Let me break this down a bit.

Hello all!

I am trying to upscale a webcam stream using JMyron. I have noticed that processing copes badly with higher resolution input, so Instead I want the input scaled up twice the size so it fills up a little more of the screen. Is there an easy way I am missing here, or do I work on the more manual version down below, currently it does not work.

I though a 2x scale algorithm could be interesting to see on live footage, and it doesn't add many lines of code. But alas I am just getting a grey rectangle it is the right size (twice the capture resolution) but no video. I think I am making some error on the display side of things, the math seems right. Here is the code:

Copy code
  1. import JMyron.*;
    JMyron m;
    int camWidth = 320; //capture resolution
    int camHeight = 240;

    void setup(){
      size(640,480); // size is twice the capture res
      m = new JMyron();
      m.start(camWidth,camHeight);
      m.findGlobs(0);
      println("Myron " + m.version());
    }

    void draw(){
      m.update();//update the camera
      int[] img = m.image(); //get frame of the camera
      int B,D,E,F,H,E0,E1,E2,E3;
      loadPixels();
      /*
          this is my implementation of super2x it uses a 9x9 grid around the pixel
                        A  | B  | C  |
                        D  | E  | F  |
                        G  | H  | I  |
         where E is expanded to four pixels
                        E0 | E1
                        E2 | E2
         based on the relation between different diagonals: B-F, F-H, H-D, D-B
         see: http://scale2x.sourceforge.net/algorithm.html for full detials
      */
      for(int i=0;i<camWidth*camHeight;i++){ //loop through all the captured pixels
          E = color(img[i]);
          // checks if given pixel is at an edge and if so fills the of edge pixel with E's value.
          B = i < camWidth                                     ? E : color(img[i-camWidth]);// pixel above E
          D = i < 1                                                  ? E : color(img[i-1]);// pixel to the left of E
          F = i > camWidth * camHeight - 1              ? E : color(img[i+1]);// pixel to the right of E
          H = i > camWidth * camHeight - camWidth ? E : color(img[i+camWidth]);// pixel below E
          // checks for diagonal relations
          if (B != H && D != F){
            E0 = D == B ? D : E;
            E1 = B == F ? F : E;
            E2 = D == H ? D : E;
            E3 = H == F ? F : E;
            // if there are none regular scaling occurs
          } else {
            E0 = E;
            E1 = E;
            E2 = E;
            E3 = E;
          }
          for (int j=0;1<width*height;j++){ // expands the read pixels in to 2 x scale
            pixels[(i*2)] = E0;
            pixels[(i*2+1)] = E1;
            pixels[(i*2+width)] = E2;
            pixels[(i*2+width+1)] = E3;
          }
      }
      updatePixels();
    }


    public void stop(){
      m.stop();//clean up
      super.stop();
    }

Replies(8)

Edited the title and the post to make my question clearer, hopefully somebody knows the answer.
for (int j=0;1<width*height;j++)

this bit looks odd

Hmnn that one should be a j, crucial mistake no doubt but something else isn't working, correcting it doesn't change the outcome.
and what's stopping you just loading the frame into an image and then displaying the image twice as large?

(can't test it here, no video camera)
EDIT: loading it in as an image? Doesn't JMyron already have something to handle the display the img int array and the load and update pixel functions, am I misunderstanding something?
have never used jmyron so i was going by your code, which was using int[] for the camera data.

if you use this version of processing's image() command then it'll resize the image, saving you from having to do any work.

http://processing.org/reference/image_.html

image( img, x, y, width, height);
ok, that is just returning int[].

i was thinking of using createImage, copying the camera data to the new image and then using image() to display that temp image at double size.

example here shows createImage and how to copy data in...
http://processing.org/reference/createImage_.html

Hmmnn that works! Just wondering whether this methods will hold up as I start doing some live pixel manipulation, it might be a bit slow? If not that solves the problem. This helps quite a bit, thanks!
Copy code
  1. import JMyron.*;

    JMyron m;//a camera object
    int camWidth = 320;
    int camHeight = 240;

    void setup(){
      size(960,720);
      m = new JMyron();//make a new instance of the object
      m.start(camWidth,camHeight);//start a capture at 320x240
      m.findGlobs(0);//disable the intelligence to speed up frame rate
    }

    void draw(){
      PImage img = createImage(camWidth, camHeight, RGB);
      img.loadPixels();
      m.update();//update the camera view
      int[] imgCamera = m.image(); //get the normal image of the camera
      loadPixels();
      for(int i=0;i<camWidth*camHeight;i++){ //loop through all the pixels
          img.pixels[i] = imgCamera[i]; //draw each pixel to the screen
      }
      img.updatePixels();
      image(img,0,0,width,height);
    }

    public void stop(){
      m.stop();//stop the object
      super.stop();
    }