/* GeoGebra - Dynamic Mathematics for Everyone http://www.geogebra.org This file is part of GeoGebra. This program is 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. */ /* * AlgoJoinPoints.java * * Created on 30. August 2001, 21:37 */ package org.geogebra.common.kernel.algos; import java.math.BigInteger; import java.util.HashMap; import java.util.HashSet; import org.geogebra.common.euclidian.EuclidianConstants; import org.geogebra.common.kernel.Construction; import org.geogebra.common.kernel.StringTemplate; import org.geogebra.common.kernel.commands.Commands; import org.geogebra.common.kernel.geos.GeoElement; import org.geogebra.common.kernel.geos.GeoLine; import org.geogebra.common.kernel.geos.GeoPoint; import org.geogebra.common.kernel.geos.GeoVec3D; import org.geogebra.common.kernel.kernelND.GeoElementND; import org.geogebra.common.kernel.prover.NoSymbolicParametersException; import org.geogebra.common.kernel.prover.polynomial.PPolynomial; import org.geogebra.common.kernel.prover.polynomial.PVariable; import org.geogebra.common.util.debug.Log; /** * * @author Markus */ public class AlgoJoinPoints extends AlgoElement implements SymbolicParametersAlgo, SymbolicParametersBotanaAlgo { private GeoPoint P, Q; // input private GeoLine g; // output private PPolynomial[] polynomials; private PVariable[] botanaVars; /** Creates new AlgoJoinPoints */ public AlgoJoinPoints(Construction cons, String label, GeoPoint P, GeoPoint Q) { this(cons, P, Q); g.setLabel(label); } public AlgoJoinPoints(Construction cons, GeoPoint P, GeoPoint Q) { super(cons); this.P = P; this.Q = Q; g = new GeoLine(cons); g.setStartPoint(P); g.setEndPoint(Q); setInputOutput(); // for AlgoElement // compute line through P, Q compute(); addIncidence(); } /** * @author Tam * * for special cases of e.g. AlgoIntersectLineConic */ private void addIncidence() { P.addIncidence(g, true); Q.addIncidence(g, true); } @Override public Commands getClassName() { return Commands.Line; } @Override public int getRelatedModeID() { return EuclidianConstants.MODE_JOIN; } // for AlgoElement @Override protected void setInputOutput() { input = new GeoElement[2]; input[0] = P; input[1] = Q; super.setOutputLength(1); super.setOutput(0, g); setDependencies(); // done by AlgoElement } public GeoLine getLine() { return g; } // Made public for LocusEqu public GeoPoint getP() { return P; } // Made public for LocusEqu public GeoPoint getQ() { return Q; } // calc the line g through P and Q @Override public final void compute() { // g = P v Q <=> g_n : n = P x Q // g = cross(P, Q) GeoVec3D.lineThroughPoints(P, Q, g); } @Override final public String toString(StringTemplate tpl) { // Michael Borcherds 2008-03-31 // simplified to allow better translation return getLoc().getPlain("LineThroughAB", P.getLabel(tpl), Q.getLabel(tpl)); } // Simon Weitzhofer 2012-04-03 @Override public SymbolicParameters getSymbolicParameters() { return new SymbolicParameters(this); } @Override public void getFreeVariables(HashSet<PVariable> variables) throws NoSymbolicParametersException { if (P != null && Q != null) { P.getFreeVariables(variables); Q.getFreeVariables(variables); return; } throw new NoSymbolicParametersException(); } @Override public int[] getDegrees() throws NoSymbolicParametersException { if (P != null && Q != null) { int[] degree1 = P.getDegrees(); int[] degree2 = Q.getDegrees(); return SymbolicParameters.crossDegree(degree1, degree2); } throw new NoSymbolicParametersException(); } @Override public BigInteger[] getExactCoordinates( final HashMap<PVariable, BigInteger> values) throws NoSymbolicParametersException { if (P != null && Q != null) { BigInteger[] coords1 = P.getExactCoordinates(values); BigInteger[] coords2 = Q.getExactCoordinates(values); if (coords1 != null && coords2 != null) { return SymbolicParameters.crossProduct(coords1, coords2); } } throw new NoSymbolicParametersException(); } @Override public PPolynomial[] getPolynomials() throws NoSymbolicParametersException { if (polynomials != null) { return polynomials; } if (P != null && Q != null) { PPolynomial[] coords1 = P.getPolynomials(); PPolynomial[] coords2 = Q.getPolynomials(); if (coords1 != null && coords2 != null) { polynomials = PPolynomial.crossProduct(coords1, coords2); Log.debug("polys(" + g.getLabelSimple() + "): " + polynomials[0].toString() + "," + polynomials[1].toString() + "," + polynomials[2].toString()); return polynomials; } } throw new NoSymbolicParametersException(); } @Override public PVariable[] getBotanaVars(GeoElementND geo) throws NoSymbolicParametersException { if (botanaVars != null) { return botanaVars; } botanaVars = SymbolicParameters.addBotanaVarsJoinPoints(input); return botanaVars; } @Override public PPolynomial[] getBotanaPolynomials(GeoElementND geo) throws NoSymbolicParametersException { // It's OK, polynomials for lines are only created when a third point is // lying on them, too: return null; } }