예제 #1
0
  /**
   * Create a front from the curve
   *
   * @param curve the curve coordinates
   * @param flip true to flip the pips
   * @return The front as a FieldImpl
   * @throws RemoteException On badness
   * @throws VisADException On badness
   */
  private FieldImpl curveToFront(float[][] curve, boolean flip)
      throws VisADException, RemoteException {

    if (flipTheFlip) {
      flip = !flip;
    }

    // compute various scaling factors
    int len = curve[0].length;
    if (len < 2) {
      return null;
    }
    float[] seg_length = new float[len - 1];
    float curve_length = curveLength(curve, seg_length);
    float delta = curve_length / (len - 1);
    // curve[findex] where
    // float findex = ibase + mul * repeat_shapes[shape][0][j]
    float mul = rprofile_length * zoom / rsegment_length;
    // curve_perp[][findex] * ratio * repeat_shapes[shape][1][j]
    float ratio = delta * mul;

    // compute unit perpendiculars to curve
    float[][] curve_perp = new float[2][len];
    for (int i = 0; i < len; i++) {
      int im = i - 1;
      int ip = i + 1;
      if (im < 0) {
        im = 0;
      }
      if (ip > len - 1) {
        ip = len - 1;
      }
      float yp = curve[0][ip] - curve[0][im];
      float xp = curve[1][ip] - curve[1][im];
      xp = -xp;
      float d = (float) Math.sqrt(xp * xp + yp * yp);
      if (flip) {
        d = -d;
      }
      xp = xp / d;
      yp = yp / d;
      curve_perp[0][i] = xp;
      curve_perp[1][i] = yp;
    }

    // build Vector of FlatFields for each shape of each segment
    Vector inner_field_vector = new Vector();
    for (int segment = 0; true; segment++) {

      // curve[findex] where
      // float findex = ibase + mul * repeat_shapes[shape][0][j]
      float segment_length = (segment == 0) ? fsegment_length : rsegment_length;
      int profile_length = (segment == 0) ? fprofile_length : rprofile_length;
      mul = profile_length * zoom / segment_length;
      // curve_perp[][findex] * ratio * repeat_shapes[shape][1][j]
      // float ratio = delta * mul;

      // figure out if clipping is needed for this segment
      // only happens for last segment
      boolean clip = false;
      float xclip = 0.0f;
      // int ibase = segment * profile_length;
      int ibase = (segment == 0) ? 0 : fprofile_length + (segment - 1) * rprofile_length;
      int iend = ibase + profile_length;
      if (ibase > len - 1) {
        break;
      }
      if (iend > len - 1) {
        clip = true;
        iend = len - 1;
        xclip = (iend - ibase) / mul;
      }

      // set up shapes for first or repeating segment
      int nshapes = nrshapes;
      float[][][] shapes = repeat_shapes;
      int[][][] tris = repeat_tris;
      float[] red = repeat_red;
      float[] green = repeat_green;
      float[] blue = repeat_blue;
      if (segment == 0) {
        nshapes = nfshapes;
        shapes = first_shapes;
        tris = first_tris;
        red = first_red;
        green = first_green;
        blue = first_blue;
      }

      // iterate over shapes for segment
      for (int shape = 0; shape < nshapes; shape++) {
        float[][] samples = shapes[shape];
        int[][] ts = tris[shape];
        /*
        // if needed, clip shape
        if (clip) {
        float[][][] outs = new float[1][][];
        int[][][] outt = new int[1][][];
        DelaunayCustom.clip(samples, ts, 1.0f, 0.0f, xclip, outs, outt);
        samples = outs[0];
        ts = outt[0];
        }
        */
        if ((samples == null) || (samples[0].length < 1)) {
          break;
        }

        float[][] ss = mapShape(samples, len, ibase, mul, ratio, curve, curve_perp);

        // **** get rid of previous calls to fill() ****
        ts = DelaunayCustom.fill(ss);

        // jeffmc: For now don't clip. This seems to fix the problem of too short a front
        boolean DOCLIP = false;
        if (clip && DOCLIP) {
          float[][] clip_samples = {
            {xclip, xclip, xclip - CLIP_DELTA},
            {CLIP_DELTA, -CLIP_DELTA, 0.0f}
          };
          float[][] clip_ss = mapShape(clip_samples, len, ibase, mul, ratio, curve, curve_perp);
          // now solve for:
          //   xc * clip_samples[0][0] + yc * clip_samples[1][0] = 1
          //   xc * clip_samples[0][1] + yc * clip_samples[1][1] = 1
          //   xc * clip_samples[0][2] + yc * clip_samples[1][2] < 1
          float det =
              (clip_samples[0][1] * clip_samples[1][0] - clip_samples[0][0] * clip_samples[1][1]);
          float xc = (clip_samples[1][0] - clip_samples[1][1]) / det;
          float yc = (clip_samples[0][1] - clip_samples[0][0]) / det;
          float v = 1.0f;
          if (xc * clip_samples[0][2] + yc * clip_samples[1][2] > v) {
            xc = -xc;
            yc = -yc;
            v = -v;
          }

          float[][][] outs = new float[1][][];
          int[][][] outt = new int[1][][];
          DelaunayCustom.clip(ss, ts, xc, yc, v, outs, outt);
          ss = outs[0];
          ts = outt[0];
        }

        if (ss == null) {
          break;
        }
        int n = ss[0].length;

        // create color values for field
        float[][] values = new float[3][n];
        float r = red[shape];
        float g = green[shape];
        float b = blue[shape];
        for (int i = 0; i < n; i++) {
          values[0][i] = r;
          values[1][i] = g;
          values[2][i] = b;
        }

        // construct set and field
        DelaunayCustom delaunay = new DelaunayCustom(ss, ts);
        Irregular2DSet set = new Irregular2DSet(curve_type, ss, null, null, null, delaunay);
        FlatField field = new FlatField(front_inner, set);
        field.setSamples(values, false);
        inner_field_vector.addElement(field);
        // some crazy bug - see Gridded3DSet.makeNormals()
      } // end for (int shape=0; shape<nshapes; shape++)
    } // end for (int segment=0; true; segment++)

    int nfields = inner_field_vector.size();
    Integer1DSet iset = new Integer1DSet(front_index, nfields);
    FieldImpl front = new FieldImpl(front_type, iset);
    FlatField[] fields = new FlatField[nfields];
    for (int i = 0; i < nfields; i++) {
      fields[i] = (FlatField) inner_field_vector.elementAt(i);
    }
    front.setSamples(fields, false);
    return front;
  }
예제 #2
0
  /**
   * run 'java FlowTest middle_latitude' to test with (lat, lon) run 'java FlowTest middle_latitude
   * x' to test with (lon, lat) adjust middle_latitude for south or north
   */
  public static void main(String args[]) throws VisADException, RemoteException {
    double mid_lat = -10.0;
    if (args.length > 0) {
      try {
        mid_lat = Double.valueOf(args[0]).doubleValue();
      } catch (NumberFormatException e) {
      }
    }
    boolean swap = (args.length > 1);
    RealType lat = RealType.Latitude;
    RealType lon = RealType.Longitude;
    RealType[] types;
    if (swap) {
      types = new RealType[] {lon, lat};
    } else {
      types = new RealType[] {lat, lon};
    }
    RealTupleType earth_location = new RealTupleType(types);
    System.out.println("earth_location = " + earth_location + " mid_lat = " + mid_lat);

    RealType flowx = RealType.getRealType("flowx", CommonUnit.meterPerSecond);
    RealType flowy = RealType.getRealType("flowy", CommonUnit.meterPerSecond);
    RealType red = RealType.getRealType("red");
    RealType green = RealType.getRealType("green");
    EarthVectorType flowxy = new EarthVectorType(flowx, flowy);
    TupleType range = null;

    range = new TupleType(new MathType[] {flowxy, red, green});
    FunctionType flow_field = new FunctionType(earth_location, range);

    DisplayImpl display = new DisplayImplJ3D("display1", new TwoDDisplayRendererJ3D());
    ScalarMap xmap = new ScalarMap(lon, Display.XAxis);
    display.addMap(xmap);
    ScalarMap ymap = new ScalarMap(lat, Display.YAxis);
    display.addMap(ymap);
    ScalarMap flowx_map = new ScalarMap(flowx, Display.Flow1X);
    display.addMap(flowx_map);
    flowx_map.setRange(-10.0, 10.0);
    ScalarMap flowy_map = new ScalarMap(flowy, Display.Flow1Y);
    display.addMap(flowy_map);
    flowy_map.setRange(-10.0, 10.0);
    FlowControl flow_control = (FlowControl) flowy_map.getControl();
    flow_control.setFlowScale(0.05f);
    display.addMap(new ScalarMap(red, Display.Red));
    display.addMap(new ScalarMap(green, Display.Green));
    display.addMap(new ConstantMap(1.0, Display.Blue));

    double lonlow = -10.0;
    double lonhi = 10.0;
    double latlow = mid_lat - 10.0;
    double lathi = mid_lat + 10.0;
    Linear2DSet set;
    if (swap) {
      set = new Linear2DSet(earth_location, lonlow, lonhi, N, latlow, lathi, N);
    } else {
      set = new Linear2DSet(earth_location, latlow, lathi, N, lonlow, lonhi, N);
    }
    double[][] values = new double[4][N * N];
    int m = 0;
    for (int i = 0; i < N; i++) {
      for (int j = 0; j < N; j++) {
        int k = i;
        int l = j;
        if (swap) {
          k = j;
          l = i;
        }
        double u = (N - 1.0) / 2.0 - l;
        double v = k - (N - 1.0) / 2.0;
        // double u = 2.0 * k / (N - 1.0) - 1.0;
        // double v = 2.0 * l / (N - 1.0);
        double fx = 6.0 * u;
        double fy = 6.0 * v;
        values[0][m] = fx;
        values[1][m] = fy;
        values[2][m] = u;
        values[3][m] = v;
        m++;
      }
    }
    FlatField field = new FlatField(flow_field, set);
    field.setSamples(values);
    DataReferenceImpl ref = new DataReferenceImpl("ref");
    ref.setData(field);
    display.addReference(ref);

    // create JFrame (i.e., a window) for display and slider
    JFrame frame = new JFrame("test FlowTest");
    frame.addWindowListener(
        new WindowAdapter() {
          public void windowClosing(WindowEvent e) {
            System.exit(0);
          }
        });

    // create JPanel in JFrame
    JPanel panel = new JPanel();
    panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
    panel.setAlignmentY(JPanel.TOP_ALIGNMENT);
    panel.setAlignmentX(JPanel.LEFT_ALIGNMENT);
    frame.getContentPane().add(panel);

    // add display to JPanel
    panel.add(display.getComponent());

    // set size of JFrame and make it visible
    frame.setSize(500, 500);
    frame.setVisible(true);
  }