Logo Search packages:      
Sourcecode: carmetal version File versions

FunctionObject.java

/* 
Copyright 2006 Rene Grothmann, modified by Eric Hakenholz
This file is part of C.a.R. software.
C.a.R. is a free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, version 3 of the License.
C.a.R. is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
package rene.zirkel.objects;

// file: Functionbject.java
import java.awt.*;
import java.awt.event.*;
import java.util.*;

import rene.gui.*;
import rene.util.xml.*;
import rene.zirkel.*;
import rene.zirkel.construction.*;
import rene.zirkel.dialogs.*;
import rene.zirkel.expression.*;
import rene.zirkel.graphics.*;
import rene.dialogs.*;
import rene.zirkel.structures.Coordinates;
import rene.zirkel.tools.UniversalTracker;

class CurveEditDialog extends ObjectEditDialog {

    TextField VarMin, VarMax, DVar, Var, EX, EY;
    IconBar IC, TypeIB;
    ZirkelCanvas ZC;
    Checkbox Special;

    public CurveEditDialog(ZirkelCanvas zc, FunctionObject o) {
        super(zc.getFrame(), Zirkel.name("edit.function.title"), o, "function");
        ZC=zc;
    }

    public void addFirst(Panel P) {
        FunctionObject f=(FunctionObject) O;

        VarMin=new TextFieldAction(this, "varmin", ""+f.VarMin, 30);
        P.add(new MyLabel(Zirkel.name("function.varmin")));
        P.add(VarMin);
        VarMax=new TextFieldAction(this, "varmax", ""+f.VarMax, 30);
        P.add(new MyLabel(Zirkel.name("function.varmax")));
        P.add(VarMax);
        DVar=new TextFieldAction(this, "dvar", ""+f.DVar, 30);
        P.add(new MyLabel(Zirkel.name("function.dvar")));
        P.add(DVar);

        Var=new TextFieldAction(this, "var", ""+f.getVar(), 30);
        P.add(new MyLabel(Zirkel.name("function.var")));
        P.add(Var);
        String ex=f.getEX();
        if (ex.equals(f.Var)) {
            ex="";
        }
        EX=new TextFieldAction(this, "ex", ""+ex, 30);
        P.add(new MyLabel(Zirkel.name("function.x")));
        P.add(EX);
        EY=new TextFieldAction(this, "ey", ""+f.getEY(), 30);
        P.add(new MyLabel(Zirkel.name("function.y")));
        P.add(EY);

    }

    public void addSecond(Panel P) {
        FunctionObject Func=(FunctionObject) O;

        IC=new IconBar(F);
        IC.setIconBarListener(this);
        IC.addOnOffLeft("filled");
        IC.setState("filled", Func.isFilled());
        IC.setIconBarListener(this);
        P.add(new MyLabel(""));
        P.add(IC);

        TypeIB=new IconBar(F);
        TypeIB.addToggleGroupLeft("type", 6);
        TypeIB.toggle("type", Func.getType());
        P.add(new MyLabel(""));
        P.add(TypeIB);

        P.add(new MyLabel(Zirkel.name("edit.discrete")));
        P.add(Special=new Checkbox());
        Special.setState(Func.isSpecial());
    }

    public void addButton(Panel P) {
        FunctionObject f=(FunctionObject) O;
        if (!f.Var.equals(f.EX)) {
            if (f.Center==null) {
                P.add(new ButtonAction(this, Zirkel.name("edit.function.center"),
                        "SetCenter"));
            } else {
                P.add(new ButtonAction(this, Zirkel.name("edit.function.free"),
                        "SetFree"));
            }
            P.add(new MyLabel(" "));
        }
    }

    public void iconPressed(String o) {
        if (o.equals("filled")) {
            if (IC.getState("filled")) {
                IB.setState("isback", true);
                ThicknessIB.setEnabled("solid", true);
            } else {
                IB.setState("isback", false);
                ThicknessIB.setState("solid", false);
                ThicknessIB.setEnabled("solid", false);
            }
        }
        super.iconPressed(o);
    }

    public void setAction() {
        FunctionObject f=(FunctionObject) O;
        f.setExpressions(Var.getText(), EX.getText(), EY.getText());
        f.setRange(VarMin.getText(), VarMax.getText(), DVar.getText());
        f.setFilled(IC.getState("filled"));
        f.setType(TypeIB.getToggleState("type"));
        f.setSpecial(Special.getState());
    }

    public void doAction(String o) {
        if (o.equals("SetCenter")) {
            ZC.setCurveCenter((FunctionObject) O);
            super.doAction("OK");
        } else if (o.equals("SetFree")) {
            ((FunctionObject) O).Center=null;
            super.doAction("OK");
        } else {
            super.doAction(o);
        }
    }

    public void focusGained(FocusEvent e) {
        VarMin.requestFocus();
    }
}

/**
 * @author Rene
 * 
 * Function objects are parametric curves (or functions).
 * Depending on a parameter t (can have another name),
 * x(t) and y(t) are computed and drawn on the screen.
 * If x(t)=t the object is a function.
 *
 */
00158 public class FunctionObject extends ConstructionObject
        implements PointonObject, HeavyObject,DriverObject {

    Expression EX=null, EY=null;
    public Expression VarMin=null,  VarMax=null,  DVar=null;
    String LASTEX="",LASTEY="",LASTVarMin="",LASTVarMax="",LASTDVar="";
    double X[]={0};
    public String Var[]={"x"};
    boolean Filled=false;
    Expression Center=null;
    protected int Type=0;
    public final static int SQUARE=0,  DIAMOND=1,  CIRCLE=2,  DOT=3,  CROSS=4,  DCROSS=5;
    protected boolean Special=false;
//    Vector RefreshList=new Vector();
    public Vector V=new Vector();
    double cx, cy, ww, wh;
    //this is a main object list which tells if the object needs to recompute :
    Vector DriverObjectList=new Vector();
    boolean NeedsRecompute=true;
    double c0, r0, c, r;

    public FunctionObject(Construction c) {
        super(c);
        VarMin=new Expression("windowcx-windoww", c, this);
        VarMax=new Expression("windowcx+windoww", c, this);
        DVar=new Expression("0", c, this);
        validate();
        updateText();
        cx=c.getX();
        cy=c.getY();
        ww=c.getW();
        wh=c.getH();
        Type=CROSS;
    }

    public void searchDependencies(Construction c) {
        DriverObjectList.clear();
        if (RekValidating) {
            return;
        } // should not happen!
        RekValidating=true;
        Enumeration e=c.elements();
        while (e.hasMoreElements()) {
            ((ConstructionObject) e.nextElement()).setRekFlag(false);
        }
        ConstructionObject oEX[]=EX.getDepList().getArray();
        ConstructionObject oEY[]=EY.getDepList().getArray();
        ConstructionObject oVarMin[]=VarMin.getDepList().getArray();
        ConstructionObject oVarMax[]=VarMax.getDepList().getArray();
        ConstructionObject oDVar[]=DVar.getDepList().getArray();


        for (int i=0; i<oEX.length; i++) {
            recursiveSearchDependencies((ConstructionObject) oEX[i]);
        }
        for (int i=0; i<oEY.length; i++) {
            recursiveSearchDependencies((ConstructionObject) oEY[i]);
        }
        for (int i=0; i<oVarMin.length; i++) {
            recursiveSearchDependencies((ConstructionObject) oVarMin[i]);
        }
        for (int i=0; i<oVarMax.length; i++) {
            recursiveSearchDependencies((ConstructionObject) oVarMax[i]);
        }
        for (int i=0; i<oDVar.length; i++) {
            recursiveSearchDependencies((ConstructionObject) oDVar[i]);
        }

        e=c.elements();
        while (e.hasMoreElements()) {
            ConstructionObject oc=(ConstructionObject) e.nextElement();
            if ((oc.isRekFlag())&&(oc.isDriverObject())) {
                DriverObjectList.addElement(oc);
            }
        }
        RekValidating=false;
        NeedsRecompute=true;
    }

    public void recursiveSearchDependencies(ConstructionObject o) {

        if (o.isRekFlag()) {
            return;
        }
        o.setRekFlag(true);
        ConstructionObject d[]=o.getDepArray();
        for (int i=0; i<d.length; i++) {
            recursiveSearchDependencies(d[i]);
        }
    }

    public void compute() {
        V.clear();

        if (!Valid) {
            return;
        }
        double varmin, varmax, d;
        boolean special=Special, reverse=false;
        try {
            varmin=VarMin.getValue();
            varmax=VarMax.getValue();
            d=DVar.getValue();
            if (varmin>varmax) {
                double h=varmin;
                varmin=varmax;
                varmax=h;
                reverse=true;
            }
            if (d<0) {
                d=-d;
            }
            if (d==0) {
                d=(varmax-varmin)/100;
            } else if (d<(varmax-varmin)/1000) {
                d=(varmax-varmin)/1000;
            }
        } catch (Exception e) {
            Valid=false;
            return;
        }
        X[0]=varmin;
        int nbsteps=(int) Math.round((varmax-varmin)/d)+1;
//        System.out.println("nbsteps="+nbsteps);
        for (int i=0; i<nbsteps; i++) {
            try {
//                System.out.println("x="+X[0]+"  y="+EY.getValue());
                V.add(new Coordinates(EX.getValue(), EY.getValue()));
            } catch (Exception ex) {
            }
            X[0]+=d;
        }
    }

    public void setNeedsToRecompte(boolean n) {
        NeedsRecompute=n;
    }

    public boolean needsToRecompute() {
        boolean needs=false;
        Enumeration pl=DriverObjectList.elements();
        while (pl.hasMoreElements()) {
            DriverObject oc=(DriverObject) pl.nextElement();
            if (oc.somethingChanged()) {
                Global.addClearList(oc);
//                ConstructionObject oo=(ConstructionObject) oc;
//                System.out.println("needsRecompute :"+oo.getName());
                needs=true;
            }
        }

        if ((Cn.getX()!=cx)||(Cn.getY()!=cy)||(Cn.getW()!=ww)||(Cn.getH()!=wh)) {
            cx=Cn.getX();
            cy=Cn.getY();
            ww=Cn.getW();
            wh=Cn.getH();
            needs=true;
        }

        if (NeedsRecompute) {
            NeedsRecompute=false;
            return true;
        }

//        System.out.println("needsRecompute :"+needs);

        return needs;
    }

    public void setFilled(boolean flag) {
        Filled=flag;
    }

    public boolean isFilled() {
        return Filled;
    }

    public String getTag() {
        return "Function";
    }

    public int getN() {
        return N.next();
    }

    public void updateText() {
        if (EX!=null&&EY!=null) {
            setText(text2(Zirkel.name("text.function"), EX.toString(), EY.toString()));
        } else {
            setText(text2(Zirkel.name("text.function"), "", ""));
        }
    }

    public void validate() {
        if (EX!=null&&EY!=null) {
            Valid=EX.isValid()&&EY.isValid()&&VarMin.isValid()&&VarMax.isValid()&&DVar.isValid();
        } else {
            Valid=false;
        }
    }

    public void setExpressions(String t, String ex, String ey) {
        StringTokenizer tok=new StringTokenizer(t);
        Var=new String[tok.countTokens()];
        X=new double[tok.countTokens()];
        int i=0;
        while (tok.hasMoreTokens()) {
            Var[i++]=tok.nextToken();
        }
        if (ex.equals("")) {
            ex=Var[0];
        }
        EX=new Expression(ex, getConstruction(), this, Var);
        EY=new Expression(ey, getConstruction(), this, Var);
        validate();
        searchDependencies(Cn);

    }

    public void setRange(String min, String max, String d) {
        VarMin=new Expression(min, getConstruction(), this);
        VarMax=new Expression(max, getConstruction(), this);
        DVar=new Expression(d, getConstruction(), this);
        searchDependencies(Cn);
    }

    public String getEX() {
        if (EX!=null) {
            return EX.toString();
        } else {
            return Var[0];
        }
    }

    public String getEY() {
        if (EY!=null) {
            return EY.toString();
        } else {
            return "0";
        }
    }
    PolygonFiller PF=null;
    double C1, C2;
    int C, R, W, H;

    public void paint(MyGraphics g, ZirkelCanvas zc) {
        if (!Valid||mustHide(zc)) {
            return;
        }
        Coordinates C;
        Enumeration e=V.elements();
        double c, r;
        g.setColor(this);

        if (Special) {
            while (e.hasMoreElements()) {
                C=(Coordinates) e.nextElement();
                PointObject.drawPoint(g, zc, this, C.X, C.Y, Type);
            }
        } else if (Tracked) {
            zc.UniversalTrack.TrackIG.setColor(this);
            zc.UniversalTrack.setActive(true);
            PolygonDrawer pd=new PolygonDrawer(g, this);
            PolygonDrawer pdt=new PolygonDrawer(zc.UniversalTrack.TrackIG, this);
            if (e.hasMoreElements()) {
                C=(Coordinates) e.nextElement();
                c0=zc.col(C.X);
                r0=zc.row(C.Y);
                pd.startPolygon(c0, r0);
                pdt.startPolygon(c0, r0);
            }
            while (e.hasMoreElements()) {
                C=(Coordinates) e.nextElement();
                c=zc.col(C.X);
                r=zc.row(C.Y);
                if (Math.abs(pd.c()-c)<1000&&Math.abs(pd.r()-r)<1000) {
                    pd.drawTo(c, r);
                    pdt.drawTo(c, r);
                } else {
                    pd.finishPolygon();
                    pdt.finishPolygon();
                    pd.startPolygon(c, r);
                    pdt.startPolygon(c, r);
                }
            }
            pd.finishPolygon();
            pdt.finishPolygon();
        } else {
            PolygonDrawer pd=new PolygonDrawer(g, this);
            if (e.hasMoreElements()) {
                C=(Coordinates) e.nextElement();
                c0=zc.col(C.X);
                r0=zc.row(C.Y);
                pd.startPolygon(c0, r0);
            }
            while (e.hasMoreElements()) {
                C=(Coordinates) e.nextElement();
                c=zc.col(C.X);
                r=zc.row(C.Y);
                if (Math.abs(pd.c()-c)<1000&&Math.abs(pd.r()-r)<1000) {
                    pd.drawTo(c, r);
                } else {
                    pd.finishPolygon();
                    pd.startPolygon(c, r);
                }
            }
            pd.finishPolygon();
        }





    }
    static double x[]=new double[4],  y[]=new double[4];

    public void finish(MyGraphics g, ZirkelCanvas zc) {
        if (isFilled()) {
            if (getEX().equals(getVar())) {
                System.out.println(C1+" "+C2);
                PF.drawTo(zc.col(C2), zc.row(0));
                PF.drawTo(zc.col(C1), zc.row(0));
            } else {
                if (getCenter()!=null) {
                    PF.drawTo(zc.col(getCenter().getX()),
                            zc.row(getCenter().getY()));
                } else {
                    PF.drawTo(zc.col(0), zc.row(0));
                }
            }
            PF.finishPolygon();
        }
    }

    public double getValue()
            throws ConstructionException {
        if (!Valid) {
            throw new InvalidException("exception.invalid");
        }
        return X[0];
    }

    public double getValue(String var)
            throws ConstructionException {
        if (!Valid) {
            throw new InvalidException("exception.invalid");
        }
        for (int i=0; i<Var.length; i++) {
            if (var.equals(Var[i])) {
                return X[i];
            }
        }
        return X[0];
    }

    public double getIntegral()
            throws ConstructionException {
        return getSum();
    }

    public String getDisplayValue() {
        if (getEX().equals(getVar())) {
            return EY.toString();
        } else {
            return "("+EX.toString()+","+EY.toString()+")";
        }
    }

    // Mainly to select the track for delete
    public boolean nearto(int x, int y, ZirkelCanvas zc) {
        if (!displays(zc)) {
            return false;
        }
//        int size=(int) zc.selectionSize();
        Enumeration e=V.elements();
        double xx=zc.x(x), yy=zc.y(y);
        double mymax=(7/Cn.getPixel());
        if (Special) {
            Coordinates CS;
            while (e.hasMoreElements()) {
                CS=(Coordinates) e.nextElement();
                if ((Math.abs(CS.X-xx)<mymax)&&(Math.abs(CS.Y-yy)<mymax)) {

                    return true;
                }
            }
        } else {

            double detmax=mymax*mymax;
            double xA=0, yA=0, xB=0, yB=0;
            Coordinates CS0, CS1;
            if (e.hasMoreElements()) {
                CS0=(Coordinates) e.nextElement();
                xA=CS0.X;
                yA=CS0.Y;

            }
            while (e.hasMoreElements()) {
                CS1=(Coordinates) e.nextElement();
                xB=CS1.X;
                yB=CS1.Y;
                double det=(xx-xA)*(yB-yA)-(yy-yA)*(xB-xA);

                if (Math.abs(det)<detmax) {
                    double prod=(xx-xA)*(xB-xA)+(yy-yA)*(yB-yA);
                    if ((prod>0)&&(prod<(xB-xA)*(xB-xA)+(yB-yA)*(yB-yA))) {
                        return true;
                    }
                }
                xA=xB;
                yA=yB;
            }
        }



        return false;
    }

//    public boolean nearto(int cc, int rr, ZirkelCanvas zc) {
//        
//        if (!displays(zc)) {
//            return false;
//        }
//        int size=(int) zc.selectionSize();
//        double varmin, varmax, d;
//        try {
//            varmin=VarMin.getValue();
//            varmax=VarMax.getValue();
//            d=DVar.getValue();
//            if (varmin>varmax) {
//                double h=varmin;
//                varmin=varmax;
//                varmax=h;
//            }
//            if (d<0) {
//                d=-d;
//            }
//            if (d<(varmax-varmin)/1000) {
//                d=(varmax-varmin)/1000;
//            }
//        } catch (Exception e) {
//            Valid=false;
//            return false;
//        }
//        X[0]=varmin;
//        double x=zc.x(cc), y=zc.y(rr);
//        boolean last=false;
//        double x0=0;
//        double y0=0;
//        while (X[0]<varmax) {
//            X[0]=X[0]+d;
//            if (X[0]>varmax) {
//                X[0]=varmax;
//            }
//            try {
//                double x1=EX.getValue();
//                double y1=EY.getValue();
//                if (Math.abs(zc.col(x1))+Math.abs(zc.col(y1))>1e5) {
//                    throw new Exception("");
//                }
//                if (last) {
//                    Value=Math.abs(cc-zc.col(x1))+Math.abs(rr-zc.row(y1));
//                    if (Value<=size) {
//                        return true;
//                    }
//                    double r=Math.sqrt(Math.abs(x1-x0)*Math.abs(x1-x0)+Math.abs(y1-y0)*Math.abs(y1-y0));
//                    if (r>1e-5) {
//                        double h=((x-x0)*(x1-x0)+(y-y0)*(y1-y0))/r;
//                        if (h>=0&&h<=r) {
//                            Value=Math.abs(((x-x0)*(y1-y0)-(y-y0)*(x1-x0))/r)/zc.dx(1);
//                            if (Value<=size) {
//                                return true;
//                            }
//                        }
//                    }
//                }
//                x0=x1;
//                y0=y1;
//                last=true;
//            } catch (Exception e) {
//                last=false;
//            }
//        }
//        return false;
//    }
    public boolean EditAborted;

    public void edit(ZirkelCanvas zc) {
        ObjectEditDialog d;
        if (!rene.zirkel.Zirkel.IsApplet) {
            eric.JGlobals.EditObject(this);
            return;
        }
        while (true) {
            d=new CurveEditDialog(zc, this);
            d.setVisible(true);
            EditAborted=false;
            if (d.isAborted()) {
                EditAborted=true;
                break;
            } else if (!EX.isValid()) {
                Frame F=zc.getFrame();
                Warning w=new Warning(F, EX.getErrorText(),
                        Zirkel.name("warning"), true);
                w.center(F);
                w.setVisible(true);
            } else if (!EY.isValid()) {
                Frame F=zc.getFrame();
                Warning w=new Warning(F, EY.getErrorText(),
                        Zirkel.name("warning"), true);
                w.center(F);
                w.setVisible(true);
            } else {
                break;
            }
        }
        validate();
        updateText();
        zc.getConstruction().updateCircleDep();
        zc.repaint();
        if (d.wantsMore()) {
            new EditConditionals(zc.getFrame(), this);
            validate();
        }
    }

    public void printArgs(XmlWriter xml) {
        xml.printArg("x", EX.toString());
        xml.printArg("y", EY.toString());
        xml.printArg("var", getVar());
        xml.printArg("min", ""+VarMin);
        xml.printArg("max", ""+VarMax);
        xml.printArg("d", ""+DVar);
        if (Special) {
            xml.printArg("special", "true");
        }
        printType(xml);
        if (Filled) {
            xml.printArg("filled", "true");
        }
        if (getCenter()!=null) {
            xml.printArg("center", getCenter().getName());
        }
    }

    public void setType(int type) {
        Type=type;
    }

    public int getType() {
        return Type;
    }

    public void printType(XmlWriter xml) {
        if (Type!=0) {
            switch (Type) {
                case DIAMOND:
                    xml.printArg("shape", "diamond");
                    break;
                case CIRCLE:
                    xml.printArg("shape", "circle");
                    break;
                case DOT:
                    xml.printArg("shape", "dot");
                    break;
                case CROSS:
                    xml.printArg("shape", "cross");
                    break;
                case DCROSS:
                    xml.printArg("shape", "dcross");
                    break;
            }
        }

    }

    public ConstructionObject copy(double x, double y) {
        FunctionObject fo=new FunctionObject(getConstruction());
        fo.EX=new Expression(EX.toString(), getConstruction(), fo, Var);
        fo.EY=new Expression(EY.toString(), getConstruction(), fo, Var);
        fo.VarMin=new Expression(VarMin.toString(), getConstruction(), fo);
        fo.VarMax=new Expression(VarMax.toString(), getConstruction(), fo);
        fo.DVar=new Expression(DVar.toString(), getConstruction(), fo);
        fo.Special=Special;
        ConstructionObject O=getTranslation();
        fo.setTranslation(this);
        fo.EX.translate();
        fo.EY.translate();
        fo.VarMin.translate();
        fo.VarMax.translate();
        fo.DVar.translate();
        fo.X=X;
        fo.Var=Var;
        fo.validate();
        fo.setTranslation(O);
        fo.searchDependencies(Cn.getTranslation());
        fo.setTargetDefaults();
        return fo;
    }

//    public void translate() {
//        try {
//            EX=new Expression(EX.toString(), getConstruction(), this, Var);
//            EY=new Expression(EY.toString(), getConstruction(), this, Var);
//            VarMin=new Expression(VarMin.toString(), getConstruction(), this);
//            VarMax=new Expression(VarMax.toString(), getConstruction(), this);
//            DVar=new Expression(DVar.toString(), getConstruction(), this);
//            ConstructionObject O=getTranslation();
//            setTranslation(this);
//            EX.translate();
//            EY.translate();
//            VarMin.translate();
//            VarMax.translate();
//            DVar.translate();
//            if (getCenter()!=null) {
//                setCenter(getCenter().getName());
//                Center.translate();
//            }
//            validate();
//            setTranslation(O);
//            System.out.println(EX.toString());
//            System.out.println("**********");
//            searchDependencies(Cn.getTranslation());
//        } catch (Exception e) {
//            System.out.println();
//            System.out.println(getName());
//            System.out.println(e);
//            e.printStackTrace();
//        }
//    }
    public boolean onlynearto(int x, int y, ZirkelCanvas zc) {
        return false;
    //return nearto(x,y,zc);
    }

    public boolean equals(ConstructionObject o) {
        return false;
    }

    public Enumeration depending() {
        DL.reset();
        addDepending(EX);
        addDepending(EY);
        addDepending(VarMin);
        addDepending(VarMax);
        addDepending(DVar);
        return DL.elements();
    }

    public void addDepending(Expression E) {
        if (E!=null) {
            Enumeration e=E.getDepList().elements();
            while (e.hasMoreElements()) {
                DL.add((ConstructionObject) e.nextElement());
            }
        }
    }

    public boolean hasUnit() {
        return false;
    }

    public double evaluateF(double x[])
            throws ConstructionException {
        int n=x.length;
        if (n>X.length) {
            n=X.length;
        }
        for (int i=0; i<n; i++) {
            X[i]=x[i];
        }
        for (int i=n; i<X.length; i++) {
            X[i]=0;
        }
        try {
            return EY.getValue();
        } catch (Exception e) {
            throw new ConstructionException("");
        }
    }

    public double evaluateF(double x)
            throws ConstructionException {
        X[0]=x;
        for (int i=1; i<X.length; i++) {
            X[i]=0;
        }
        try {
            return EY.getValue();
        } catch (Exception e) {

            throw new ConstructionException("");
        }
    }

    public void project(PointObject P) {
        double varmin, varmax, dvar;
        try {
            varmin=VarMin.getValue();
            varmax=VarMax.getValue();
            dvar=DVar.getValue();
            if (varmin>varmax) {
                double h=varmin;
                varmin=varmax;
                varmax=h;
            }
            
            
            if (dvar<0) {
                dvar=-dvar;
            }
            if (dvar==0) {
                dvar=(varmax-varmin)/100;
            } else if (dvar<(varmax-varmin)/1000) {
                dvar=(varmax-varmin)/1000;
            }

        } catch (Exception e) {
            Valid=false;
            return;
        }



        try {
            // if P is a PointOn (a parmetric curve) and function is just plot with points :
            if ((!getEX().equals("x"))&&(P.isPointOn())&&(Special)) {
                if (P.haveBoundOrder()) {
                    X[0]=P.getBoundOrder();
                    P.setXY(EX.getValue(), EY.getValue());
                    return;
                } else {
                    Coordinates CS;
                    Enumeration e=V.elements();
                    double delta0=0, delta1=0, xx=0, yy=0;
                    int i=0, k=0;
                    if (e.hasMoreElements()) {
                        CS=(Coordinates) e.nextElement();
                        delta0=Math.abs(CS.X-P.getX())+Math.abs(CS.Y-P.getY());
                        xx=CS.X;
                        yy=CS.Y;
                    }

                    while (e.hasMoreElements()) {
                        i++;
                        CS=(Coordinates) e.nextElement();
                        delta1=Math.abs(CS.X-P.getX())+Math.abs(CS.Y-P.getY());
                        if (delta1<delta0) {
                            k=i;
                            delta0=delta1;
                            xx=CS.X;
                            yy=CS.Y;

                        }
                    }
                    P.setXY(xx, yy);
                    P.setBoundOrder(varmin+k*dvar);
                    return;
                }

            }

        } catch (Exception e) {
            Valid=false;
            return;
        }



        try {
            // if P is a PointOn (a cartesian function), try to calculate the "real" coords :
            if ((P.isPointOn())&&(getEX().equals("x"))) {
                double x=(P.getX()<varmin)?varmin:P.getX();
                x=(P.getX()>varmax)?varmax:x;
                double y=evaluateF(x);
                P.move(x, y);
                return;
            }
        } catch (Exception e) {
        }

        // Otherwise, at Least get the approx coordinates on the polygon :
        Enumeration e=V.elements();
        double x=0, y=0, x0=0, y0=0, dmin=0;
        boolean started=false;
        while (e.hasMoreElements()) {
            Coordinates c=(Coordinates) e.nextElement();
            double x1=c.X;
            double y1=c.Y;
            if (!started) {
                dmin=Math.sqrt((P.getX()-x1)*(P.getX()-x1)+
                        (P.getY()-y1)*(P.getY()-y1));
                x0=x=x1;
                y0=y=y1;
                started=true;
            } else {
                if (c.flag) {
                    double h=(x1-x0)*(x1-x0)+(y1-y0)*(y1-y0);
                    if (h<1e-10) {
                        h=1e-10;
                    }
                    double g=(P.getX()-x0)*(x1-x0)+(P.getY()-y0)*(y1-y0);
                    if (g<0) {
                        g=0;
                    }
                    if (g>h) {
                        g=h;
                    }
                    double x2=x0+g/h*(x1-x0), y2=y0+g/h*(y1-y0);
                    double d=Math.sqrt((P.getX()-x2)*(P.getX()-x2)+
                            (P.getY()-y2)*(P.getY()-y2));
                    if (d<dmin) {
                        dmin=d;
                        x=x2;
                        y=y2;
                    }
                }
                x0=x1;
                y0=y1;
            }
        }
        if (started) {
            P.setXY(x, y);
            P.Valid=true;
        } else {
            P.Valid=false;
        }


//        X[0]=varmin;
//        double x=0, y=0, x0=0, y0=0, dmin=0;
//        boolean started=false;
//        while (true) {
//            try {
//                double x1=EX.getValue();
//                double y1=EY.getValue();
//                if (!started) {
//                    dmin=Math.sqrt((P.getX()-x1)*(P.getX()-x1)+
//                            (P.getY()-y1)*(P.getY()-y1));
//                    x0=x=x1;
//                    y0=y=y1;
//                    started=true;
//                } else {
//                    double h=(x1-x0)*(x1-x0)+(y1-y0)*(y1-y0);
//                    double g=(P.getX()-x0)*(x1-x0)+(P.getY()-y0)*(y1-y0);
//                    if (g<0) {
//                        g=0;
//                    }
//                    if (g>h) {
//                        g=h;
//                    }
//                    double x2=x0+g/h*(x1-x0), y2=y0+g/h*(y1-y0);
//                    double d=Math.sqrt((P.getX()-x2)*(P.getX()-x2)+
//                            (P.getY()-y2)*(P.getY()-y2));
//                    if (d<dmin) {
//                        dmin=d;
//                        x=x2;
//                        y=y2;
//                    }
//                    x0=x1;
//                    y0=y1;
//                }
//            } catch (Exception e) {
//            }
//            if (X[0]>=varmax) {
//                break;
//            }
//            X[0]=X[0]+dvar;
//            if (X[0]>varmax) {
//                X[0]=varmax;
//            }
//        }
//        if (started) {
//            P.setXY(x, y);
//        }
    }

    public double getSum() {
        double varmin, varmax, dvar;
        boolean reverse=false;
        boolean parametric=!getEX().equals(getVar());
        try {
            varmin=VarMin.getValue();
            varmax=VarMax.getValue();
            dvar=DVar.getValue();
            if (varmin>varmax) {
                double h=varmin;
                varmin=varmax;
                varmax=h;
                reverse=true;
            }
            if (dvar<0) {
                dvar=-dvar;
            }
            if (dvar==0) {
                dvar=(varmax-varmin)/100;
            } else if (dvar<(varmax-varmin)/1000) {
                dvar=(varmax-varmin)/1000;
            }
        } catch (Exception e) {
            Valid=false;
            return 0;
        }
        X[0]=varmin;
        double x0=0, y0=0;
        boolean started=false;
        double sum=0;
        while (true) {
            try {
                double x1=EX.getValue();
                double y1=EY.getValue();
                if (parametric) {
                    double x=0, y=0;
                    if (getCenter()!=null) {
                        x=getCenter().getX();
                        y=getCenter().getY();
                    }
                    if (started) {
                        sum+=((x0-x)*(y1-y)-(y0-y)*(x1-x))/2;
                    }
                } else {
                    if (started) {
                        if (Special) {
                            if (reverse) {
                                sum+=(x1-x0)*y1;
                            } else {
                                sum+=(x1-x0)*y0;
                            }
                        } else {
                            sum+=(x1-x0)*(y0+y1)/2;
                        }
                    }
                }
                x0=x1;
                y0=y1;
                started=true;
            } catch (Exception e) {
            }
            if (X[0]>=varmax) {
                break;
            }
            X[0]=X[0]+dvar;
            if (X[0]>varmax) {
                X[0]=varmax;
            }
        }
        return sum;
    }

    public double getLength() {
        double varmin, varmax, dvar;
        boolean reverse=false;
        boolean parametric=!getEX().equals(getVar());
        try {
            varmin=VarMin.getValue();
            varmax=VarMax.getValue();
            dvar=DVar.getValue();
            if (varmin>varmax) {
                double h=varmin;
                varmin=varmax;
                varmax=h;
                reverse=true;
            }
            if (dvar<0) {
                dvar=-dvar;
            }
            if (dvar==0) {
                dvar=(varmax-varmin)/100;
            } else if (dvar<(varmax-varmin)/1000) {
                dvar=(varmax-varmin)/1000;
            }
        } catch (Exception e) {
            Valid=false;
            return 0;
        }
        X[0]=varmin;
        double x0=0, y0=0;
        boolean started=false;
        double sum=0;
        while (true) {
            try {
                double x1=EX.getValue();
                double y1=EY.getValue();
                if (started) {
                    sum+=Math.sqrt((x1-x0)*(x1-x0)+(y1-y0)*(y1-y0));
                }
                started=true;
                x0=x1;
                y0=y1;
            } catch (Exception e) {
            }
            if (X[0]>=varmax) {
                break;
            }
            X[0]=X[0]+dvar;
            if (X[0]>varmax) {
                X[0]=varmax;
            }
        }
        return sum;
    }

    public boolean isSpecial() {
        return Special;
    }

    public void setSpecial(boolean f) {
        Special=f;
    }

    public void project(PointObject P, double alpha) {
        project(P);
    }

    public boolean maybeTransparent() {
        return true;
    }

    public boolean canDisplayName() {
        return false;
    }

    public void setCenter(String s) {
        if (Cn==null) {
            return;
        }
        Center=new Expression("@\""+s+"\"", Cn, this);
    }

    public boolean isFilledForSelect() {
        return false;
    }

    public PointObject getCenter() {
        try {
            return (PointObject) Center.getObject();
        } catch (Exception e) {
            return null;
        }
    }

    public String getVar() {
        String vars=Var[0];
        for (int i=1; i<Var.length; i++) {
            vars=vars+" "+Var[i];
        }
        return vars;
    }

    public boolean canInteresectWith(ConstructionObject o) {
        return true;
    }

    public boolean isDriverObject(){
        return true;
    }

    public boolean somethingChanged() {
        boolean b=!EX.toString().equals(LASTEX);
        b=b || !EY.toString().equals(LASTEY);
        
        return b;
    }

    public void clearChanges() {
        LASTEX=EX.toString();
        LASTEY=EY.toString();
    }
}

Generated by  Doxygen 1.6.0   Back to index